Luanti 5.18.0-dev
Loading...
Searching...
No Matches
l_base.h
Go to the documentation of this file.
1// Luanti
2// SPDX-License-Identifier: LGPL-2.1-or-later
3// Copyright (C) 2013 celeron55, Perttu Ahola <celeron55@gmail.com>
4
5#pragma once
6
7#include "common/c_types.h"
8#include "common/helper.h"
9#include "config.h"
10#include "debug.h"
11#include "gamedef.h"
12
13extern "C" {
14#include <lua.h>
15#include <lauxlib.h>
16}
17
18#if CHECK_CLIENT_BUILD()
19class Client;
20class GUIEngine;
21#endif
22class EmergeThread;
23class ScriptApiBase;
24class Server;
25class Environment;
28
29class ModApiBase : protected LuaHelper {
30public:
31 static ScriptApiBase* getScriptApiBase(lua_State *L);
32 static Server* getServer(lua_State *L);
34 #if CHECK_CLIENT_BUILD()
35 static Client* getClient(lua_State *L);
36 static GUIEngine* getGuiEngine(lua_State *L);
37 static SSCSMEnvironment *getSSCSMEnv(lua_State *L);
38 #endif // !SERVER
39 static EmergeThread* getEmergeThread(lua_State *L);
40
41 static IGameDef* getGameDef(lua_State *L);
42
43 static Environment* getEnv(lua_State *L);
44
45 // When we are not loading the mod, this function returns "."
46 static std::string getCurrentModPath(lua_State *L);
47
48 // Get an arbitrary subclass of ScriptApiBase
49 // by using dynamic_cast<> on getScriptApiBase()
50 template<typename T>
51 static T* getScriptApi(lua_State *L) {
52 ScriptApiBase *scriptIface = getScriptApiBase(L);
53 T *scriptIfaceDowncast = dynamic_cast<T*>(scriptIface);
54 if (!scriptIfaceDowncast) {
55 throw LuaError("Requested unavailable ScriptApi - core engine bug!");
56 }
57 return scriptIfaceDowncast;
58 }
59
60 static bool registerFunction(lua_State *L,
61 const char* name,
62 lua_CFunction func,
63 int top);
64
65 template<typename T>
66 static void registerClass(lua_State *L,
67 const luaL_Reg *methods,
68 const luaL_Reg *metamethods)
69 {
70 luaL_newmetatable(L, T::className);
71 luaL_register(L, NULL, metamethods);
72 int metatable = lua_gettop(L);
73
74 lua_newtable(L);
75 luaL_register(L, NULL, methods);
76 int methodtable = lua_gettop(L);
77
78 lua_pushvalue(L, methodtable);
79 lua_setfield(L, metatable, "__index");
80
81 lua_getfield(L, metatable, "__tostring");
82 bool default_tostring = lua_isnil(L, -1);
83 lua_pop(L, 1);
84 if (default_tostring) {
85 lua_pushcfunction(L, ModApiBase::defaultToString<T>);
86 lua_setfield(L, metatable, "__tostring");
87 }
88
89 // Protect the real metatable.
90 lua_pushvalue(L, methodtable);
91 lua_setfield(L, metatable, "__metatable");
92
93 // Pop methodtable and metatable.
94 lua_pop(L, 2);
95 }
96
97 template<typename T>
98 static inline T *checkObject(lua_State *L, int narg)
99 {
100 T *obj = *reinterpret_cast<T**>(luaL_checkudata(L, narg, T::className));
101 if (!obj)
102 luaL_error(L, "Object of type %s has been deleted already", T::className);
103 return obj;
104 }
105
106 /*
107 * Lua does not actually guarantee that an object entirely disappears after `__gc` is called,
108 * so to avoid potential use-after-free we have to unset the pointer upon deleting.
109 * This helper takes the pointer (unsetting it), and returns the old pointer.
110 */
111 template<typename T>
112 static inline T *takeObjectForGC(lua_State *L)
113 {
114 T **ud = reinterpret_cast<T **>(lua_touserdata(L, 1));
115 T *o = *ud;
116 *ud = nullptr;
117 return o;
118 }
119
133 static int l_deprecated_function(lua_State *L, const char *good, const char *bad, lua_CFunction func);
134
135private:
136
137 template<typename T>
138 static int defaultToString(lua_State *L)
139 {
140 auto *t = checkObject<T>(L, 1);
141 lua_pushfstring(L, "%s: %p", T::className, t);
142 return 1;
143 }
144};
Definition client.h:107
Definition emerge_internal.h:25
Definition environment.h:31
implementation of main menu based upon formspecs
Definition guiEngine.h:115
Definition gamedef.h:26
Definition c_types.h:32
Definition helper.h:15
Definition l_base.h:29
static bool registerFunction(lua_State *L, const char *name, lua_CFunction func, int top)
Definition l_base.cpp:86
static int l_deprecated_function(lua_State *L, const char *good, const char *bad, lua_CFunction func)
A wrapper for deprecated functions.
Definition l_base.cpp:97
static void registerClass(lua_State *L, const luaL_Reg *methods, const luaL_Reg *metamethods)
Definition l_base.h:66
static ServerInventoryManager * getServerInventoryMgr(lua_State *L)
Definition l_base.cpp:33
static Server * getServer(lua_State *L)
Definition l_base.cpp:28
static IGameDef * getGameDef(lua_State *L)
Definition l_base.cpp:45
static std::string getCurrentModPath(lua_State *L)
Definition l_base.cpp:72
static int defaultToString(lua_State *L)
Definition l_base.h:138
static ScriptApiBase * getScriptApiBase(lua_State *L)
Definition l_base.cpp:14
static Environment * getEnv(lua_State *L)
Definition l_base.cpp:50
static T * getScriptApi(lua_State *L)
Definition l_base.h:51
static EmergeThread * getEmergeThread(lua_State *L)
Definition l_base.cpp:67
static T * takeObjectForGC(lua_State *L)
Definition l_base.h:112
static T * checkObject(lua_State *L, int narg)
Definition l_base.h:98
The thread that runs SSCSM code.
Definition sscsm_environment.h:26
Definition s_base.h:66
Definition serverinventorymgr.h:17
Definition server.h:178