LCOV - code coverage report
Current view: top level - src - ldebug.c Hit Total Coverage
Test: Lua 5.1.5 Lines: 208 341 61.0 %
Date: 2017-04-16 16:03:13
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*
       2             : ** $Id: ldebug.c,v 2.29.1.6 2008/05/08 16:56:26 roberto Exp $
       3             : ** Debug Interface
       4             : ** See Copyright Notice in lua.h
       5             : */
       6             : 
       7             : 
       8             : #include <stdarg.h>
       9             : #include <stddef.h>
      10             : #include <string.h>
      11             : 
      12             : 
      13             : #define ldebug_c
      14             : #define LUA_CORE
      15             : 
      16             : #include "lua.h"
      17             : 
      18             : #include "lapi.h"
      19             : #include "lcode.h"
      20             : #include "ldebug.h"
      21             : #include "ldo.h"
      22             : #include "lfunc.h"
      23             : #include "lobject.h"
      24             : #include "lopcodes.h"
      25             : #include "lstate.h"
      26             : #include "lstring.h"
      27             : #include "ltable.h"
      28             : #include "ltm.h"
      29             : #include "lvm.h"
      30             : 
      31             : 
      32             : 
      33             : static const char *getfuncname (lua_State *L, CallInfo *ci, const char **name);
      34             : 
      35             : 
      36         356 : static int currentpc (lua_State *L, CallInfo *ci) {
      37         356 :   if (!isLua(ci)) return -1;  /* function is not a Lua function? */
      38         345 :   if (ci == L->ci)
      39         254 :     ci->savedpc = L->savedpc;
      40         345 :   return pcRel(ci->savedpc, ci_func(ci)->l.p);
      41             : }
      42             : 
      43             : 
      44         244 : static int currentline (lua_State *L, CallInfo *ci) {
      45         244 :   int pc = currentpc(L, ci);
      46         244 :   if (pc < 0)
      47          11 :     return -1;  /* only active lua functions have current-line information */
      48             :   else
      49         233 :     return getline(ci_func(ci)->l.p, pc);
      50             : }
      51             : 
      52             : 
      53             : /*
      54             : ** this function can be called asynchronous (e.g. during a signal)
      55             : */
      56           0 : LUA_API int lua_sethook (lua_State *L, lua_Hook func, int mask, int count) {
      57           0 :   if (func == NULL || mask == 0) {  /* turn off hooks? */
      58           0 :     mask = 0;
      59           0 :     func = NULL;
      60             :   }
      61           0 :   L->hook = func;
      62           0 :   L->basehookcount = count;
      63           0 :   resethookcount(L);
      64           0 :   L->hookmask = cast_byte(mask);
      65           0 :   return 1;
      66             : }
      67             : 
      68             : 
      69           0 : LUA_API lua_Hook lua_gethook (lua_State *L) {
      70           0 :   return L->hook;
      71             : }
      72             : 
      73             : 
      74           0 : LUA_API int lua_gethookmask (lua_State *L) {
      75           0 :   return L->hookmask;
      76             : }
      77             : 
      78             : 
      79           0 : LUA_API int lua_gethookcount (lua_State *L) {
      80           0 :   return L->basehookcount;
      81             : }
      82             : 
      83             : 
      84         126 : LUA_API int lua_getstack (lua_State *L, int level, lua_Debug *ar) {
      85             :   int status;
      86             :   CallInfo *ci;
      87             :   lua_lock(L);
      88         233 :   for (ci = L->ci; level > 0 && ci > L->base_ci; ci--) {
      89         107 :     level--;
      90         107 :     if (f_isLua(ci))  /* Lua function? */
      91          13 :       level -= ci->tailcalls;  /* skip lost tail calls */
      92             :   }
      93         126 :   if (level == 0 && ci > L->base_ci) {  /* level found? */
      94         101 :     status = 1;
      95         101 :     ar->i_ci = cast_int(ci - L->base_ci);
      96             :   }
      97          25 :   else if (level < 0) {  /* level is of a lost tail call? */
      98           0 :     status = 1;
      99           0 :     ar->i_ci = 0;
     100             :   }
     101          25 :   else status = 0;  /* no such level */
     102             :   lua_unlock(L);
     103         126 :   return status;
     104             : }
     105             : 
     106             : 
     107         182 : static Proto *getluaproto (CallInfo *ci) {
     108         182 :   return (isLua(ci) ? ci_func(ci)->l.p : NULL);
     109             : }
     110             : 
     111             : 
     112           0 : static const char *findlocal (lua_State *L, CallInfo *ci, int n) {
     113             :   const char *name;
     114           0 :   Proto *fp = getluaproto(ci);
     115           0 :   if (fp && (name = luaF_getlocalname(fp, n, currentpc(L, ci))) != NULL)
     116           0 :     return name;  /* is a local variable in a Lua function */
     117             :   else {
     118           0 :     StkId limit = (ci == L->ci) ? L->top : (ci+1)->func;
     119           0 :     if (limit - ci->base >= n && n > 0)  /* is 'n' inside 'ci' stack? */
     120           0 :       return "(*temporary)";
     121             :     else
     122           0 :       return NULL;
     123             :   }
     124             : }
     125             : 
     126             : 
     127           0 : LUA_API const char *lua_getlocal (lua_State *L, const lua_Debug *ar, int n) {
     128           0 :   CallInfo *ci = L->base_ci + ar->i_ci;
     129           0 :   const char *name = findlocal(L, ci, n);
     130             :   lua_lock(L);
     131           0 :   if (name)
     132           0 :       luaA_pushobject(L, ci->base + (n - 1));
     133             :   lua_unlock(L);
     134           0 :   return name;
     135             : }
     136             : 
     137             : 
     138           0 : LUA_API const char *lua_setlocal (lua_State *L, const lua_Debug *ar, int n) {
     139           0 :   CallInfo *ci = L->base_ci + ar->i_ci;
     140           0 :   const char *name = findlocal(L, ci, n);
     141             :   lua_lock(L);
     142           0 :   if (name)
     143           0 :       setobjs2s(L, ci->base + (n - 1), L->top - 1);
     144           0 :   L->top--;  /* pop value */
     145             :   lua_unlock(L);
     146           0 :   return name;
     147             : }
     148             : 
     149             : 
     150          63 : static void funcinfo (lua_Debug *ar, Closure *cl) {
     151          63 :   if (cl->c.isC) {
     152          11 :     ar->source = "=[C]";
     153          11 :     ar->linedefined = -1;
     154          11 :     ar->lastlinedefined = -1;
     155          11 :     ar->what = "C";
     156             :   }
     157             :   else {
     158          52 :     ar->source = getstr(cl->l.p->source);
     159          52 :     ar->linedefined = cl->l.p->linedefined;
     160          52 :     ar->lastlinedefined = cl->l.p->lastlinedefined;
     161          52 :     ar->what = (ar->linedefined == 0) ? "main" : "Lua";
     162             :   }
     163          63 :   luaO_chunkid(ar->short_src, ar->source, LUA_IDSIZE);
     164          63 : }
     165             : 
     166             : 
     167           0 : static void info_tailcall (lua_Debug *ar) {
     168           0 :   ar->name = ar->namewhat = "";
     169           0 :   ar->what = "tail";
     170           0 :   ar->lastlinedefined = ar->linedefined = ar->currentline = -1;
     171           0 :   ar->source = "=(tail call)";
     172           0 :   luaO_chunkid(ar->short_src, ar->source, LUA_IDSIZE);
     173           0 :   ar->nups = 0;
     174           0 : }
     175             : 
     176             : 
     177           0 : static void collectvalidlines (lua_State *L, Closure *f) {
     178           0 :   if (f == NULL || f->c.isC) {
     179           0 :     setnilvalue(L->top);
     180             :   }
     181             :   else {
     182           0 :     Table *t = luaH_new(L, 0, 0);
     183           0 :     int *lineinfo = f->l.p->lineinfo;
     184             :     int i;
     185           0 :     for (i=0; i<f->l.p->sizelineinfo; i++)
     186           0 :       setbvalue(luaH_setnum(L, t, lineinfo[i]), 1);
     187           0 :     sethvalue(L, L->top, t); 
     188             :   }
     189           0 :   incr_top(L);
     190           0 : }
     191             : 
     192             : 
     193         102 : static int auxgetinfo (lua_State *L, const char *what, lua_Debug *ar,
     194             :                     Closure *f, CallInfo *ci) {
     195         102 :   int status = 1;
     196         102 :   if (f == NULL) {
     197           0 :     info_tailcall(ar);
     198           0 :     return status;
     199             :   }
     200         279 :   for (; *what; what++) {
     201         177 :     switch (*what) {
     202             :       case 'S': {
     203          63 :         funcinfo(ar, f);
     204          63 :         break;
     205             :       }
     206             :       case 'l': {
     207          63 :         ar->currentline = (ci) ? currentline(L, ci) : -1;
     208          63 :         break;
     209             :       }
     210             :       case 'u': {
     211           2 :         ar->nups = f->c.nupvalues;
     212           2 :         break;
     213             :       }
     214             :       case 'n': {
     215          32 :         ar->namewhat = (ci) ? getfuncname(L, ci, &ar->name) : NULL;
     216          32 :         if (ar->namewhat == NULL) {
     217          12 :           ar->namewhat = "";  /* not found */
     218          12 :           ar->name = NULL;
     219             :         }
     220          32 :         break;
     221             :       }
     222             :       case 'L':
     223             :       case 'f':  /* handled by lua_getinfo */
     224          17 :         break;
     225           0 :       default: status = 0;  /* invalid option */
     226             :     }
     227             :   }
     228         102 :   return status;
     229             : }
     230             : 
     231             : 
     232         102 : LUA_API int lua_getinfo (lua_State *L, const char *what, lua_Debug *ar) {
     233             :   int status;
     234         102 :   Closure *f = NULL;
     235         102 :   CallInfo *ci = NULL;
     236             :   lua_lock(L);
     237         102 :   if (*what == '>') {
     238           1 :     StkId func = L->top - 1;
     239             :     luai_apicheck(L, ttisfunction(func));
     240           1 :     what++;  /* skip the '>' */
     241           1 :     f = clvalue(func);
     242           1 :     L->top--;  /* pop function */
     243             :   }
     244         101 :   else if (ar->i_ci != 0) {  /* no tail call? */
     245         101 :     ci = L->base_ci + ar->i_ci;
     246             :     lua_assert(ttisfunction(ci->func));
     247         101 :     f = clvalue(ci->func);
     248             :   }
     249         102 :   status = auxgetinfo(L, what, ar, f, ci);
     250         102 :   if (strchr(what, 'f')) {
     251          17 :     if (f == NULL) setnilvalue(L->top);
     252          17 :     else setclvalue(L, L->top, f);
     253          17 :     incr_top(L);
     254             :   }
     255         102 :   if (strchr(what, 'L'))
     256           0 :     collectvalidlines(L, f);
     257             :   lua_unlock(L);
     258         102 :   return status;
     259             : }
     260             : 
     261             : 
     262             : /*
     263             : ** {======================================================
     264             : ** Symbolic Execution and code checker
     265             : ** =======================================================
     266             : */
     267             : 
     268             : #define check(x)                if (!(x)) return 0;
     269             : 
     270             : #define checkjump(pt,pc)        check(0 <= pc && pc < pt->sizecode)
     271             : 
     272             : #define checkreg(pt,reg)        check((reg) < (pt)->maxstacksize)
     273             : 
     274             : 
     275             : 
     276          92 : static int precheck (const Proto *pt) {
     277          92 :   check(pt->maxstacksize <= MAXSTACK);
     278          92 :   check(pt->numparams+(pt->is_vararg & VARARG_HASARG) <= pt->maxstacksize);
     279          92 :   check(!(pt->is_vararg & VARARG_NEEDSARG) ||
     280             :               (pt->is_vararg & VARARG_HASARG));
     281          92 :   check(pt->sizeupvalues <= pt->nups);
     282          92 :   check(pt->sizelineinfo == pt->sizecode || pt->sizelineinfo == 0);
     283          92 :   check(pt->sizecode > 0 && GET_OPCODE(pt->code[pt->sizecode-1]) == OP_RETURN);
     284          92 :   return 1;
     285             : }
     286             : 
     287             : 
     288             : #define checkopenop(pt,pc)      luaG_checkopenop((pt)->code[(pc)+1])
     289             : 
     290           0 : int luaG_checkopenop (Instruction i) {
     291           0 :   switch (GET_OPCODE(i)) {
     292             :     case OP_CALL:
     293             :     case OP_TAILCALL:
     294             :     case OP_RETURN:
     295             :     case OP_SETLIST: {
     296           0 :       check(GETARG_B(i) == 0);
     297           0 :       return 1;
     298             :     }
     299           0 :     default: return 0;  /* invalid instruction after an open call */
     300             :   }
     301             : }
     302             : 
     303             : 
     304          62 : static int checkArgMode (const Proto *pt, int r, enum OpArgMask mode) {
     305          62 :   switch (mode) {
     306           1 :     case OpArgN: check(r == 0); break;
     307          45 :     case OpArgU: break;
     308           8 :     case OpArgR: checkreg(pt, r); break;
     309             :     case OpArgK:
     310           8 :       check(ISK(r) ? INDEXK(r) < pt->sizek : r < pt->maxstacksize);
     311           8 :       break;
     312             :   }
     313          62 :   return 1;
     314             : }
     315             : 
     316             : 
     317          92 : static Instruction symbexec (const Proto *pt, int lastpc, int reg) {
     318             :   int pc;
     319             :   int last;  /* stores position of last instruction that changed `reg' */
     320          92 :   last = pt->sizecode-1;  /* points to final return (a `neutral' instruction) */
     321          92 :   check(precheck(pt));
     322         265 :   for (pc = 0; pc < lastpc; pc++) {
     323         173 :     Instruction i = pt->code[pc];
     324         173 :     OpCode op = GET_OPCODE(i);
     325         173 :     int a = GETARG_A(i);
     326         173 :     int b = 0;
     327         173 :     int c = 0;
     328         173 :     check(op < NUM_OPCODES);
     329         173 :     checkreg(pt, a);
     330         173 :     switch (getOpMode(op)) {
     331             :       case iABC: {
     332          31 :         b = GETARG_B(i);
     333          31 :         c = GETARG_C(i);
     334          31 :         check(checkArgMode(pt, b, getBMode(op)));
     335          31 :         check(checkArgMode(pt, c, getCMode(op)));
     336          31 :         break;
     337             :       }
     338             :       case iABx: {
     339         142 :         b = GETARG_Bx(i);
     340         142 :         if (getBMode(op) == OpArgK) check(b < pt->sizek);
     341         142 :         break;
     342             :       }
     343             :       case iAsBx: {
     344           0 :         b = GETARG_sBx(i);
     345           0 :         if (getBMode(op) == OpArgR) {
     346           0 :           int dest = pc+1+b;
     347           0 :           check(0 <= dest && dest < pt->sizecode);
     348           0 :           if (dest > 0) {
     349             :             int j;
     350             :             /* check that it does not jump to a setlist count; this
     351             :                is tricky, because the count from a previous setlist may
     352             :                have the same value of an invalid setlist; so, we must
     353             :                go all the way back to the first of them (if any) */
     354           0 :             for (j = 0; j < dest; j++) {
     355           0 :               Instruction d = pt->code[dest-1-j];
     356           0 :               if (!(GET_OPCODE(d) == OP_SETLIST && GETARG_C(d) == 0)) break;
     357             :             }
     358             :             /* if 'j' is even, previous value is not a setlist (even if
     359             :                it looks like one) */
     360           0 :             check((j&1) == 0);
     361             :           }
     362             :         }
     363           0 :         break;
     364             :       }
     365             :     }
     366         173 :     if (testAMode(op)) {
     367         152 :       if (a == reg) last = pc;  /* change register `a' */
     368             :     }
     369         173 :     if (testTMode(op)) {
     370           0 :       check(pc+2 < pt->sizecode);  /* check skip */
     371           0 :       check(GET_OPCODE(pt->code[pc+1]) == OP_JMP);
     372             :     }
     373         173 :     switch (op) {
     374             :       case OP_LOADBOOL: {
     375           8 :         if (c == 1) {  /* does it jump? */
     376           0 :           check(pc+2 < pt->sizecode);  /* check its jump */
     377           0 :           check(GET_OPCODE(pt->code[pc+1]) != OP_SETLIST ||
     378             :                 GETARG_C(pt->code[pc+1]) != 0);
     379             :         }
     380           8 :         break;
     381             :       }
     382             :       case OP_LOADNIL: {
     383           0 :         if (a <= reg && reg <= b)
     384           0 :           last = pc;  /* set registers from `a' to `b' */
     385           0 :         break;
     386             :       }
     387             :       case OP_GETUPVAL:
     388             :       case OP_SETUPVAL: {
     389           0 :         check(b < pt->nups);
     390           0 :         break;
     391             :       }
     392             :       case OP_GETGLOBAL:
     393             :       case OP_SETGLOBAL: {
     394         106 :         check(ttisstring(&pt->k[b]));
     395         106 :         break;
     396             :       }
     397             :       case OP_SELF: {
     398           2 :         checkreg(pt, a+1);
     399           2 :         if (reg == a+1) last = pc;
     400           2 :         break;
     401             :       }
     402             :       case OP_CONCAT: {
     403           0 :         check(b < c);  /* at least two operands */
     404           0 :         break;
     405             :       }
     406             :       case OP_TFORLOOP: {
     407           0 :         check(c >= 1);  /* at least one result (control variable) */
     408           0 :         checkreg(pt, a+2+c);  /* space for results */
     409           0 :         if (reg >= a+2) last = pc;  /* affect all regs above its base */
     410           0 :         break;
     411             :       }
     412             :       case OP_FORLOOP:
     413             :       case OP_FORPREP:
     414           0 :         checkreg(pt, a+3);
     415             :         /* go through */
     416             :       case OP_JMP: {
     417           0 :         int dest = pc+1+b;
     418             :         /* not full check and jump is forward and do not skip `lastpc'? */
     419           0 :         if (reg != NO_REG && pc < dest && dest <= lastpc)
     420           0 :           pc += b;  /* do the jump */
     421           0 :         break;
     422             :       }
     423             :       case OP_CALL:
     424             :       case OP_TAILCALL: {
     425           1 :         if (b != 0) {
     426           1 :           checkreg(pt, a+b-1);
     427             :         }
     428           1 :         c--;  /* c = num. returns */
     429           1 :         if (c == LUA_MULTRET) {
     430           0 :           check(checkopenop(pt, pc));
     431             :         }
     432           1 :         else if (c != 0)
     433           0 :           checkreg(pt, a+c-1);
     434           1 :         if (reg >= a) last = pc;  /* affect all registers above base */
     435           1 :         break;
     436             :       }
     437             :       case OP_RETURN: {
     438           1 :         b--;  /* b = num. returns */
     439           1 :         if (b > 0) checkreg(pt, a+b-1);
     440           1 :         break;
     441             :       }
     442             :       case OP_SETLIST: {
     443           0 :         if (b > 0) checkreg(pt, a + b);
     444           0 :         if (c == 0) {
     445           0 :           pc++;
     446           0 :           check(pc < pt->sizecode - 1);
     447             :         }
     448           0 :         break;
     449             :       }
     450             :       case OP_CLOSURE: {
     451             :         int nup, j;
     452           0 :         check(b < pt->sizep);
     453           0 :         nup = pt->p[b]->nups;
     454           0 :         check(pc + nup < pt->sizecode);
     455           0 :         for (j = 1; j <= nup; j++) {
     456           0 :           OpCode op1 = GET_OPCODE(pt->code[pc + j]);
     457           0 :           check(op1 == OP_GETUPVAL || op1 == OP_MOVE);
     458             :         }
     459           0 :         if (reg != NO_REG)  /* tracing? */
     460           0 :           pc += nup;  /* do not 'execute' these pseudo-instructions */
     461           0 :         break;
     462             :       }
     463             :       case OP_VARARG: {
     464           0 :         check((pt->is_vararg & VARARG_ISVARARG) &&
     465             :              !(pt->is_vararg & VARARG_NEEDSARG));
     466           0 :         b--;
     467           0 :         if (b == LUA_MULTRET) check(checkopenop(pt, pc));
     468           0 :         checkreg(pt, a+b-1);
     469           0 :         break;
     470             :       }
     471          55 :       default: break;
     472             :     }
     473             :   }
     474          92 :   return pt->code[last];
     475             : }
     476             : 
     477             : #undef check
     478             : #undef checkjump
     479             : #undef checkreg
     480             : 
     481             : /* }====================================================== */
     482             : 
     483             : 
     484           1 : int luaG_checkcode (const Proto *pt) {
     485           1 :   return (symbexec(pt, pt->sizecode, NO_REG) != 0);
     486             : }
     487             : 
     488             : 
     489           8 : static const char *kname (Proto *p, int c) {
     490           8 :   if (ISK(c) && ttisstring(&p->k[INDEXK(c)]))
     491           8 :     return svalue(&p->k[INDEXK(c)]);
     492             :   else
     493           0 :     return "?";
     494             : }
     495             : 
     496             : 
     497          93 : static const char *getobjname (lua_State *L, CallInfo *ci, int stackpos,
     498             :                                const char **name) {
     499          93 :   if (isLua(ci)) {  /* a Lua function? */
     500          92 :     Proto *p = ci_func(ci)->l.p;
     501          92 :     int pc = currentpc(L, ci);
     502             :     Instruction i;
     503          92 :     *name = luaF_getlocalname(p, stackpos+1, pc);
     504          92 :     if (*name)  /* is a local? */
     505           1 :       return "local";
     506          91 :     i = symbexec(p, pc, stackpos);  /* try symbolic execution */
     507             :     lua_assert(pc != -1);
     508          91 :     switch (GET_OPCODE(i)) {
     509             :       case OP_GETGLOBAL: {
     510          63 :         int g = GETARG_Bx(i);  /* global index */
     511             :         lua_assert(ttisstring(&p->k[g]));
     512          63 :         *name = svalue(&p->k[g]);
     513          63 :         return "global";
     514             :       }
     515             :       case OP_MOVE: {
     516           0 :         int a = GETARG_A(i);
     517           0 :         int b = GETARG_B(i);  /* move from `b' to `a' */
     518           0 :         if (b < a)
     519           0 :           return getobjname(L, ci, b, name);  /* get name for `b' */
     520           0 :         break;
     521             :       }
     522             :       case OP_GETTABLE: {
     523           6 :         int k = GETARG_C(i);  /* key index */
     524           6 :         *name = kname(p, k);
     525           6 :         return "field";
     526             :       }
     527             :       case OP_GETUPVAL: {
     528           0 :         int u = GETARG_B(i);  /* upvalue index */
     529           0 :         *name = p->upvalues ? getstr(p->upvalues[u]) : "?";
     530           0 :         return "upvalue";
     531             :       }
     532             :       case OP_SELF: {
     533           2 :         int k = GETARG_C(i);  /* key index */
     534           2 :         *name = kname(p, k);
     535           2 :         return "method";
     536             :       }
     537          20 :       default: break;
     538             :     }
     539             :   }
     540          21 :   return NULL;  /* no useful name found */
     541             : }
     542             : 
     543             : 
     544          31 : static const char *getfuncname (lua_State *L, CallInfo *ci, const char **name) {
     545             :   Instruction i;
     546          31 :   if ((isLua(ci) && ci->tailcalls > 0) || !isLua(ci - 1))
     547          11 :     return NULL;  /* calling function is not Lua (or is unknown) */
     548          20 :   ci--;  /* calling function */
     549          20 :   i = ci_func(ci)->l.p->code[currentpc(L, ci)];
     550          20 :   if (GET_OPCODE(i) == OP_CALL || GET_OPCODE(i) == OP_TAILCALL ||
     551           0 :       GET_OPCODE(i) == OP_TFORLOOP)
     552          20 :     return getobjname(L, ci, GETARG_A(i), name);
     553             :   else
     554           0 :     return NULL;  /* no useful name can be found */
     555             : }
     556             : 
     557             : 
     558             : /* only ANSI way to check whether a pointer points to an array */
     559         108 : static int isinstack (CallInfo *ci, const TValue *o) {
     560             :   StkId p;
     561         181 :   for (p = ci->base; p < ci->top; p++)
     562         146 :     if (o == p) return 1;
     563          35 :   return 0;
     564             : }
     565             : 
     566             : 
     567         108 : void luaG_typeerror (lua_State *L, const TValue *o, const char *op) {
     568         108 :   const char *name = NULL;
     569         108 :   const char *t = luaT_typenames[ttype(o)];
     570         216 :   const char *kind = (isinstack(L->ci, o)) ?
     571         108 :                          getobjname(L, L->ci, cast_int(o - L->base), &name) :
     572             :                          NULL;
     573         108 :   if (kind)
     574          52 :     luaG_runerror(L, "attempt to %s %s " LUA_QS " (a %s value)",
     575             :                 op, kind, name, t);
     576             :   else
     577          56 :     luaG_runerror(L, "attempt to %s a %s value", op, t);
     578           0 : }
     579             : 
     580             : 
     581           9 : void luaG_concaterror (lua_State *L, StkId p1, StkId p2) {
     582           9 :   if (ttisstring(p1) || ttisnumber(p1)) p1 = p2;
     583             :   lua_assert(!ttisstring(p1) && !ttisnumber(p1));
     584           9 :   luaG_typeerror(L, p1, "concatenate");
     585           0 : }
     586             : 
     587             : 
     588          75 : void luaG_aritherror (lua_State *L, const TValue *p1, const TValue *p2) {
     589             :   TValue temp;
     590          75 :   if (luaV_tonumber(p1, &temp) == NULL)
     591          51 :     p2 = p1;  /* first operand is wrong */
     592          75 :   luaG_typeerror(L, p2, "perform arithmetic on");
     593           0 : }
     594             : 
     595             : 
     596          74 : int luaG_ordererror (lua_State *L, const TValue *p1, const TValue *p2) {
     597          74 :   const char *t1 = luaT_typenames[ttype(p1)];
     598          74 :   const char *t2 = luaT_typenames[ttype(p2)];
     599          74 :   if (t1[2] == t2[2])
     600          28 :     luaG_runerror(L, "attempt to compare two %s values", t1);
     601             :   else
     602          46 :     luaG_runerror(L, "attempt to compare %s with %s", t1, t2);
     603           0 :   return 0;
     604             : }
     605             : 
     606             : 
     607         184 : static void addinfo (lua_State *L, const char *msg) {
     608         184 :   CallInfo *ci = L->ci;
     609         184 :   if (isLua(ci)) {  /* is Lua code? */
     610             :     char buff[LUA_IDSIZE];  /* add file:line information */
     611         182 :     int line = currentline(L, ci);
     612         182 :     luaO_chunkid(buff, getstr(getluaproto(ci)->source), LUA_IDSIZE);
     613         182 :     luaO_pushfstring(L, "%s:%d: %s", buff, line, msg);
     614             :   }
     615         184 : }
     616             : 
     617             : 
     618         241 : void luaG_errormsg (lua_State *L) {
     619         241 :   if (L->errfunc != 0) {  /* is there an error handling function? */
     620           3 :     StkId errfunc = restorestack(L, L->errfunc);
     621           3 :     if (!ttisfunction(errfunc)) luaD_throw(L, LUA_ERRERR);
     622           2 :     setobjs2s(L, L->top, L->top - 1);  /* move argument */
     623           2 :     setobjs2s(L, L->top - 1, errfunc);  /* push function */
     624           2 :     incr_top(L);
     625           2 :     luaD_call(L, L->top - 2, 1);  /* call it */
     626             :   }
     627         240 :   luaD_throw(L, LUA_ERRRUN);
     628           0 : }
     629             : 
     630             : 
     631         184 : void luaG_runerror (lua_State *L, const char *fmt, ...) {
     632             :   va_list argp;
     633         184 :   va_start(argp, fmt);
     634         184 :   addinfo(L, luaO_pushvfstring(L, fmt, argp));
     635         184 :   va_end(argp);
     636         184 :   luaG_errormsg(L);
     637           0 : }
     638             : 

Generated by: LCOV version 1.13