这是一个非常有用的功能,在排查错误的过程中,可以起到非常好的作用
先来看一段代码
local f = function(x, y)
return x.a + y
end
f(1, 2)
这段代码肯定是会报错的,但是,请注意看下面绿色框里的内容
正常的报错信息里面是没有函数的参数信息的,加上这个信息,对于错误的排查,是能起到非常好的作用的
实现方法
通过修改lua的源代码实现,在源码中搜索 luaL_traceback,参考如下代码进行修改
LUALIB_API void luaL_traceback (lua_State *L, lua_State *L1,
const char *msg, int level) {
lua_Debug ar;
int top = lua_gettop(L);
int last = lastlevel(L1);
int n1 = (last - level > LEVELS1 + LEVELS2) ? LEVELS1 : -1;
if (msg)
lua_pushfstring(L, "%s\n", msg);
luaL_checkstack(L, 10, NULL);
lua_pushliteral(L, "stack traceback:");
while (lua_getstack(L1, level++, &ar)) {
if (n1-- == 0) { /* too many levels? */
lua_pushliteral(L, "\n\t..."); /* add a '...' */
level = last - LEVELS2 + 1; /* and skip to last ones */
}
else {
lua_getinfo(L1, "Slntu", &ar);
lua_pushfstring(L, "\n\t%s:", ar.short_src);
if (ar.currentline > 0)
lua_pushfstring(L, "%d:", ar.currentline);
lua_pushliteral(L, " in ");
pushfuncname(L, &ar);
if (ar.nparams > 0) {
lua_pushliteral(L, ", params:");
}
for (int i = 1; i <= ar.nparams; ++i) {
const char *name = lua_getlocal(L1, &ar, i);
if (name) {
lua_xmove(L1, L, 1); // -3
const char *val = luaL_tolstring(L, -1, NULL); // -2
lua_pushfstring(L, " %s = %s;", name, val); // -1
lua_insert(L, -3);
lua_pop(L, 2);
}
}
if (ar.istailcall)
lua_pushliteral(L, "\n\t(...tail calls...)");
lua_concat(L, lua_gettop(L) - top);
}
}
lua_concat(L, lua_gettop(L) - top);
}