static const char *getobjname (lua_State *L, StkId obj, const char **name) { StkId func = aux_stackedfunction(L, 0, obj); if (!isLmark(func)) return NULL; /* not an active Lua function */ else { Proto *p = infovalue(func)->func->f.l; int pc = currentpc(func); int stackpos = obj - (func+1); /* func+1 == function base */ Instruction i = luaG_symbexec(p, pc, stackpos); LUA_ASSERT(pc != -1, "function must be active"); switch (GET_OPCODE(i)) { case OP_GETGLOBAL: { *name = p->kstr[GETARG_U(i)]->str; return "global"; } case OP_GETLOCAL: { *name = luaF_getlocalname(p, GETARG_U(i)+1, pc); LUA_ASSERT(*name, "local must exist"); return "local"; } case OP_PUSHSELF: case OP_GETDOTTED: { *name = p->kstr[GETARG_U(i)]->str; return "field"; } default: return NULL; /* no useful name found */ } } }
static const char * getobjname(CallInfo * ci, int stackpos, const char **name) { if (isLua(ci)) { /* a Lua function? */ Proto *p = ci_func(ci)->l.p; int pc = currentpc(ci); Instruction i; *name = luaF_getlocalname(p, stackpos + 1, pc); if (*name) /* is a local? */ return "local"; i = luaG_symbexec(p, pc, stackpos); /* try symbolic execution */ lua_assert(pc != -1); switch (GET_OPCODE(i)) { case OP_GETGLOBAL: { int g = GETARG_Bx(i); /* global index */ lua_assert(ttisstring(&p->k[g])); *name = svalue(&p->k[g]); return "global"; } case OP_MOVE: { int a = GETARG_A(i); int b = GETARG_B(i); /* move from `b' to `a' */ if (b < a) return getobjname(ci, b, name); /* get name for `b' */ break; } case OP_GETTABLE: { int k = GETARG_C(i); /* key index */ *name = kname(p, k); return "field"; } case OP_SELF: { int k = GETARG_C(i); /* key index */ *name = kname(p, k); return "method"; } default: break; } } return NULL; /* no useful name found */ }
int luaG_checkcode (const Proto *pt) { return luaG_symbexec(pt, pt->sizecode, NO_REG); }