aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Pall <mike>2011-10-24 16:02:37 +0200
committerMike Pall <mike>2011-10-24 16:11:38 +0200
commita0d782755482483c09e919a51c396322dd228bf2 (patch)
treebf599dfa722e463593f44f9f8647fb75b4618381
parent84683405fbacad0938a953d9654bec27ac75d565 (diff)
downloadluajit-a0d782755482483c09e919a51c396322dd228bf2.tar.gz
luajit-a0d782755482483c09e919a51c396322dd228bf2.tar.bz2
luajit-a0d782755482483c09e919a51c396322dd228bf2.zip
Generalize handling of stack checks indicated by highest exit + 1.
-rw-r--r--src/lj_asm.c10
-rw-r--r--src/lj_asm_arm.h1
-rw-r--r--src/lj_target_arm.h2
-rw-r--r--src/lj_trace.c21
4 files changed, 22 insertions, 12 deletions
diff --git a/src/lj_asm.c b/src/lj_asm.c
index c795b99e..bb134ac2 100644
--- a/src/lj_asm.c
+++ b/src/lj_asm.c
@@ -1357,9 +1357,15 @@ static void asm_head_side(ASMState *as)
1357 /* Inherit top stack slot already checked by parent trace. */ 1357 /* Inherit top stack slot already checked by parent trace. */
1358 as->T->topslot = as->parent->topslot; 1358 as->T->topslot = as->parent->topslot;
1359 if (as->topslot > as->T->topslot) { /* Need to check for higher slot? */ 1359 if (as->topslot > as->T->topslot) { /* Need to check for higher slot? */
1360 as->T->topslot = (uint8_t)as->topslot; /* Remember for child traces. */ 1360#ifdef EXITSTATE_CHECKEXIT
1361 /* Highest exit + 1 indicates stack check. */
1362 ExitNo exitno = as->T->nsnap;
1363#else
1361 /* Reuse the parent exit in the context of the parent trace. */ 1364 /* Reuse the parent exit in the context of the parent trace. */
1362 asm_stack_check(as, as->topslot, irp, allow & RSET_GPR, as->J->exitno); 1365 ExitNo exitno = as->J->exitno;
1366#endif
1367 as->T->topslot = (uint8_t)as->topslot; /* Remember for child traces. */
1368 asm_stack_check(as, as->topslot, irp, allow & RSET_GPR, exitno);
1363 } 1369 }
1364} 1370}
1365 1371
diff --git a/src/lj_asm_arm.h b/src/lj_asm_arm.h
index 27f1d6c1..786dd831 100644
--- a/src/lj_asm_arm.h
+++ b/src/lj_asm_arm.h
@@ -1418,7 +1418,6 @@ static void asm_stack_check(ASMState *as, BCReg topslot,
1418 Reg pbase; 1418 Reg pbase;
1419 uint32_t k; 1419 uint32_t k;
1420 if (irp) { 1420 if (irp) {
1421 exitno = as->T->nsnap; /* Highest exit + 1 indicates stack check. */
1422 if (ra_hasreg(irp->r)) { 1421 if (ra_hasreg(irp->r)) {
1423 pbase = irp->r; 1422 pbase = irp->r;
1424 } else if (allow) { 1423 } else if (allow) {
diff --git a/src/lj_target_arm.h b/src/lj_target_arm.h
index 210fe497..0f50cf9c 100644
--- a/src/lj_target_arm.h
+++ b/src/lj_target_arm.h
@@ -117,6 +117,8 @@ typedef struct {
117 117
118/* PC after instruction that caused an exit. Used to find the trace number. */ 118/* PC after instruction that caused an exit. Used to find the trace number. */
119#define EXITSTATE_PCREG RID_PC 119#define EXITSTATE_PCREG RID_PC
120/* Highest exit + 1 indicates stack check. */
121#define EXITSTATE_CHECKEXIT 1
120 122
121#define EXITSTUB_SPACING 4 123#define EXITSTUB_SPACING 4
122#define EXITSTUBS_PER_GROUP 32 124#define EXITSTUBS_PER_GROUP 32
diff --git a/src/lj_trace.c b/src/lj_trace.c
index f907a77f..9645ecba 100644
--- a/src/lj_trace.c
+++ b/src/lj_trace.c
@@ -727,14 +727,8 @@ static TraceNo trace_exit_find(jit_State *J, MCode *pc)
727 TraceNo traceno; 727 TraceNo traceno;
728 for (traceno = 1; traceno < J->sizetrace; traceno++) { 728 for (traceno = 1; traceno < J->sizetrace; traceno++) {
729 GCtrace *T = traceref(J, traceno); 729 GCtrace *T = traceref(J, traceno);
730 if (T && pc >= T->mcode && pc < (MCode *)((char *)T->mcode + T->szmcode)) { 730 if (T && pc >= T->mcode && pc < (MCode *)((char *)T->mcode + T->szmcode))
731 if (J->exitno == T->nsnap) { /* Treat stack check like a parent exit. */
732 lua_assert(T->root != 0);
733 traceno = T->ir[REF_BASE].op1;
734 J->exitno = T->ir[REF_BASE].op2;
735 }
736 return traceno; 731 return traceno;
737 }
738 } 732 }
739 lua_assert(0); 733 lua_assert(0);
740 return 0; 734 return 0;
@@ -751,11 +745,20 @@ int LJ_FASTCALL lj_trace_exit(jit_State *J, void *exptr)
751 int errcode; 745 int errcode;
752 const BCIns *pc; 746 const BCIns *pc;
753 void *cf; 747 void *cf;
748 GCtrace *T;
754#ifdef EXITSTATE_PCREG 749#ifdef EXITSTATE_PCREG
755 J->parent = trace_exit_find(J, (MCode *)(intptr_t)ex->gpr[EXITSTATE_PCREG]); 750 J->parent = trace_exit_find(J, (MCode *)(intptr_t)ex->gpr[EXITSTATE_PCREG]);
756#endif 751#endif
757 lua_assert(traceref(J, J->parent) != NULL && 752 T = traceref(J, J->parent); UNUSED(T);
758 J->exitno < traceref(J, J->parent)->nsnap); 753#ifdef EXITSTATE_CHECKEXIT
754 if (J->exitno == T->nsnap) { /* Treat stack check like a parent exit. */
755 lua_assert(T->root != 0);
756 J->exitno = T->ir[REF_BASE].op2;
757 J->parent = T->ir[REF_BASE].op1;
758 T = traceref(J, J->parent);
759 }
760#endif
761 lua_assert(T != NULL && J->exitno < T->nsnap);
759 exd.J = J; 762 exd.J = J;
760 exd.exptr = exptr; 763 exd.exptr = exptr;
761 errcode = lj_vm_cpcall(L, NULL, &exd, trace_exit_cp); 764 errcode = lj_vm_cpcall(L, NULL, &exd, trace_exit_cp);