/* Typecheck error for operands. */ LJ_NOINLINE void lj_err_optype(lua_State *L, cTValue *o, ErrMsg opm) { const char *tname = typename(o); const char *opname = err2msg(opm); if (curr_funcisL(L)) { GCproto *pt = curr_proto(L); const BCIns *pc = cframe_Lpc(L) - 1; const char *oname = NULL; const char *kind = lj_debug_slotname(pt, pc, (BCReg)(o-L->base), &oname); if (kind) err_msgv(L, LJ_ERR_BADOPRT, opname, kind, oname, tname); } err_msgv(L, LJ_ERR_BADOPRV, opname, tname); }
/* Instruction dispatch callback for instr/line hooks or when recording. */ void lj_dispatch_ins(lua_State *L, const BCIns *pc, uint32_t nres) { GCfunc *fn = curr_func(L); GCproto *pt = funcproto(fn); BCReg slots = cur_topslot(pt, pc, nres); global_State *g = G(L); const BCIns *oldpc = cframe_Lpc(L); cframe_Lpc(L) = pc; L->top = L->base + slots; /* Fix top. */ #if LJ_HASJIT { jit_State *J = G2J(g); if (J->state != LJ_TRACE_IDLE) { J->L = L; J->pc = pc-1; J->fn = fn; J->pt = pt; lj_trace_ins(J); } } #endif if ((g->hookmask & LUA_MASKCOUNT) && g->hookcount == 0) { g->hookcount = g->hookcstart; callhook(L, LUA_HOOKCOUNT, -1); } if ((g->hookmask & LUA_MASKLINE) && pt->lineinfo) { BCPos npc = (BCPos)(pc - pt->bc)-1; BCPos opc = (BCPos)(oldpc - pt->bc)-1; BCLine line = pt->lineinfo[npc]; if (npc == 0 || pc <= oldpc || opc >= pt->sizebc || line != pt->lineinfo[opc]) { L->top = L->base + slots; /* Fix top again after instruction hook. */ callhook(L, LUA_HOOKLINE, line); } } }
/* Typecheck error for __call. */ LJ_NOINLINE void lj_err_optype_call(lua_State *L, TValue *o) { /* Gross hack if lua_[p]call or pcall/xpcall fail for a non-callable object: ** L->base still points to the caller. So add a dummy frame with L instead ** of a function. See lua_getstack(). */ const BCIns *pc = cframe_Lpc(L); if (((ptrdiff_t)pc & FRAME_TYPE) != FRAME_LUA) { const char *tname = typename(o); setframe_pc(o, pc); setframe_gc(o, obj2gco(L)); L->top = L->base = o+1; err_msgv(L, LJ_ERR_BADCALL, tname); } lj_err_optype(L, o, LJ_ERR_OPCALL); }