diff --git a/src/lj_opt_fold.c b/src/lj_opt_fold.c index ce78505b..62483c26 100644 --- a/src/lj_opt_fold.c +++ b/src/lj_opt_fold.c @@ -1935,9 +1935,10 @@ LJFOLDF(abc_k) LJFOLD(ABC any any) LJFOLDF(abc_invar) { - /* Invariant ABC marked as PTR. Drop if op1 is invariant, too. */ + /* Invariant ABC marked as P32 or U32. Drop if op1 is invariant too. */ if (!irt_isint(fins->t) && fins->op1 < J->chain[IR_LOOP] && - !irt_isphi(IR(fins->op1)->t)) + (irt_isu32(fins->t) || + (!irref_isk(fins->op1) && !irt_isphi(IR(fins->op1)->t)))) return DROPFOLD; return NEXTFOLD; } @@ -2485,6 +2486,17 @@ LJFOLD(CNEW any any) LJFOLD(XSNEW any any) LJFOLDX(lj_ir_emit) +/* -- Miscellaneous ------------------------------------------------------- */ + +LJFOLD(CARG any any) +LJFOLDF(cse_carg) +{ + TRef tr = lj_opt_cse(J); + if (tref_ref(tr) < J->chain[IR_LOOP]) /* CSE across loop? */ + return EMITFOLD; /* Raw emit. Assumes fins is left intact by CSE. */ + return tr; +} + /* ------------------------------------------------------------------------ */ /* Every entry in the generated hash table is a 32 bit pattern: diff --git a/src/lj_record.c b/src/lj_record.c index 6666b3c6..3ba2ce8b 100644 --- a/src/lj_record.c +++ b/src/lj_record.c @@ -1395,12 +1395,13 @@ static void rec_idx_abc(jit_State *J, TRef asizeref, TRef ikey, uint32_t asize) /* Runtime value for stop of loop is within bounds? */ if ((uint64_t)stop + ofs < (uint64_t)asize) { /* Emit invariant bounds check for stop. */ - emitir(IRTG(IR_ABC, IRT_P32), asizeref, ofs == 0 ? J->scev.stop : + uint32_t abc = IRTG(IR_ABC, tref_isk(asizeref) ? IRT_U32 : IRT_P32); + emitir(abc, asizeref, ofs == 0 ? J->scev.stop : emitir(IRTI(IR_ADD), J->scev.stop, ofsref)); /* Emit invariant bounds check for start, if not const or negative. */ if (!(J->scev.dir && J->scev.start && (int64_t)IR(J->scev.start)->i + ofs >= 0)) - emitir(IRTG(IR_ABC, IRT_P32), asizeref, ikey); + emitir(abc, asizeref, ikey); return; } } diff --git a/src/lj_snap.c b/src/lj_snap.c index 6fda08ba..27f9c8e5 100644 --- a/src/lj_snap.c +++ b/src/lj_snap.c @@ -957,7 +957,8 @@ const BCIns *lj_snap_restore(jit_State *J, void *exptr) lua_State *L = J->L; /* Set interpreter PC to the next PC to get correct error messages. */ - setcframe_pc(cframe_raw(L->cframe), pc+1); + setcframe_pc(L->cframe, pc+1); + setcframe_pc(cframe_raw(cframe_prev(L->cframe)), pc); /* Make sure the stack is big enough for the slots from the snapshot. */ if (LJ_UNLIKELY(L->base + snap->topslot >= tvref(L->maxstack))) { diff --git a/src/lj_trace.c b/src/lj_trace.c index f384cbdb..a5e316e1 100644 --- a/src/lj_trace.c +++ b/src/lj_trace.c @@ -905,10 +905,8 @@ int LJ_FASTCALL lj_trace_exit(jit_State *J, void *exptr) exd.J = J; exd.exptr = exptr; errcode = lj_vm_cpcall(L, NULL, &exd, trace_exit_cp); - if (errcode) { - setcframe_pc(cframe_raw(L->cframe), L); /* Point to any valid memory. */ + if (errcode) return -errcode; /* Return negated error code. */ - } if (exitcode) copyTV(L, L->top++, &exiterr); /* Anchor the error object. */