aboutsummaryrefslogtreecommitdiff
path: root/src/lj_err.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/lj_err.c')
-rw-r--r--src/lj_err.c211
1 files changed, 131 insertions, 80 deletions
diff --git a/src/lj_err.c b/src/lj_err.c
index ad3394df..656631a9 100644
--- a/src/lj_err.c
+++ b/src/lj_err.c
@@ -16,6 +16,7 @@
16#include "lj_ff.h" 16#include "lj_ff.h"
17#include "lj_trace.h" 17#include "lj_trace.h"
18#include "lj_vm.h" 18#include "lj_vm.h"
19#include "lj_strfmt.h"
19 20
20/* 21/*
21** LuaJIT can either use internal or external frame unwinding: 22** LuaJIT can either use internal or external frame unwinding:
@@ -45,7 +46,8 @@
45** the wrapper function feature. Lua errors thrown through C++ frames 46** the wrapper function feature. Lua errors thrown through C++ frames
46** cannot be caught by C++ code and C++ destructors are not run. 47** cannot be caught by C++ code and C++ destructors are not run.
47** 48**
48** EXT is the default on x64 systems, INT is the default on all other systems. 49** EXT is the default on x64 systems and on Windows, INT is the default on all
50** other systems.
49** 51**
50** EXT can be manually enabled on POSIX systems using GCC and DWARF2 stack 52** EXT can be manually enabled on POSIX systems using GCC and DWARF2 stack
51** unwinding with -DLUAJIT_UNWIND_EXTERNAL. *All* C code must be compiled 53** unwinding with -DLUAJIT_UNWIND_EXTERNAL. *All* C code must be compiled
@@ -54,15 +56,14 @@
54** and all C libraries that have callbacks which may be used to call back 56** and all C libraries that have callbacks which may be used to call back
55** into Lua. C++ code must *not* be compiled with -fno-exceptions. 57** into Lua. C++ code must *not* be compiled with -fno-exceptions.
56** 58**
57** EXT cannot be enabled on WIN32 since system exceptions use code-driven SEH.
58** EXT is mandatory on WIN64 since the calling convention has an abundance 59** EXT is mandatory on WIN64 since the calling convention has an abundance
59** of callee-saved registers (rbx, rbp, rsi, rdi, r12-r15, xmm6-xmm15). 60** of callee-saved registers (rbx, rbp, rsi, rdi, r12-r15, xmm6-xmm15).
60** The POSIX/x64 interpreter only saves r12/r13 for INT (e.g. PS4). 61** The POSIX/x64 interpreter only saves r12/r13 for INT (e.g. PS4).
61*/ 62*/
62 63
63#if defined(__GNUC__) && (LJ_TARGET_X64 || defined(LUAJIT_UNWIND_EXTERNAL)) && !LJ_NO_UNWIND 64#if (defined(__GNUC__) || defined(__clang__)) && (LJ_TARGET_X64 || defined(LUAJIT_UNWIND_EXTERNAL)) && !LJ_NO_UNWIND
64#define LJ_UNWIND_EXT 1 65#define LJ_UNWIND_EXT 1
65#elif LJ_TARGET_X64 && LJ_TARGET_WINDOWS 66#elif LJ_TARGET_WINDOWS
66#define LJ_UNWIND_EXT 1 67#define LJ_UNWIND_EXT 1
67#endif 68#endif
68 69
@@ -98,14 +99,14 @@ static void *err_unwind(lua_State *L, void *stopcf, int errcode)
98 TValue *top = restorestack(L, -nres); 99 TValue *top = restorestack(L, -nres);
99 if (frame < top) { /* Frame reached? */ 100 if (frame < top) { /* Frame reached? */
100 if (errcode) { 101 if (errcode) {
101 L->cframe = cframe_prev(cf);
102 L->base = frame+1; 102 L->base = frame+1;
103 L->cframe = cframe_prev(cf);
103 unwindstack(L, top); 104 unwindstack(L, top);
104 } 105 }
105 return cf; 106 return cf;
106 } 107 }
107 } 108 }
108 if (frame <= tvref(L->stack)) 109 if (frame <= tvref(L->stack)+LJ_FR2)
109 break; 110 break;
110 switch (frame_typep(frame)) { 111 switch (frame_typep(frame)) {
111 case FRAME_LUA: /* Lua frame. */ 112 case FRAME_LUA: /* Lua frame. */
@@ -113,14 +114,12 @@ static void *err_unwind(lua_State *L, void *stopcf, int errcode)
113 frame = frame_prevl(frame); 114 frame = frame_prevl(frame);
114 break; 115 break;
115 case FRAME_C: /* C frame. */ 116 case FRAME_C: /* C frame. */
116#if LJ_HASFFI
117 unwind_c: 117 unwind_c:
118#endif
119#if LJ_UNWIND_EXT 118#if LJ_UNWIND_EXT
120 if (errcode) { 119 if (errcode) {
121 L->cframe = cframe_prev(cf);
122 L->base = frame_prevd(frame) + 1; 120 L->base = frame_prevd(frame) + 1;
123 unwindstack(L, frame); 121 L->cframe = cframe_prev(cf);
122 unwindstack(L, frame - LJ_FR2);
124 } else if (cf != stopcf) { 123 } else if (cf != stopcf) {
125 cf = cframe_prev(cf); 124 cf = cframe_prev(cf);
126 frame = frame_prevd(frame); 125 frame = frame_prevd(frame);
@@ -143,16 +142,14 @@ static void *err_unwind(lua_State *L, void *stopcf, int errcode)
143 return cf; 142 return cf;
144 } 143 }
145 if (errcode) { 144 if (errcode) {
146 L->cframe = cframe_prev(cf);
147 L->base = frame_prevd(frame) + 1; 145 L->base = frame_prevd(frame) + 1;
148 unwindstack(L, frame); 146 L->cframe = cframe_prev(cf);
147 unwindstack(L, frame - LJ_FR2);
149 } 148 }
150 return cf; 149 return cf;
151 case FRAME_CONT: /* Continuation frame. */ 150 case FRAME_CONT: /* Continuation frame. */
152#if LJ_HASFFI 151 if (frame_iscont_fficb(frame))
153 if ((frame-1)->u32.lo == LJ_CONT_FFI_CALLBACK)
154 goto unwind_c; 152 goto unwind_c;
155#endif
156 /* fallthrough */ 153 /* fallthrough */
157 case FRAME_VARG: /* Vararg frame. */ 154 case FRAME_VARG: /* Vararg frame. */
158 frame = frame_prevd(frame); 155 frame = frame_prevd(frame);
@@ -166,8 +163,8 @@ static void *err_unwind(lua_State *L, void *stopcf, int errcode)
166 } 163 }
167 if (frame_typep(frame) == FRAME_PCALL) 164 if (frame_typep(frame) == FRAME_PCALL)
168 hook_leave(G(L)); 165 hook_leave(G(L));
169 L->cframe = cf;
170 L->base = frame_prevd(frame) + 1; 166 L->base = frame_prevd(frame) + 1;
167 L->cframe = cf;
171 unwindstack(L, L->base); 168 unwindstack(L, L->base);
172 } 169 }
173 return (void *)((intptr_t)cf | CFRAME_UNWIND_FF); 170 return (void *)((intptr_t)cf | CFRAME_UNWIND_FF);
@@ -175,8 +172,8 @@ static void *err_unwind(lua_State *L, void *stopcf, int errcode)
175 } 172 }
176 /* No C frame. */ 173 /* No C frame. */
177 if (errcode) { 174 if (errcode) {
175 L->base = tvref(L->stack)+1+LJ_FR2;
178 L->cframe = NULL; 176 L->cframe = NULL;
179 L->base = tvref(L->stack)+1;
180 unwindstack(L, L->base); 177 unwindstack(L, L->base);
181 if (G(L)->panic) 178 if (G(L)->panic)
182 G(L)->panic(L); 179 G(L)->panic(L);
@@ -187,20 +184,13 @@ static void *err_unwind(lua_State *L, void *stopcf, int errcode)
187 184
188/* -- External frame unwinding -------------------------------------------- */ 185/* -- External frame unwinding -------------------------------------------- */
189 186
190#if defined(__GNUC__) && !LJ_NO_UNWIND && !LJ_ABI_WIN 187#if (defined(__GNUC__) || defined(__clang__)) && !LJ_NO_UNWIND && !LJ_ABI_WIN
191 188
192/* 189/*
193** We have to use our own definitions instead of the mandatory (!) unwind.h, 190** We have to use our own definitions instead of the mandatory (!) unwind.h,
194** since various OS, distros and compilers mess up the header installation. 191** since various OS, distros and compilers mess up the header installation.
195*/ 192*/
196 193
197typedef struct _Unwind_Exception
198{
199 uint64_t exclass;
200 void (*excleanup)(int, struct _Unwind_Exception *);
201 uintptr_t p1, p2;
202} __attribute__((__aligned__)) _Unwind_Exception;
203
204typedef struct _Unwind_Context _Unwind_Context; 194typedef struct _Unwind_Context _Unwind_Context;
205 195
206#define _URC_OK 0 196#define _URC_OK 0
@@ -210,8 +200,20 @@ typedef struct _Unwind_Context _Unwind_Context;
210#define _URC_CONTINUE_UNWIND 8 200#define _URC_CONTINUE_UNWIND 8
211#define _URC_FAILURE 9 201#define _URC_FAILURE 9
212 202
203#define LJ_UEXCLASS 0x4c55414a49543200ULL /* LUAJIT2\0 */
204#define LJ_UEXCLASS_MAKE(c) (LJ_UEXCLASS | (uint64_t)(c))
205#define LJ_UEXCLASS_CHECK(cl) (((cl) ^ LJ_UEXCLASS) <= 0xff)
206#define LJ_UEXCLASS_ERRCODE(cl) ((int)((cl) & 0xff))
207
213#if !LJ_TARGET_ARM 208#if !LJ_TARGET_ARM
214 209
210typedef struct _Unwind_Exception
211{
212 uint64_t exclass;
213 void (*excleanup)(int, struct _Unwind_Exception *);
214 uintptr_t p1, p2;
215} __attribute__((__aligned__)) _Unwind_Exception;
216
215extern uintptr_t _Unwind_GetCFA(_Unwind_Context *); 217extern uintptr_t _Unwind_GetCFA(_Unwind_Context *);
216extern void _Unwind_SetGR(_Unwind_Context *, int, uintptr_t); 218extern void _Unwind_SetGR(_Unwind_Context *, int, uintptr_t);
217extern void _Unwind_SetIP(_Unwind_Context *, uintptr_t); 219extern void _Unwind_SetIP(_Unwind_Context *, uintptr_t);
@@ -223,11 +225,6 @@ extern int _Unwind_RaiseException(_Unwind_Exception *);
223#define _UA_HANDLER_FRAME 4 225#define _UA_HANDLER_FRAME 4
224#define _UA_FORCE_UNWIND 8 226#define _UA_FORCE_UNWIND 8
225 227
226#define LJ_UEXCLASS 0x4c55414a49543200ULL /* LUAJIT2\0 */
227#define LJ_UEXCLASS_MAKE(c) (LJ_UEXCLASS | (uint64_t)(c))
228#define LJ_UEXCLASS_CHECK(cl) (((cl) ^ LJ_UEXCLASS) <= 0xff)
229#define LJ_UEXCLASS_ERRCODE(cl) ((int)((cl) & 0xff))
230
231/* DWARF2 personality handler referenced from interpreter .eh_frame. */ 228/* DWARF2 personality handler referenced from interpreter .eh_frame. */
232LJ_FUNCA int lj_err_unwind_dwarf(int version, int actions, 229LJ_FUNCA int lj_err_unwind_dwarf(int version, int actions,
233 uint64_t uexclass, _Unwind_Exception *uex, _Unwind_Context *ctx) 230 uint64_t uexclass, _Unwind_Exception *uex, _Unwind_Context *ctx)
@@ -301,10 +298,22 @@ static void err_raise_ext(int errcode)
301} 298}
302#endif 299#endif
303 300
304#else 301#else /* LJ_TARGET_ARM */
305 302
306extern void _Unwind_DeleteException(void *); 303#define _US_VIRTUAL_UNWIND_FRAME 0
307extern int __gnu_unwind_frame (void *, _Unwind_Context *); 304#define _US_UNWIND_FRAME_STARTING 1
305#define _US_ACTION_MASK 3
306#define _US_FORCE_UNWIND 8
307
308typedef struct _Unwind_Control_Block _Unwind_Control_Block;
309
310struct _Unwind_Control_Block {
311 uint64_t exclass;
312 uint32_t misc[20];
313};
314
315extern int _Unwind_RaiseException(_Unwind_Control_Block *);
316extern int __gnu_unwind_frame(_Unwind_Control_Block *, _Unwind_Context *);
308extern int _Unwind_VRS_Set(_Unwind_Context *, int, uint32_t, int, void *); 317extern int _Unwind_VRS_Set(_Unwind_Context *, int, uint32_t, int, void *);
309extern int _Unwind_VRS_Get(_Unwind_Context *, int, uint32_t, int, void *); 318extern int _Unwind_VRS_Get(_Unwind_Context *, int, uint32_t, int, void *);
310 319
@@ -320,35 +329,58 @@ static inline void _Unwind_SetGR(_Unwind_Context *ctx, int r, uint32_t v)
320 _Unwind_VRS_Set(ctx, 0, r, 0, &v); 329 _Unwind_VRS_Set(ctx, 0, r, 0, &v);
321} 330}
322 331
323#define _US_VIRTUAL_UNWIND_FRAME 0 332extern void lj_vm_unwind_ext(void);
324#define _US_UNWIND_FRAME_STARTING 1
325#define _US_ACTION_MASK 3
326#define _US_FORCE_UNWIND 8
327 333
328/* ARM unwinder personality handler referenced from interpreter .ARM.extab. */ 334/* ARM unwinder personality handler referenced from interpreter .ARM.extab. */
329LJ_FUNCA int lj_err_unwind_arm(int state, void *ucb, _Unwind_Context *ctx) 335LJ_FUNCA int lj_err_unwind_arm(int state, _Unwind_Control_Block *ucb,
336 _Unwind_Context *ctx)
330{ 337{
331 void *cf = (void *)_Unwind_GetGR(ctx, 13); 338 void *cf = (void *)_Unwind_GetGR(ctx, 13);
332 lua_State *L = cframe_L(cf); 339 lua_State *L = cframe_L(cf);
333 if ((state & _US_ACTION_MASK) == _US_VIRTUAL_UNWIND_FRAME) { 340 int errcode;
334 setstrV(L, L->top++, lj_err_str(L, LJ_ERR_ERRCPP)); 341
342 switch ((state & _US_ACTION_MASK)) {
343 case _US_VIRTUAL_UNWIND_FRAME:
344 if ((state & _US_FORCE_UNWIND)) break;
335 return _URC_HANDLER_FOUND; 345 return _URC_HANDLER_FOUND;
336 } 346 case _US_UNWIND_FRAME_STARTING:
337 if ((state&(_US_ACTION_MASK|_US_FORCE_UNWIND)) == _US_UNWIND_FRAME_STARTING) { 347 if (LJ_UEXCLASS_CHECK(ucb->exclass)) {
338 _Unwind_DeleteException(ucb); 348 errcode = LJ_UEXCLASS_ERRCODE(ucb->exclass);
339 _Unwind_SetGR(ctx, 15, (uint32_t)(void *)lj_err_throw); 349 } else {
340 _Unwind_SetGR(ctx, 0, (uint32_t)L); 350 errcode = LUA_ERRRUN;
341 _Unwind_SetGR(ctx, 1, (uint32_t)LUA_ERRRUN); 351 setstrV(L, L->top++, lj_err_str(L, LJ_ERR_ERRCPP));
352 }
353 cf = err_unwind(L, cf, errcode);
354 if ((state & _US_FORCE_UNWIND) || cf == NULL) break;
355 _Unwind_SetGR(ctx, 15, (uint32_t)lj_vm_unwind_ext);
356 _Unwind_SetGR(ctx, 0, (uint32_t)ucb);
357 _Unwind_SetGR(ctx, 1, (uint32_t)errcode);
358 _Unwind_SetGR(ctx, 2, cframe_unwind_ff(cf) ?
359 (uint32_t)lj_vm_unwind_ff_eh :
360 (uint32_t)lj_vm_unwind_c_eh);
342 return _URC_INSTALL_CONTEXT; 361 return _URC_INSTALL_CONTEXT;
362 default:
363 return _URC_FAILURE;
343 } 364 }
344 if (__gnu_unwind_frame(ucb, ctx) != _URC_OK) 365 if (__gnu_unwind_frame(ucb, ctx) != _URC_OK)
345 return _URC_FAILURE; 366 return _URC_FAILURE;
346 return _URC_CONTINUE_UNWIND; 367 return _URC_CONTINUE_UNWIND;
347} 368}
348 369
370#if LJ_UNWIND_EXT
371static __thread _Unwind_Control_Block static_uex;
372
373static void err_raise_ext(int errcode)
374{
375 memset(&static_uex, 0, sizeof(static_uex));
376 static_uex.exclass = LJ_UEXCLASS_MAKE(errcode);
377 _Unwind_RaiseException(&static_uex);
378}
349#endif 379#endif
350 380
351#elif LJ_TARGET_X64 && LJ_ABI_WIN 381#endif /* LJ_TARGET_ARM */
382
383#elif LJ_ABI_WIN
352 384
353/* 385/*
354** Someone in Redmond owes me several days of my life. A lot of this is 386** Someone in Redmond owes me several days of my life. A lot of this is
@@ -366,6 +398,7 @@ LJ_FUNCA int lj_err_unwind_arm(int state, void *ucb, _Unwind_Context *ctx)
366#define WIN32_LEAN_AND_MEAN 398#define WIN32_LEAN_AND_MEAN
367#include <windows.h> 399#include <windows.h>
368 400
401#if LJ_TARGET_X64
369/* Taken from: http://www.nynaeve.net/?p=99 */ 402/* Taken from: http://www.nynaeve.net/?p=99 */
370typedef struct UndocumentedDispatcherContext { 403typedef struct UndocumentedDispatcherContext {
371 ULONG64 ControlPc; 404 ULONG64 ControlPc;
@@ -380,11 +413,14 @@ typedef struct UndocumentedDispatcherContext {
380 ULONG ScopeIndex; 413 ULONG ScopeIndex;
381 ULONG Fill0; 414 ULONG Fill0;
382} UndocumentedDispatcherContext; 415} UndocumentedDispatcherContext;
416#else
417typedef void *UndocumentedDispatcherContext;
418#endif
383 419
384/* Another wild guess. */ 420/* Another wild guess. */
385extern void __DestructExceptionObject(EXCEPTION_RECORD *rec, int nothrow); 421extern void __DestructExceptionObject(EXCEPTION_RECORD *rec, int nothrow);
386 422
387#ifdef MINGW_SDK_INIT 423#if LJ_TARGET_X64 && defined(MINGW_SDK_INIT)
388/* Workaround for broken MinGW64 declaration. */ 424/* Workaround for broken MinGW64 declaration. */
389VOID RtlUnwindEx_FIXED(PVOID,PVOID,PVOID,PVOID,PVOID,PVOID) asm("RtlUnwindEx"); 425VOID RtlUnwindEx_FIXED(PVOID,PVOID,PVOID,PVOID,PVOID,PVOID) asm("RtlUnwindEx");
390#define RtlUnwindEx RtlUnwindEx_FIXED 426#define RtlUnwindEx RtlUnwindEx_FIXED
@@ -398,10 +434,15 @@ VOID RtlUnwindEx_FIXED(PVOID,PVOID,PVOID,PVOID,PVOID,PVOID) asm("RtlUnwindEx");
398#define LJ_EXCODE_CHECK(cl) (((cl) ^ LJ_EXCODE) <= 0xff) 434#define LJ_EXCODE_CHECK(cl) (((cl) ^ LJ_EXCODE) <= 0xff)
399#define LJ_EXCODE_ERRCODE(cl) ((int)((cl) & 0xff)) 435#define LJ_EXCODE_ERRCODE(cl) ((int)((cl) & 0xff))
400 436
401/* Win64 exception handler for interpreter frame. */ 437/* Windows exception handler for interpreter frame. */
402LJ_FUNCA EXCEPTION_DISPOSITION lj_err_unwind_win64(EXCEPTION_RECORD *rec, 438LJ_FUNCA int lj_err_unwind_win(EXCEPTION_RECORD *rec,
403 void *cf, CONTEXT *ctx, UndocumentedDispatcherContext *dispatch) 439 void *f, CONTEXT *ctx, UndocumentedDispatcherContext *dispatch)
404{ 440{
441#if LJ_TARGET_X64
442 void *cf = f;
443#else
444 void *cf = (char *)f - CFRAME_OFS_SEH;
445#endif
405 lua_State *L = cframe_L(cf); 446 lua_State *L = cframe_L(cf);
406 int errcode = LJ_EXCODE_CHECK(rec->ExceptionCode) ? 447 int errcode = LJ_EXCODE_CHECK(rec->ExceptionCode) ?
407 LJ_EXCODE_ERRCODE(rec->ExceptionCode) : LUA_ERRRUN; 448 LJ_EXCODE_ERRCODE(rec->ExceptionCode) : LUA_ERRRUN;
@@ -419,8 +460,9 @@ LJ_FUNCA EXCEPTION_DISPOSITION lj_err_unwind_win64(EXCEPTION_RECORD *rec,
419 setstrV(L, L->top++, lj_err_str(L, LJ_ERR_ERRCPP)); 460 setstrV(L, L->top++, lj_err_str(L, LJ_ERR_ERRCPP));
420 } else if (!LJ_EXCODE_CHECK(rec->ExceptionCode)) { 461 } else if (!LJ_EXCODE_CHECK(rec->ExceptionCode)) {
421 /* Don't catch access violations etc. */ 462 /* Don't catch access violations etc. */
422 return ExceptionContinueSearch; 463 return 1; /* ExceptionContinueSearch */
423 } 464 }
465#if LJ_TARGET_X64
424 /* Unwind the stack and call all handlers for all lower C frames 466 /* Unwind the stack and call all handlers for all lower C frames
425 ** (including ourselves) again with EH_UNWINDING set. Then set 467 ** (including ourselves) again with EH_UNWINDING set. Then set
426 ** rsp = cf, rax = errcode and jump to the specified target. 468 ** rsp = cf, rax = errcode and jump to the specified target.
@@ -430,9 +472,21 @@ LJ_FUNCA EXCEPTION_DISPOSITION lj_err_unwind_win64(EXCEPTION_RECORD *rec,
430 lj_vm_unwind_c_eh), 472 lj_vm_unwind_c_eh),
431 rec, (void *)(uintptr_t)errcode, ctx, dispatch->HistoryTable); 473 rec, (void *)(uintptr_t)errcode, ctx, dispatch->HistoryTable);
432 /* RtlUnwindEx should never return. */ 474 /* RtlUnwindEx should never return. */
475#else
476 UNUSED(ctx);
477 UNUSED(dispatch);
478 /* Call all handlers for all lower C frames (including ourselves) again
479 ** with EH_UNWINDING set. Then call the specified function, passing cf
480 ** and errcode.
481 */
482 lj_vm_rtlunwind(cf, (void *)rec,
483 (cframe_unwind_ff(cf2) && errcode != LUA_YIELD) ?
484 (void *)lj_vm_unwind_ff : (void *)lj_vm_unwind_c, errcode);
485 /* lj_vm_rtlunwind does not return. */
486#endif
433 } 487 }
434 } 488 }
435 return ExceptionContinueSearch; 489 return 1; /* ExceptionContinueSearch */
436} 490}
437 491
438/* Raise Windows exception. */ 492/* Raise Windows exception. */
@@ -450,8 +504,8 @@ LJ_NOINLINE void LJ_FASTCALL lj_err_throw(lua_State *L, int errcode)
450{ 504{
451 global_State *g = G(L); 505 global_State *g = G(L);
452 lj_trace_abort(g); 506 lj_trace_abort(g);
453 setgcrefnull(g->jit_L); 507 setmref(g->jit_base, NULL);
454 L->status = 0; 508 L->status = LUA_OK;
455#if LJ_UNWIND_EXT 509#if LJ_UNWIND_EXT
456 err_raise_ext(errcode); 510 err_raise_ext(errcode);
457 /* 511 /*
@@ -495,7 +549,7 @@ LJ_NOINLINE void lj_err_mem(lua_State *L)
495/* Find error function for runtime errors. Requires an extra stack traversal. */ 549/* Find error function for runtime errors. Requires an extra stack traversal. */
496static ptrdiff_t finderrfunc(lua_State *L) 550static ptrdiff_t finderrfunc(lua_State *L)
497{ 551{
498 cTValue *frame = L->base-1, *bot = tvref(L->stack); 552 cTValue *frame = L->base-1, *bot = tvref(L->stack)+LJ_FR2;
499 void *cf = L->cframe; 553 void *cf = L->cframe;
500 while (frame > bot && cf) { 554 while (frame > bot && cf) {
501 while (cframe_nres(cframe_raw(cf)) < 0) { /* cframe without frame? */ 555 while (cframe_nres(cframe_raw(cf)) < 0) { /* cframe without frame? */
@@ -519,10 +573,8 @@ static ptrdiff_t finderrfunc(lua_State *L)
519 frame = frame_prevd(frame); 573 frame = frame_prevd(frame);
520 break; 574 break;
521 case FRAME_CONT: 575 case FRAME_CONT:
522#if LJ_HASFFI 576 if (frame_iscont_fficb(frame))
523 if ((frame-1)->u32.lo == LJ_CONT_FFI_CALLBACK)
524 cf = cframe_prev(cf); 577 cf = cframe_prev(cf);
525#endif
526 frame = frame_prevd(frame); 578 frame = frame_prevd(frame);
527 break; 579 break;
528 case FRAME_CP: 580 case FRAME_CP:
@@ -534,11 +586,11 @@ static ptrdiff_t finderrfunc(lua_State *L)
534 break; 586 break;
535 case FRAME_PCALL: 587 case FRAME_PCALL:
536 case FRAME_PCALLH: 588 case FRAME_PCALLH:
537 if (frame_ftsz(frame) >= (ptrdiff_t)(2*sizeof(TValue))) /* xpcall? */ 589 if (frame_func(frame_prevd(frame))->c.ffid == FF_xpcall)
538 return savestack(L, frame-1); /* Point to xpcall's errorfunc. */ 590 return savestack(L, frame_prevd(frame)+1); /* xpcall's errorfunc. */
539 return 0; 591 return 0;
540 default: 592 default:
541 lua_assert(0); 593 lj_assertL(0, "bad frame type");
542 return 0; 594 return 0;
543 } 595 }
544 } 596 }
@@ -558,8 +610,9 @@ LJ_NOINLINE void LJ_FASTCALL lj_err_run(lua_State *L)
558 lj_err_throw(L, LUA_ERRERR); 610 lj_err_throw(L, LUA_ERRERR);
559 } 611 }
560 L->status = LUA_ERRERR; 612 L->status = LUA_ERRERR;
561 copyTV(L, top, top-1); 613 copyTV(L, top+LJ_FR2, top-1);
562 copyTV(L, top-1, errfunc); 614 copyTV(L, top-1, errfunc);
615 if (LJ_FR2) setnilV(top++);
563 L->top = top+1; 616 L->top = top+1;
564 lj_vm_call(L, top, 1+1); /* Stack: |errfunc|msg| -> |msg| */ 617 lj_vm_call(L, top, 1+1); /* Stack: |errfunc|msg| -> |msg| */
565 } 618 }
@@ -573,7 +626,7 @@ LJ_NORET LJ_NOINLINE static void err_msgv(lua_State *L, ErrMsg em, ...)
573 va_list argp; 626 va_list argp;
574 va_start(argp, em); 627 va_start(argp, em);
575 if (curr_funcisL(L)) L->top = curr_topL(L); 628 if (curr_funcisL(L)) L->top = curr_topL(L);
576 msg = lj_str_pushvf(L, err2msg(em), argp); 629 msg = lj_strfmt_pushvf(L, err2msg(em), argp);
577 va_end(argp); 630 va_end(argp);
578 lj_debug_addloc(L, msg, L->base-1, NULL); 631 lj_debug_addloc(L, msg, L->base-1, NULL);
579 lj_err_run(L); 632 lj_err_run(L);
@@ -591,11 +644,11 @@ LJ_NOINLINE void lj_err_lex(lua_State *L, GCstr *src, const char *tok,
591{ 644{
592 char buff[LUA_IDSIZE]; 645 char buff[LUA_IDSIZE];
593 const char *msg; 646 const char *msg;
594 lj_debug_shortname(buff, src); 647 lj_debug_shortname(buff, src, line);
595 msg = lj_str_pushvf(L, err2msg(em), argp); 648 msg = lj_strfmt_pushvf(L, err2msg(em), argp);
596 msg = lj_str_pushf(L, "%s:%d: %s", buff, line, msg); 649 msg = lj_strfmt_pushf(L, "%s:%d: %s", buff, line, msg);
597 if (tok) 650 if (tok)
598 lj_str_pushf(L, err2msg(LJ_ERR_XNEAR), msg, tok); 651 lj_strfmt_pushf(L, err2msg(LJ_ERR_XNEAR), msg, tok);
599 lj_err_throw(L, LUA_ERRSYNTAX); 652 lj_err_throw(L, LUA_ERRSYNTAX);
600} 653}
601 654
@@ -634,8 +687,9 @@ LJ_NOINLINE void lj_err_optype_call(lua_State *L, TValue *o)
634 const BCIns *pc = cframe_Lpc(L); 687 const BCIns *pc = cframe_Lpc(L);
635 if (((ptrdiff_t)pc & FRAME_TYPE) != FRAME_LUA) { 688 if (((ptrdiff_t)pc & FRAME_TYPE) != FRAME_LUA) {
636 const char *tname = lj_typename(o); 689 const char *tname = lj_typename(o);
690 setframe_gc(o, obj2gco(L), LJ_TTHREAD);
691 if (LJ_FR2) o++;
637 setframe_pc(o, pc); 692 setframe_pc(o, pc);
638 setframe_gc(o, obj2gco(L));
639 L->top = L->base = o+1; 693 L->top = L->base = o+1;
640 err_msgv(L, LJ_ERR_BADCALL, tname); 694 err_msgv(L, LJ_ERR_BADCALL, tname);
641 } 695 }
@@ -650,13 +704,10 @@ LJ_NOINLINE void lj_err_callermsg(lua_State *L, const char *msg)
650 if (frame_islua(frame)) { 704 if (frame_islua(frame)) {
651 pframe = frame_prevl(frame); 705 pframe = frame_prevl(frame);
652 } else if (frame_iscont(frame)) { 706 } else if (frame_iscont(frame)) {
653#if LJ_HASFFI 707 if (frame_iscont_fficb(frame)) {
654 if ((frame-1)->u32.lo == LJ_CONT_FFI_CALLBACK) {
655 pframe = frame; 708 pframe = frame;
656 frame = NULL; 709 frame = NULL;
657 } else 710 } else {
658#endif
659 {
660 pframe = frame_prevd(frame); 711 pframe = frame_prevd(frame);
661#if LJ_HASFFI 712#if LJ_HASFFI
662 /* Remove frame for FFI metamethods. */ 713 /* Remove frame for FFI metamethods. */
@@ -679,7 +730,7 @@ LJ_NOINLINE void lj_err_callerv(lua_State *L, ErrMsg em, ...)
679 const char *msg; 730 const char *msg;
680 va_list argp; 731 va_list argp;
681 va_start(argp, em); 732 va_start(argp, em);
682 msg = lj_str_pushvf(L, err2msg(em), argp); 733 msg = lj_strfmt_pushvf(L, err2msg(em), argp);
683 va_end(argp); 734 va_end(argp);
684 lj_err_callermsg(L, msg); 735 lj_err_callermsg(L, msg);
685} 736}
@@ -699,9 +750,9 @@ LJ_NORET LJ_NOINLINE static void err_argmsg(lua_State *L, int narg,
699 if (narg < 0 && narg > LUA_REGISTRYINDEX) 750 if (narg < 0 && narg > LUA_REGISTRYINDEX)
700 narg = (int)(L->top - L->base) + narg + 1; 751 narg = (int)(L->top - L->base) + narg + 1;
701 if (ftype && ftype[3] == 'h' && --narg == 0) /* Check for "method". */ 752 if (ftype && ftype[3] == 'h' && --narg == 0) /* Check for "method". */
702 msg = lj_str_pushf(L, err2msg(LJ_ERR_BADSELF), fname, msg); 753 msg = lj_strfmt_pushf(L, err2msg(LJ_ERR_BADSELF), fname, msg);
703 else 754 else
704 msg = lj_str_pushf(L, err2msg(LJ_ERR_BADARG), narg, fname, msg); 755 msg = lj_strfmt_pushf(L, err2msg(LJ_ERR_BADARG), narg, fname, msg);
705 lj_err_callermsg(L, msg); 756 lj_err_callermsg(L, msg);
706} 757}
707 758
@@ -711,7 +762,7 @@ LJ_NOINLINE void lj_err_argv(lua_State *L, int narg, ErrMsg em, ...)
711 const char *msg; 762 const char *msg;
712 va_list argp; 763 va_list argp;
713 va_start(argp, em); 764 va_start(argp, em);
714 msg = lj_str_pushvf(L, err2msg(em), argp); 765 msg = lj_strfmt_pushvf(L, err2msg(em), argp);
715 va_end(argp); 766 va_end(argp);
716 err_argmsg(L, narg, msg); 767 err_argmsg(L, narg, msg);
717} 768}
@@ -741,7 +792,7 @@ LJ_NOINLINE void lj_err_argtype(lua_State *L, int narg, const char *xname)
741 TValue *o = narg < 0 ? L->top + narg : L->base + narg-1; 792 TValue *o = narg < 0 ? L->top + narg : L->base + narg-1;
742 tname = o < L->top ? lj_typename(o) : lj_obj_typename[0]; 793 tname = o < L->top ? lj_typename(o) : lj_obj_typename[0];
743 } 794 }
744 msg = lj_str_pushf(L, err2msg(LJ_ERR_BADTYPE), xname, tname); 795 msg = lj_strfmt_pushf(L, err2msg(LJ_ERR_BADTYPE), xname, tname);
745 err_argmsg(L, narg, msg); 796 err_argmsg(L, narg, msg);
746} 797}
747 798
@@ -791,7 +842,7 @@ LUALIB_API int luaL_error(lua_State *L, const char *fmt, ...)
791 const char *msg; 842 const char *msg;
792 va_list argp; 843 va_list argp;
793 va_start(argp, fmt); 844 va_start(argp, fmt);
794 msg = lj_str_pushvf(L, fmt, argp); 845 msg = lj_strfmt_pushvf(L, fmt, argp);
795 va_end(argp); 846 va_end(argp);
796 lj_err_callermsg(L, msg); 847 lj_err_callermsg(L, msg);
797 return 0; /* unreachable */ 848 return 0; /* unreachable */