diff options
author | Mike Pall <mike> | 2010-03-13 17:45:09 +0100 |
---|---|---|
committer | Mike Pall <mike> | 2010-03-13 17:45:09 +0100 |
commit | 16f33422f14573d23522bc4e69cc6219e36f63e9 (patch) | |
tree | 5bc71712d294c856ca32e0c707a5fb61ad375cc9 /src | |
parent | 4f19a15bd9dfbd4e5c3ffc6a70b72449fb79a7ee (diff) | |
download | luajit-16f33422f14573d23522bc4e69cc6219e36f63e9.tar.gz luajit-16f33422f14573d23522bc4e69cc6219e36f63e9.tar.bz2 luajit-16f33422f14573d23522bc4e69cc6219e36f63e9.zip |
Restore MULTRES for snapshots pointing to CALLM etc. bytecodes.
Diffstat (limited to 'src')
-rw-r--r-- | src/lj_asm.c | 23 | ||||
-rw-r--r-- | src/lj_snap.c | 9 | ||||
-rw-r--r-- | src/lj_trace.c | 20 |
3 files changed, 49 insertions, 3 deletions
diff --git a/src/lj_asm.c b/src/lj_asm.c index cd1c0dbd..c749ada0 100644 --- a/src/lj_asm.c +++ b/src/lj_asm.c | |||
@@ -3253,6 +3253,16 @@ static void asm_head_side(ASMState *as) | |||
3253 | 3253 | ||
3254 | /* -- Tail of trace ------------------------------------------------------- */ | 3254 | /* -- Tail of trace ------------------------------------------------------- */ |
3255 | 3255 | ||
3256 | /* Set MULTRES in C frame. */ | ||
3257 | static void asm_tail_multres(ASMState *as, BCReg mres) | ||
3258 | { | ||
3259 | /* We don't know spadj yet, so get the C frame from L->cframe. */ | ||
3260 | emit_movmroi(as, RID_RET, CFRAME_OFS_MULTRES, mres); | ||
3261 | emit_gri(as, XG_ARITHi(XOg_AND), RID_RET|REX_64, CFRAME_RAWMASK); | ||
3262 | emit_rmro(as, XO_MOV, RID_RET|REX_64, RID_RET, offsetof(lua_State, cframe)); | ||
3263 | emit_getgl(as, RID_RET, jit_L); | ||
3264 | } | ||
3265 | |||
3256 | /* Link to another trace. */ | 3266 | /* Link to another trace. */ |
3257 | static void asm_tail_link(ASMState *as) | 3267 | static void asm_tail_link(ASMState *as) |
3258 | { | 3268 | { |
@@ -3273,6 +3283,19 @@ static void asm_tail_link(ASMState *as) | |||
3273 | } | 3283 | } |
3274 | emit_loada(as, RID_DISPATCH, J2GG(as->J)->dispatch); | 3284 | emit_loada(as, RID_DISPATCH, J2GG(as->J)->dispatch); |
3275 | emit_loada(as, RID_PC, pc); | 3285 | emit_loada(as, RID_PC, pc); |
3286 | switch (bc_op(*pc)) { | ||
3287 | case BC_CALLM: case BC_CALLMT: | ||
3288 | asm_tail_multres(as, snap->nslots - baseslot - 1 - bc_a(*pc) - bc_c(*pc)); | ||
3289 | break; | ||
3290 | case BC_RETM: | ||
3291 | asm_tail_multres(as, snap->nslots - baseslot - bc_a(*pc) - bc_d(*pc)); | ||
3292 | break; | ||
3293 | case BC_TSETM: | ||
3294 | asm_tail_multres(as, snap->nslots - baseslot - bc_a(*pc)); | ||
3295 | break; | ||
3296 | default: | ||
3297 | break; | ||
3298 | } | ||
3276 | } else if (baseslot) { | 3299 | } else if (baseslot) { |
3277 | /* Save modified BASE for linking to trace with higher start frame. */ | 3300 | /* Save modified BASE for linking to trace with higher start frame. */ |
3278 | emit_setgl(as, RID_BASE, jit_base); | 3301 | emit_setgl(as, RID_BASE, jit_base); |
diff --git a/src/lj_snap.c b/src/lj_snap.c index 86890a26..fe0389fe 100644 --- a/src/lj_snap.c +++ b/src/lj_snap.c | |||
@@ -309,7 +309,14 @@ const BCIns *lj_snap_restore(jit_State *J, void *exptr) | |||
309 | } | 309 | } |
310 | } | 310 | } |
311 | } | 311 | } |
312 | L->top = curr_topL(L); | 312 | switch (bc_op(*pc)) { |
313 | case BC_CALLM: case BC_CALLMT: case BC_RETM: case BC_TSETM: | ||
314 | L->top = frame + nslots; | ||
315 | break; | ||
316 | default: | ||
317 | L->top = curr_topL(L); | ||
318 | break; | ||
319 | } | ||
313 | lua_assert(map + nent == flinks); | 320 | lua_assert(map + nent == flinks); |
314 | return pc; | 321 | return pc; |
315 | } | 322 | } |
diff --git a/src/lj_trace.c b/src/lj_trace.c index 246dc03c..f7b12068 100644 --- a/src/lj_trace.c +++ b/src/lj_trace.c | |||
@@ -666,6 +666,7 @@ int LJ_FASTCALL lj_trace_exit(jit_State *J, void *exptr) | |||
666 | ExitDataCP exd; | 666 | ExitDataCP exd; |
667 | int errcode; | 667 | int errcode; |
668 | const BCIns *pc; | 668 | const BCIns *pc; |
669 | void *cf; | ||
669 | exd.J = J; | 670 | exd.J = J; |
670 | exd.exptr = exptr; | 671 | exd.exptr = exptr; |
671 | errcode = lj_vm_cpcall(L, NULL, &exd, trace_exit_cp); | 672 | errcode = lj_vm_cpcall(L, NULL, &exd, trace_exit_cp); |
@@ -692,7 +693,9 @@ int LJ_FASTCALL lj_trace_exit(jit_State *J, void *exptr) | |||
692 | 693 | ||
693 | pc = exd.pc; | 694 | pc = exd.pc; |
694 | trace_hotside(J, pc); | 695 | trace_hotside(J, pc); |
695 | if (bc_op(*pc) == BC_JLOOP) { | 696 | cf = cframe_raw(L->cframe); |
697 | switch (bc_op(*pc)) { | ||
698 | case BC_JLOOP: { | ||
696 | BCIns *retpc = &J->trace[bc_d(*pc)]->startins; | 699 | BCIns *retpc = &J->trace[bc_d(*pc)]->startins; |
697 | if (bc_isret(bc_op(*retpc))) { | 700 | if (bc_isret(bc_op(*retpc))) { |
698 | if (J->state == LJ_TRACE_RECORD) { | 701 | if (J->state == LJ_TRACE_RECORD) { |
@@ -703,8 +706,21 @@ int LJ_FASTCALL lj_trace_exit(jit_State *J, void *exptr) | |||
703 | pc = retpc; | 706 | pc = retpc; |
704 | } | 707 | } |
705 | } | 708 | } |
709 | break; | ||
710 | } | ||
711 | case BC_CALLM: case BC_CALLMT: | ||
712 | cframe_multres(cf) = (BCReg)(L->top - L->base) - bc_a(*pc) - bc_c(*pc); | ||
713 | break; | ||
714 | case BC_RETM: | ||
715 | cframe_multres(cf) = (BCReg)(L->top - L->base) + 1 - bc_a(*pc) - bc_d(*pc); | ||
716 | break; | ||
717 | case BC_TSETM: | ||
718 | cframe_multres(cf) = (BCReg)(L->top - L->base) + 1 - bc_a(*pc); | ||
719 | break; | ||
720 | default: | ||
721 | break; | ||
706 | } | 722 | } |
707 | setcframe_pc(cframe_raw(L->cframe), pc); | 723 | setcframe_pc(cf, pc); |
708 | return 0; | 724 | return 0; |
709 | } | 725 | } |
710 | 726 | ||