From aafb49ea89dba570b583103f8163ba8368669a48 Mon Sep 17 00:00:00 2001 From: Zhongwei Yao Date: Fri, 18 Nov 2016 03:37:53 +0000 Subject: [PATCH] Work around the invalid lightuserdata usage for 48-bit platform Static variable's virtual address will exceed 47-bit under 48-bit platform, which causes failure when such variable is used as light user data. This patch changes such static variables to heap variables to get around this issue. Change-Id: Iaf046d567a553cff33109af57e28acdf38c8507b --- src/lib_debug.c | 24 ++++++++++++++++++++---- src/lib_package.c | 17 +++++++++++++++-- src/lj_state.c | 5 +++++ 3 files changed, 40 insertions(+), 6 deletions(-) diff --git a/src/lib_debug.c b/src/lib_debug.c index cda7137e..95cf3b7e 100644 --- a/src/lib_debug.c +++ b/src/lib_debug.c @@ -283,13 +283,29 @@ LJLIB_CF(debug_setuservalue) /* ------------------------------------------------------------------------ */ -static const char KEY_HOOK = 'h'; +static const char *KEY_HOOK = NULL; + +static const char *get_key_hook(lua_State *L, const char **KEY_HOOK) { + if (*KEY_HOOK == NULL) { + char *p = lj_mem_newt(L, sizeof(char), char); + *p = 'h'; + *KEY_HOOK = p; + } + return *KEY_HOOK; +} + +void free_key_hook(lua_State *L) { + if (KEY_HOOK != NULL) { + lj_mem_free(G(L), (void *)KEY_HOOK, sizeof(char)); + KEY_HOOK = NULL; + } +} static void hookf(lua_State *L, lua_Debug *ar) { static const char *const hooknames[] = {"call", "return", "line", "count", "tail return"}; - lua_pushlightuserdata(L, (void *)&KEY_HOOK); + lua_pushlightuserdata(L, (void *)get_key_hook(L, &KEY_HOOK)); lua_rawget(L, LUA_REGISTRYINDEX); if (lua_isfunction(L, -1)) { lua_pushstring(L, hooknames[(int)ar->event]); @@ -334,7 +350,7 @@ LJLIB_CF(debug_sethook) count = luaL_optint(L, arg+3, 0); func = hookf; mask = makemask(smask, count); } - lua_pushlightuserdata(L, (void *)&KEY_HOOK); + lua_pushlightuserdata(L, (void *)get_key_hook(L, &KEY_HOOK)); lua_pushvalue(L, arg+1); lua_rawset(L, LUA_REGISTRYINDEX); lua_sethook(L, func, mask, count); @@ -349,7 +365,7 @@ LJLIB_CF(debug_gethook) if (hook != NULL && hook != hookf) { /* external hook? */ lua_pushliteral(L, "external hook"); } else { - lua_pushlightuserdata(L, (void *)&KEY_HOOK); + lua_pushlightuserdata(L, (void *)get_key_hook(L, &KEY_HOOK)); lua_rawget(L, LUA_REGISTRYINDEX); /* get hook */ } lua_pushstring(L, unmakemask(mask, buff)); diff --git a/src/lib_package.c b/src/lib_package.c index 8c336b02..58a405cc 100644 --- a/src/lib_package.c +++ b/src/lib_package.c @@ -16,6 +16,7 @@ #include "lj_obj.h" #include "lj_err.h" #include "lj_lib.h" +#include "lj_gc.h" /* ------------------------------------------------------------------------ */ @@ -399,11 +400,23 @@ static int lj_cf_package_loader_preload(lua_State *L) /* ------------------------------------------------------------------------ */ -static const int sentinel_ = 0; -#define sentinel ((void *)&sentinel_) +static const int *sentinel_ = NULL; +#define sentinel ((void *)sentinel_) + +void lj_cf_free_sentinel(lua_State *L) { + if (sentinel_ != NULL) { + lj_mem_free(G(L), (void *)sentinel_, sizeof(int)); + sentinel_ = NULL; + } +} static int lj_cf_package_require(lua_State *L) { + if (sentinel_ == NULL) { + int *p = lj_mem_newt(L, sizeof(int), int); + *p = 0; + sentinel_ = p; + } const char *name = luaL_checkstring(L, 1); int i; lua_settop(L, 1); /* _LOADED table will be at index 2 */ diff --git a/src/lj_state.c b/src/lj_state.c index a3bfc45e..10ecb9c7 100644 --- a/src/lj_state.c +++ b/src/lj_state.c @@ -157,6 +157,9 @@ static TValue *cpluaopen(lua_State *L, lua_CFunction dummy, void *ud) return NULL; } +extern void lj_cf_free_sentinel(lua_State *L); +extern void free_key_hook(lua_State *L); + static void close_state(lua_State *L) { global_State *g = G(L); @@ -171,6 +174,8 @@ static void close_state(lua_State *L) lj_mem_freevec(g, g->strhash, g->strmask+1, GCRef); lj_buf_free(g, &g->tmpbuf); lj_mem_freevec(g, tvref(L->stack), L->stacksize, TValue); + lj_cf_free_sentinel(L); + free_key_hook(L); lua_assert(g->gc.total == sizeof(GG_State)); #ifndef LUAJIT_USE_SYSMALLOC if (g->allocf == lj_alloc_f)