mirror of
https://git.do.srb2.org/STJr/SRB2.git
synced 2024-11-15 17:22:12 +00:00
Merge branch 'lua-lump-load-only' into 'master'
Lua lump load only This branch prevents the following Lua functions from being used within hooks or coroutines, to prevent netgame desync problems or any other similar oddities when using these weirdly: * `freeslot()` * `addHook()` * `hud.add()` * `COM_AddCommand()` * `CV_RegisterVar()` All of the above should only be called when the Lua script is being loaded (i.e. it takes place the same instant a ".lua" file or a WAD file with a "LUA_" lump is being loaded) To put it another way: ``` //This is valid usage: freeslot("MT_TEST") //This is NOT valid usage addHook("MobjSpawn", function() freeslot("MT_TEST2") end, MT_PLAYER) ``` See *Monster Iestyn/Lua lump load only* on the FTP for an exe and test script. See merge request !87
This commit is contained in:
commit
0ac63c0949
6 changed files with 28 additions and 8 deletions
|
@ -7861,11 +7861,14 @@ void FUNCMATH DEH_Check(void)
|
|||
static inline int lib_freeslot(lua_State *L)
|
||||
{
|
||||
int n = lua_gettop(L);
|
||||
int r = 0; // args returned
|
||||
int r = 0; // args returned
|
||||
char *s, *type,*word;
|
||||
|
||||
while (n-- > 0)
|
||||
{
|
||||
if (!lua_lumploading)
|
||||
return luaL_error(L, "This function cannot be called from within a hook or coroutine!");
|
||||
|
||||
while (n-- > 0)
|
||||
{
|
||||
s = Z_StrDup(luaL_checkstring(L,1));
|
||||
type = strtok(s, "_");
|
||||
if (type)
|
||||
|
|
|
@ -22,8 +22,13 @@
|
|||
#include "lua_libs.h"
|
||||
#include "lua_hud.h" // hud_running errors
|
||||
|
||||
// for functions not allowed in hud.add hooks
|
||||
#define NOHUD if (hud_running)\
|
||||
return luaL_error(L, "HUD rendering code should not call this function!");
|
||||
// for functions not allowed in hooks or coroutines (supercedes above)
|
||||
#define NOHOOK if (!lua_lumploading)\
|
||||
return luaL_error(L, "This function cannot be called from within a hook or coroutine!");
|
||||
// for functions only allowed within a level
|
||||
#define INLEVEL if (gamestate != GS_LEVEL)\
|
||||
return luaL_error(L, "This function can only be used in a level!");
|
||||
|
||||
|
@ -184,7 +189,7 @@ static int lib_comAddCommand(lua_State *L)
|
|||
strlwr(name);
|
||||
|
||||
luaL_checktype(L, 2, LUA_TFUNCTION);
|
||||
NOHUD
|
||||
NOHOOK
|
||||
if (lua_gettop(L) >= 3)
|
||||
{ // For the third argument, only take a boolean or a number.
|
||||
lua_settop(L, 3);
|
||||
|
@ -296,7 +301,7 @@ static int lib_cvRegisterVar(lua_State *L)
|
|||
consvar_t *cvar;
|
||||
luaL_checktype(L, 1, LUA_TTABLE);
|
||||
lua_settop(L, 1); // Clear out all other possible arguments, leaving only the first one.
|
||||
NOHUD
|
||||
NOHOOK
|
||||
cvar = lua_newuserdata(L, sizeof(consvar_t));
|
||||
luaL_getmetatable(L, META_CVAR);
|
||||
lua_setmetatable(L, -2);
|
||||
|
|
|
@ -109,8 +109,8 @@ static int lib_addHook(lua_State *L)
|
|||
|
||||
luaL_checktype(L, 1, LUA_TFUNCTION);
|
||||
|
||||
if (hud_running)
|
||||
return luaL_error(L, "HUD rendering code should not call this function!");
|
||||
if (!lua_lumploading)
|
||||
return luaL_error(L, "This function cannot be called from within a hook or coroutine!");
|
||||
|
||||
switch(hook.type)
|
||||
{
|
||||
|
|
|
@ -612,6 +612,9 @@ static int lib_hudadd(lua_State *L)
|
|||
luaL_checktype(L, 1, LUA_TFUNCTION);
|
||||
field = luaL_checkoption(L, 2, "game", hudhook_opt);
|
||||
|
||||
if (!lua_lumploading)
|
||||
return luaL_error(L, "This function cannot be called from within a hook or coroutine!");
|
||||
|
||||
lua_getfield(L, LUA_REGISTRYINDEX, "HUD");
|
||||
I_Assert(lua_istable(L, -1));
|
||||
lua_rawgeti(L, -1, field+2); // HUD[2+]
|
||||
|
|
|
@ -161,6 +161,11 @@ void LUA_ClearExtVars(void)
|
|||
}
|
||||
#endif
|
||||
|
||||
// Use this variable to prevent certain functions from running
|
||||
// if they were not called on lump load
|
||||
// (i.e. they were called in hooks or coroutines etc)
|
||||
boolean lua_lumploading = false;
|
||||
|
||||
// Load a script from a MYFILE
|
||||
static inline void LUA_LoadFile(MYFILE *f, char *name)
|
||||
{
|
||||
|
@ -198,7 +203,9 @@ void LUA_LoadLump(UINT16 wad, UINT16 lump)
|
|||
name[strlen(wadfiles[wad]->filename)+9] = '\0';
|
||||
}
|
||||
|
||||
LUA_LoadFile(&f, name);
|
||||
lua_lumploading = true; // turn on loading flag
|
||||
LUA_LoadFile(&f, name); // actually load file!
|
||||
lua_lumploading = false; // turn off again
|
||||
|
||||
free(name);
|
||||
Z_Free(f.data);
|
||||
|
|
|
@ -38,6 +38,8 @@
|
|||
void LUA_ClearExtVars(void);
|
||||
#endif
|
||||
|
||||
extern boolean lua_lumploading; // is LUA_LoadLump being called?
|
||||
|
||||
void LUA_LoadLump(UINT16 wad, UINT16 lump);
|
||||
#ifdef LUA_ALLOW_BYTECODE
|
||||
void LUA_DumpFile(const char *filename);
|
||||
|
|
Loading…
Reference in a new issue