He creado un script GDB para hacer las cosas en la página web vinculada por macs. No es hermoso, y probablemente debería estar adecuadamente envuelto en una función, etc., pero aquí está para los curiosos.
NOTA: Parece que la página web está mal con respecto al nombre del archivo para las funciones lua. En el caso de que la cadena provenga de luaL_dofile()
, el nombre del archivo comienza con un símbolo @
. Si se llaman desde lua_dostring()
. En ese caso, la variable $filename
se establece en la totalidad de la cadena que se pasa al lua_dostring()
, y el usuario probablemente solo esté interesado en una o dos líneas de contexto de ese archivo. No estaba seguro de cómo arreglarlo.
set $p = L->base_ci
while ($p <= L->ci)
if ($p->func->value.gc->cl.c.isC == 1)
printf "0x%x C FUNCTION", $p
output $p->func->value.gc->cl.c.f
printf "\n"
else
if ($p->func.tt==6)
set $proto = $p->func->value.gc->cl.l.p
set $filename = (char*)(&($proto->source->tsv) + 1)
set $lineno = $proto->lineinfo[ $p->savedpc - $proto->code -1 ]
printf "0x%x LUA FUNCTION : %d %s\n", $p, $lineno, $filename
else
printf "0x%x LUA BASE\n", $p
end
end
set $p = $p+1
end
Esto da salida a algo como:
0x1002b0 LUA BASE
0x1002c8 LUA FUNCTION : 4 @a.lua
0x1002e0 LUA FUNCTION : 3 @b.lua
0x100310 C FUNCTION(lua_CFunction) 0x1fda <crash_function(lua_State*)>
Cuando puedo depurar el choque de este código:
// This is a file designed to crash horribly when run.
// It should generate a core, and it should crash inside some lua functions
#include "lua.h"
#include "lualib.h"
#include "lauxlib.h"
#include <iostream>
#include <signal.h>
int crash_function(lua_State * L)
{
raise(SIGABRT); //This should dump core!
return 0;
}
int main()
{
lua_State * L = luaL_newstate();
lua_pushcfunction(L, crash_function);
lua_setfield(L, LUA_GLOBALSINDEX, "C");
luaopen_base(L);
if(1 == luaL_dofile(L, "a.lua"))
{
std::cout<<"ERROR: "<<lua_tostring(L,-1)<<std::endl;
return 1;
}
if(1 == luaL_dofile(L, "b.lua"))
{
std::cout<<"ERROR: "<<lua_tostring(L,-1)<<std::endl;
return 1;
}
lua_getfield(L, LUA_GLOBALSINDEX, "A");
lua_pcall(L, 0, 0, NULL);
}
Con a.lua
-- a.lua
-- just calls B, which calls C which should crash
function A()
B()
end
y b.lua
-- b.lua
function B()
C()
end
Por lo tanto, tal vez usted ha leído esto ya, pero yo no lo sabe, así que no tenga mal humor, por favor;) [Lua pila de llamadas con C++ depurador] (http://zeuxcg.org/2010/11/07/lua-callstack-with-c-debugger /) –
@macs Esa es una muy buena visión general. La sección "Inspeccionar estructuras de datos Lua" es la clave. Había resuelto la mayor parte de eso, pero es bastante engorroso de usar. Probablemente buscaré escribir macros/scripts GDB para hacerlo viable. –
Me complace darle una mano, también hay [StackTracePlus] (https://github.com/ignacio/StackTracePlus) pero tendrá que modificar la función de llamada C, si estoy en lo correcto. Entonces es bastante inútil en este caso particular. –