From eabfdfe1aa3b4b9c37b99137e6d5fb7cadbd47e9 Mon Sep 17 00:00:00 2001 From: Mike Pall Date: Tue, 9 Oct 2012 13:19:57 +0200 Subject: [PATCH] Don't use stack unwinding for lua_yield(). --- src/lj_api.c | 13 ++++++++----- src/vm_arm.dasc | 8 +++++--- src/vm_mips.dasc | 4 +++- src/vm_ppc.dasc | 11 +++++++---- src/vm_ppcspe.dasc | 11 +++++++---- src/vm_x86.dasc | 5 +++++ 6 files changed, 35 insertions(+), 17 deletions(-) diff --git a/src/lj_api.c b/src/lj_api.c index 5a0bd07a..8d35e0d0 100644 --- a/src/lj_api.c +++ b/src/lj_api.c @@ -1103,6 +1103,9 @@ LUA_API int lua_yield(lua_State *L, int nresults) while (--nresults >= 0) copyTV(L, t++, f++); L->top = t; } + L->cframe = NULL; + L->status = LUA_YIELD; + return -1; } else { /* Yield from hook: add a pseudo-frame. */ TValue *top = L->top; hook_leave(g); @@ -1112,14 +1115,14 @@ LUA_API int lua_yield(lua_State *L, int nresults) setframe_gc(top+2, obj2gco(L)); setframe_ftsz(top+2, (int)((char *)(top+3)-(char *)L->base)+FRAME_CONT); L->top = L->base = top+3; - } #if LJ_TARGET_X64 - lj_err_throw(L, LUA_YIELD); + lj_err_throw(L, LUA_YIELD); #else - L->cframe = NULL; - L->status = LUA_YIELD; - lj_vm_unwind_c(cf, LUA_YIELD); + L->cframe = NULL; + L->status = LUA_YIELD; + lj_vm_unwind_c(cf, LUA_YIELD); #endif + } } lj_err_msg(L, LJ_ERR_CYIELD); return 0; /* unreachable */ diff --git a/src/vm_arm.dasc b/src/vm_arm.dasc index 4909d827..f00b3028 100644 --- a/src/vm_arm.dasc +++ b/src/vm_arm.dasc @@ -269,10 +269,12 @@ static void build_subroutines(BuildCtx *ctx) | sub RA, RA, #8 | |->vm_returnc: - | add RC, RC, #8 // RC = (nresults+1)*8. - | ands CARG1, PC, #FRAME_TYPE + | adds RC, RC, #8 // RC = (nresults+1)*8. + | mov CRET1, #LUA_YIELD + | beq ->vm_unwind_c_eh | str RC, SAVE_MULTRES - | beq ->BC_RET_Z // Handle regular return to Lua. + | ands CARG1, PC, #FRAME_TYPE + | beq ->BC_RET_Z // Handle regular return to Lua. | |->vm_return: | // BASE = base, RA = resultptr, RC/MULTRES = (nresults+1)*8, PC = return diff --git a/src/vm_mips.dasc b/src/vm_mips.dasc index f82cefe8..52fc5fe1 100644 --- a/src/vm_mips.dasc +++ b/src/vm_mips.dasc @@ -327,8 +327,10 @@ static void build_subroutines(BuildCtx *ctx) | addiu RA, RA, -8 | |->vm_returnc: - | andi TMP0, PC, FRAME_TYPE | addiu RD, RD, 8 // RD = (nresults+1)*8. + | andi TMP0, PC, FRAME_TYPE + | beqz RD, ->vm_unwind_c_eh + |. li CRET1, LUA_YIELD | beqz TMP0, ->BC_RET_Z // Handle regular return to Lua. |. move MULTRES, RD | diff --git a/src/vm_ppc.dasc b/src/vm_ppc.dasc index 5a6737ae..ac572ec5 100644 --- a/src/vm_ppc.dasc +++ b/src/vm_ppc.dasc @@ -452,10 +452,13 @@ static void build_subroutines(BuildCtx *ctx) | stwu TMP1, FRAME_PC(RA) // Prepend true to results. | |->vm_returnc: - | andix. TMP0, PC, FRAME_TYPE - | addi RD, RD, 8 // RD = (nresults+1)*8. - | mr MULTRES, RD - | beq ->BC_RET_Z // Handle regular return to Lua. + | addi RD, RD, 8 // RD = (nresults+1)*8. + | andix. TMP0, PC, FRAME_TYPE + | cmpwi cr1, RD, 0 + | li CRET1, LUA_YIELD + | beq cr1, ->vm_unwind_c_eh + | mr MULTRES, RD + | beq ->BC_RET_Z // Handle regular return to Lua. | |->vm_return: | // BASE = base, RA = resultptr, RD/MULTRES = (nresults+1)*8, PC = return diff --git a/src/vm_ppcspe.dasc b/src/vm_ppcspe.dasc index ab2d7670..cbd6ecdd 100644 --- a/src/vm_ppcspe.dasc +++ b/src/vm_ppcspe.dasc @@ -294,10 +294,13 @@ static void build_subroutines(BuildCtx *ctx) | stwu TMP1, FRAME_PC(RA) // Prepend true to results. | |->vm_returnc: - | andi. TMP0, PC, FRAME_TYPE - | addi RD, RD, 8 // RD = (nresults+1)*8. - | mr MULTRES, RD - | beq ->BC_RET_Z // Handle regular return to Lua. + | addi RD, RD, 8 // RD = (nresults+1)*8. + | andi. TMP0, PC, FRAME_TYPE + | cmpwi cr1, RD, 0 + | li CRET1, LUA_YIELD + | beq cr1, ->vm_unwind_c_eh + | mr MULTRES, RD + | beq ->BC_RET_Z // Handle regular return to Lua. | |->vm_return: | // BASE = base, RA = resultptr, RD/MULTRES = (nresults+1)*8, PC = return diff --git a/src/vm_x86.dasc b/src/vm_x86.dasc index 92e98f98..e2b6a078 100644 --- a/src/vm_x86.dasc +++ b/src/vm_x86.dasc @@ -443,6 +443,7 @@ static void build_subroutines(BuildCtx *ctx) | |->vm_returnc: | add RD, 1 // RD = nresults+1 + | jz ->vm_unwind_yield | mov MULTRES, RD | test PC, FRAME_TYPE | jz ->BC_RET_Z // Handle regular return to Lua. @@ -526,6 +527,10 @@ static void build_subroutines(BuildCtx *ctx) | mov BASE, L:RB->top // Need the (realloced) L->top in BASE. | jmp <3 | + |->vm_unwind_yield: + | mov al, LUA_YIELD + | jmp ->vm_unwind_c_eh + | |->vm_unwind_c@8: // Unwind C stack, return from vm_pcall. | // (void *cframe, int errcode) |.if X64