From d58ade6e883d0153348e774a1f83444748b9baf6 Mon Sep 17 00:00:00 2001 From: David Anderson Date: Fri, 23 Oct 2009 11:16:05 -0700 Subject: [PATCH] Fixed slurp-fail anchors trying to import and read from the tracker (bug 524061, r=gal). --- js/src/jsrecursion.cpp | 7 +++++-- js/src/jstracer.cpp | 35 +++++++++++++++++++---------------- 2 files changed, 24 insertions(+), 18 deletions(-) diff --git a/js/src/jsrecursion.cpp b/js/src/jsrecursion.cpp index 0b2fc0dc58a7..0cee51511ffe 100644 --- a/js/src/jsrecursion.cpp +++ b/js/src/jsrecursion.cpp @@ -447,7 +447,10 @@ TraceRecorder::slurpDownFrames(jsbytecode* return_pc) cx->fp->regs->pc = exit->pc; js_CaptureStackTypes(cx, frameDepth, typeMap); cx->fp->regs->pc = oldpc; - typeMap[downPostSlots] = determineSlotType(&stackval(-1)); + if (!anchor || anchor->exitType != RECURSIVE_SLURP_FAIL_EXIT) + typeMap[downPostSlots] = determineSlotType(&stackval(-1)); + else + typeMap[downPostSlots] = anchor->stackTypeMap()[anchor->numStackSlots - 1]; determineGlobalTypes(&typeMap[exit->numStackSlots]); #if defined JS_JIT_SPEW TreevisLogExit(cx, exit); @@ -553,7 +556,7 @@ TraceRecorder::slurpDownFrames(jsbytecode* return_pc) RecursiveSlotMap slotMap(*this, downPostSlots, rval_ins); for (unsigned i = 0; i < downPostSlots; i++) slotMap.addSlot(typeMap[i]); - slotMap.addSlot(&stackval(-1)); + slotMap.addSlot(&stackval(-1), typeMap[downPostSlots]); VisitGlobalSlots(slotMap, cx, *treeInfo->globalSlots); debug_only_print0(LC_TMTracer, "Compiling up-recursive slurp...\n"); exit = copy(exit); diff --git a/js/src/jstracer.cpp b/js/src/jstracer.cpp index f92f9dac184a..ab043c2d372a 100644 --- a/js/src/jstracer.cpp +++ b/js/src/jstracer.cpp @@ -3615,9 +3615,6 @@ TraceRecorder::import(TreeInfo* treeInfo, LIns* sp, unsigned stackSlots, unsigne ImportUnboxedStackSlotVisitor unboxedStackVisitor(*this, sp, offset, typeMap); VisitStackSlots(unboxedStackVisitor, cx, callDepth); - } else { - import(sp, nativeStackOffset(&stackval(-1)), &stackval(-1), - typeMap[treeInfo->nStackTypes - 1], "retval", 0, cx->fp); } } @@ -4370,15 +4367,15 @@ class SlotMap : public SlotVisitorBase struct SlotInfo { SlotInfo() - : v(NULL), promoteInt(false), lastCheck(TypeCheck_Bad) + : vp(NULL), promoteInt(false), lastCheck(TypeCheck_Bad) {} - SlotInfo(jsval* v, bool promoteInt) - : v(v), promoteInt(promoteInt), lastCheck(TypeCheck_Bad), type(getCoercedType(*v)) + SlotInfo(jsval* vp, bool promoteInt) + : vp(vp), promoteInt(promoteInt), lastCheck(TypeCheck_Bad), type(getCoercedType(*vp)) {} - SlotInfo(JSTraceType t) - : v(NULL), promoteInt(t == TT_INT32), lastCheck(TypeCheck_Bad), type(t) + SlotInfo(jsval* vp, JSTraceType t) + : vp(vp), promoteInt(t == TT_INT32), lastCheck(TypeCheck_Bad), type(t) {} - jsval *v; + jsval *vp; bool promoteInt; TypeCheckResult lastCheck; JSTraceType type; @@ -4454,7 +4451,13 @@ class SlotMap : public SlotVisitorBase JS_REQUIRES_STACK JS_ALWAYS_INLINE void addSlot(JSTraceType t) { - slots.add(SlotInfo(t)); + slots.add(SlotInfo(NULL, t)); + } + + JS_REQUIRES_STACK JS_ALWAYS_INLINE void + addSlot(jsval *vp, JSTraceType t) + { + slots.add(SlotInfo(vp, t)); } JS_REQUIRES_STACK void @@ -4484,13 +4487,13 @@ class SlotMap : public SlotVisitorBase JS_ASSERT(info.lastCheck != TypeCheck_Undemote && info.lastCheck != TypeCheck_Bad); if (info.lastCheck == TypeCheck_Promote) { JS_ASSERT(info.type == TT_INT32 || info.type == TT_DOUBLE); - mRecorder.set(info.v, mRecorder.f2i(mRecorder.get(info.v))); + mRecorder.set(info.vp, mRecorder.f2i(mRecorder.get(info.vp))); } else if (info.lastCheck == TypeCheck_Demote) { JS_ASSERT(info.type == TT_INT32 || info.type == TT_DOUBLE); - JS_ASSERT(mRecorder.get(info.v)->isQuad()); + JS_ASSERT(mRecorder.get(info.vp)->isQuad()); /* Never demote this final i2f. */ - mRecorder.set(info.v, mRecorder.get(info.v), false, false); + mRecorder.set(info.vp, mRecorder.get(info.vp), false, false); } } @@ -4513,13 +4516,13 @@ class SlotMap : public SlotVisitorBase if (!slots[i].promoteInt) return TypeCheck_Undemote; /* Looks good, slot is an int32, the last instruction should be promotable. */ - JS_ASSERT_IF(slots[i].v, isInt32(*slots[i].v) && slots[i].promoteInt); - return slots[i].v ? TypeCheck_Promote : TypeCheck_Okay; + JS_ASSERT_IF(slots[i].vp, isInt32(*slots[i].vp) && slots[i].promoteInt); + return slots[i].vp ? TypeCheck_Promote : TypeCheck_Okay; case TT_DOUBLE: if (slots[i].type != TT_INT32 && slots[i].type != TT_DOUBLE) return TypeCheck_Bad; /* Not a number? Type mismatch. */ if (slots[i].promoteInt) - return slots[i].v ? TypeCheck_Demote : TypeCheck_Bad; + return slots[i].vp ? TypeCheck_Demote : TypeCheck_Bad; return TypeCheck_Okay; default: return slots[i].type == t ? TypeCheck_Okay : TypeCheck_Bad;