From 86609aa9f8894eca0ce053e95c877c2e7739d3fc Mon Sep 17 00:00:00 2001 From: David Mandelin Date: Mon, 10 Aug 2009 13:03:50 -0700 Subject: [PATCH] Bug 508187: do stack push after all guards when tracing JSOP_INCNAME et al, r=gal --- js/src/jstracer.cpp | 32 ++++++++++++++++++++++++-------- js/src/jstracer.h | 6 ++++-- js/src/trace-test.js | 19 +++++++++++++++++++ 3 files changed, 47 insertions(+), 10 deletions(-) diff --git a/js/src/jstracer.cpp b/js/src/jstracer.cpp index 4d945ee5bf7..dfee6445986 100644 --- a/js/src/jstracer.cpp +++ b/js/src/jstracer.cpp @@ -7267,12 +7267,10 @@ TraceRecorder::inc(jsval& v, jsint incr, bool pre) * (pre- or post-increment as described by pre) is stacked. */ JS_REQUIRES_STACK JSRecordingStatus -TraceRecorder::inc(jsval& v, LIns*& v_ins, jsint incr, bool pre) +TraceRecorder::inc(jsval v, LIns*& v_ins, jsint incr, bool pre) { - if (!isNumber(v)) - ABORT_TRACE("can only inc numbers"); - - LIns* v_after = alu(LIR_fadd, asNumber(v), incr, v_ins, lir->insImmf(incr)); + LIns* v_after; + CHECK_STATUS(incHelper(v, v_ins, v_after, incr)); const JSCodeSpec& cs = js_CodeSpec[*cx->fp->regs->pc]; JS_ASSERT(cs.ndefs == 1); @@ -7281,6 +7279,18 @@ TraceRecorder::inc(jsval& v, LIns*& v_ins, jsint incr, bool pre) return JSRS_CONTINUE; } +/* + * Do an increment operation without storing anything to the stack. + */ +JS_REQUIRES_STACK JSRecordingStatus +TraceRecorder::incHelper(jsval v, LIns* v_ins, LIns*& v_after, jsint incr) +{ + if (!isNumber(v)) + ABORT_TRACE("can only inc numbers"); + v_after = alu(LIR_fadd, asNumber(v), incr, v_ins, lir->insImmf(incr)); + return JSRS_CONTINUE; +} + JS_REQUIRES_STACK JSRecordingStatus TraceRecorder::incProp(jsint incr, bool pre) { @@ -9539,11 +9549,15 @@ TraceRecorder::incName(jsint incr, bool pre) { jsval* vp; LIns* v_ins; + LIns* v_after; NameResult nr; + CHECK_STATUS(name(vp, v_ins, nr)); - CHECK_STATUS(inc(*vp, v_ins, incr, pre)); + CHECK_STATUS(incHelper(*vp, v_ins, v_after, incr)); + LIns* v_result = pre ? v_after : v_ins; if (nr.tracked) { - set(vp, v_ins); + set(vp, v_after); + stack(0, v_result); return JSRS_CONTINUE; } @@ -9552,7 +9566,9 @@ TraceRecorder::incName(jsint incr, bool pre) LIns* callobj_ins = get(&cx->fp->argv[-2]); for (jsint i = 0; i < nr.scopeIndex; ++i) callobj_ins = stobj_get_parent(callobj_ins); - return setCallProp(nr.obj, callobj_ins, nr.sprop, v_ins, *vp); + CHECK_STATUS(setCallProp(nr.obj, callobj_ins, nr.sprop, v_after, *vp)); + stack(0, v_result); + return JSRS_CONTINUE; } JS_REQUIRES_STACK JSRecordingStatus diff --git a/js/src/jstracer.h b/js/src/jstracer.h index a609aaa7fe1..9930e2ce564 100644 --- a/js/src/jstracer.h +++ b/js/src/jstracer.h @@ -709,8 +709,10 @@ class TraceRecorder : public avmplus::GCObject { JS_REQUIRES_STACK JSRecordingStatus tableswitch(); #endif JS_REQUIRES_STACK JSRecordingStatus inc(jsval& v, jsint incr, bool pre = true); - JS_REQUIRES_STACK JSRecordingStatus inc(jsval& v, nanojit::LIns*& v_ins, jsint incr, - bool pre = true); + JS_REQUIRES_STACK JSRecordingStatus inc(jsval v, nanojit::LIns*& v_ins, jsint incr, + bool pre = true); + JS_REQUIRES_STACK JSRecordingStatus incHelper(jsval v, nanojit::LIns* v_ins, + nanojit::LIns*& v_after, jsint incr); JS_REQUIRES_STACK JSRecordingStatus incProp(jsint incr, bool pre = true); JS_REQUIRES_STACK JSRecordingStatus incElem(jsint incr, bool pre = true); JS_REQUIRES_STACK JSRecordingStatus incName(jsint incr, bool pre = true); diff --git a/js/src/trace-test.js b/js/src/trace-test.js index bd10bc1fc57..49d67ca12aa 100644 --- a/js/src/trace-test.js +++ b/js/src/trace-test.js @@ -5664,6 +5664,25 @@ function testMultipleArgumentsObjects() { testMultipleArgumentsObjects.expected = ",,,,f"; test(testMultipleArgumentsObjects); +function testClosureIncrSideExit() { + let(f = function (y) { + let(ff = function (g) { + for each(let h in g) { + if (++y > 5) { + return 'ddd'; + } + } + return 'qqq'; + }) { + return ff(['', null, '', false, '', '', null]); + } + }) { + return f(-1); + } +} +testClosureIncrSideExit.expected = "ddd"; +test(testClosureIncrSideExit); + /***************************************************************************** * * * _____ _ _ _____ ______ _____ _______ *