lua

A copy of the Lua development repository
Log | Files | Refs | README

commit 6e285e539274920830eeec5cd2dde5eeca5863e4
parent b8cdea01908f8d436e9d5a73d640645ea52d5f65
Author: Roberto Ierusalimschy <roberto@inf.puc-rio.br>
Date:   Wed, 23 Oct 2019 10:30:35 -0300

More pious implementation of 'string.dump'

In 'str__dump', the call to 'lua_dump' assumes the function is on the
top of the stack, but the manual allows 'luaL_buffinit' to push stuff
on the stack (although the current implementation does not).  So, the
call to 'luaL_buffinit' must come after the call to 'lua_dump'.

Diffstat:
Mlstrlib.c | 32++++++++++++++++++++++++--------
1 file changed, 24 insertions(+), 8 deletions(-)

diff --git a/lstrlib.c b/lstrlib.c @@ -206,22 +206,38 @@ static int str_char (lua_State *L) { } -static int writer (lua_State *L, const void *b, size_t size, void *B) { - (void)L; - luaL_addlstring((luaL_Buffer *) B, (const char *)b, size); +/* +** Buffer to store the result of 'string.dump'. It must be initialized +** after the call to 'lua_dump', to ensure that the function is on the +** top of the stack when 'lua_dump' is called. ('luaL_buffinit' might +** push stuff.) +*/ +struct str_Writer { + int init; /* true iff buffer has been initialized */ + luaL_Buffer B; +}; + + +static int writer (lua_State *L, const void *b, size_t size, void *ud) { + struct str_Writer *state = (struct str_Writer *)ud; + if (!state->init) { + state->init = 1; + luaL_buffinit(L, &state->B); + } + luaL_addlstring(&state->B, (const char *)b, size); return 0; } static int str_dump (lua_State *L) { - luaL_Buffer b; + struct str_Writer state; int strip = lua_toboolean(L, 2); luaL_checktype(L, 1, LUA_TFUNCTION); - lua_settop(L, 1); - luaL_buffinit(L,&b); - if (lua_dump(L, writer, &b, strip) != 0) + lua_settop(L, 1); /* ensure function is on the top of the stack */ + state.init = 0; + if (lua_dump(L, writer, &state, strip) != 0) return luaL_error(L, "unable to dump given function"); - luaL_pushresult(&b); + luaL_pushresult(&state.B); return 1; }