author | Bill McCloskey <wmccloskey@mozilla.com> |
Wed, 12 Jan 2011 10:09:48 -0800 | |
changeset 60567 | 4f71ecca94fe1c220de703e52aa6ca78b05eab45 |
parent 60566 | 1e5925b72c513e2c5e4643b6174930f7ad531112 |
child 60568 | d1adb7b245bdeebc6167f0e068e0366d1e3d0da6 |
push id | 18037 |
push user | cleary@mozilla.com |
push date | Fri, 14 Jan 2011 17:42:55 +0000 |
treeherder | mozilla-central@4e0501a0c5e5 [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
reviewers | dmandelin |
bugs | 617904 |
milestone | 2.0b10pre |
first release with | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
last release without | nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
|
--- a/js/src/jstracer.cpp +++ b/js/src/jstracer.cpp @@ -1411,17 +1411,17 @@ static void Unblacklist(JSScript *script, jsbytecode *pc) { JS_ASSERT(*pc == JSOP_NOTRACE || *pc == JSOP_TRACE); if (*pc == JSOP_NOTRACE) { *pc = JSOP_TRACE; #ifdef JS_METHODJIT /* This code takes care of unblacklisting in the method JIT. */ - js::mjit::EnableTraceHint(script, pc, GET_UINT16(pc)); + js::mjit::ResetTraceHint(script, pc, GET_UINT16(pc), false); #endif } } static bool IsBlacklisted(jsbytecode* pc) { if (*pc == JSOP_NOTRACE) @@ -2740,16 +2740,27 @@ TraceMonitor::flush() verbose_only( for (Seq<Fragment*>* f = branches; f; f = f->tail) FragProfiling_FragFinalizer(f->head, this); ) flushEpoch++; +#ifdef JS_METHODJIT + if (loopProfiles) { + for (LoopProfileMap::Enum e(*loopProfiles); !e.empty(); e.popFront()) { + jsbytecode *pc = e.front().key; + LoopProfile *prof = e.front().value; + /* This code takes care of resetting all methodjit state. */ + js::mjit::ResetTraceHint(prof->entryScript, pc, GET_UINT16(pc), true); + } + } +#endif + frameCache->reset(); dataAlloc->reset(); traceAlloc->reset(); codeAlloc->reset(); tempAlloc->reset(); oracle->clear(); loopProfiles->clear(); @@ -7794,16 +7805,21 @@ PurgeScriptFragments(TraceMonitor* tm, J { debug_only_printf(LC_TMTracer, "Purging fragments for JSScript %p.\n", (void*)script); /* A recorder script is being evaluated and can not be destroyed or GC-ed. */ JS_ASSERT_IF(tm->recorder, JS_UPTRDIFF(tm->recorder->getTree()->ip, script->code) >= script->length); + for (LoopProfileMap::Enum e(*tm->loopProfiles); !e.empty(); e.popFront()) { + if (JS_UPTRDIFF(e.front().key, script->code) < script->length) + e.removeFront(); + } + TracedScriptSet::Ptr found = tm->tracedScripts.lookup(script); if (!found) return; tm->tracedScripts.remove(found); for (size_t i = 0; i < FRAGMENT_TABLE_SIZE; ++i) { TreeFragment** fragp = &tm->vmfragments[i]; while (TreeFragment* frag = *fragp) { @@ -7822,21 +7838,16 @@ PurgeScriptFragments(TraceMonitor* tm, J TrashTree(frag); } while ((frag = frag->peer) != NULL); continue; } fragp = &frag->next; } } - for (LoopProfileMap::Enum e(*tm->loopProfiles); !e.empty(); e.popFront()) { - if (JS_UPTRDIFF(e.front().key, script->code) < script->length) - e.removeFront(); - } - RecordAttemptMap &table = *tm->recordAttempts; for (RecordAttemptMap::Enum e(table); !e.empty(); e.popFront()) { if (JS_UPTRDIFF(e.front().key, script->code) < script->length) e.removeFront(); } } bool
--- a/js/src/methodjit/InvokeHelpers.cpp +++ b/js/src/methodjit/InvokeHelpers.cpp @@ -912,62 +912,69 @@ UpdateTraceHintSingle(Repatcher &repatch */ repatcher.relink(jump, target); JaegerSpew(JSpew_PICs, "relinking trace hint %p to %p\n", jump.executableAddress(), target.executableAddress()); } static void -DisableTraceHint(VMFrame &f, ic::TraceICInfo &tic) +DisableTraceHint(VMFrame &f, ic::TraceICInfo &ic) { Repatcher repatcher(f.jit()); - UpdateTraceHintSingle(repatcher, tic.traceHint, tic.jumpTarget); + UpdateTraceHintSingle(repatcher, ic.traceHint, ic.jumpTarget); - if (tic.hasSlowTraceHint) - UpdateTraceHintSingle(repatcher, tic.slowTraceHint, tic.jumpTarget); + if (ic.hasSlowTraceHint) + UpdateTraceHintSingle(repatcher, ic.slowTraceHint, ic.jumpTarget); } static void -EnableTraceHintAt(JSScript *script, js::mjit::JITScript *jit, jsbytecode *pc, uint16_t index) +ResetTraceHintAt(JSScript *script, js::mjit::JITScript *jit, + jsbytecode *pc, uint16_t index, bool full) { if (index >= jit->nTraceICs) return; - ic::TraceICInfo &tic = jit->traceICs[index]; - if (!tic.initialized) + ic::TraceICInfo &ic = jit->traceICs[index]; + if (!ic.initialized) return; - JS_ASSERT(tic.jumpTargetPC == pc); + JS_ASSERT(ic.jumpTargetPC == pc); JaegerSpew(JSpew_PICs, "Enabling trace IC %u in script %p\n", index, script); Repatcher repatcher(jit); - UpdateTraceHintSingle(repatcher, tic.traceHint, tic.stubEntry); + UpdateTraceHintSingle(repatcher, ic.traceHint, ic.stubEntry); + + if (ic.hasSlowTraceHint) + UpdateTraceHintSingle(repatcher, ic.slowTraceHint, ic.stubEntry); - if (tic.hasSlowTraceHint) - UpdateTraceHintSingle(repatcher, tic.slowTraceHint, tic.stubEntry); + if (full) { + ic.traceData = NULL; + ic.loopCounterStart = 1; + ic.loopCounter = ic.loopCounterStart; + } } #endif void -js::mjit::EnableTraceHint(JSScript *script, jsbytecode *pc, uint16_t index) +js::mjit::ResetTraceHint(JSScript *script, jsbytecode *pc, uint16_t index, bool full) { #if JS_MONOIC if (script->jitNormal) - EnableTraceHintAt(script, script->jitNormal, pc, index); + ResetTraceHintAt(script, script->jitNormal, pc, index, full); if (script->jitCtor) - EnableTraceHintAt(script, script->jitCtor, pc, index); + ResetTraceHintAt(script, script->jitCtor, pc, index, full); #endif } #if JS_MONOIC void * -RunTracer(VMFrame &f, ic::TraceICInfo &tic) +RunTracer(VMFrame &f, ic::TraceICInfo &ic) #else void * RunTracer(VMFrame &f) #endif { JSContext *cx = f.cx; JSStackFrame *entryFrame = f.fp(); TracePointAction tpa; @@ -988,35 +995,35 @@ RunTracer(VMFrame &f) bool blacklist; uintN inlineCallCount = 0; void **traceData; uintN *traceEpoch; uint32 *loopCounter; uint32 hits; #if JS_MONOIC - traceData = &tic.traceData; - traceEpoch = &tic.traceEpoch; - loopCounter = &tic.loopCounter; + traceData = &ic.traceData; + traceEpoch = &ic.traceEpoch; + loopCounter = &ic.loopCounter; *loopCounter = 1; - hits = tic.loopCounterStart; + hits = ic.loopCounterStart; #else traceData = NULL; traceEpoch = NULL; loopCounter = NULL; hits = 1; #endif tpa = MonitorTracePoint(f.cx, inlineCallCount, &blacklist, traceData, traceEpoch, loopCounter, hits); JS_ASSERT(!TRACE_RECORDER(cx)); #if JS_MONOIC - tic.loopCounterStart = *loopCounter; + ic.loopCounterStart = *loopCounter; if (blacklist) - DisableTraceHint(f, tic); + DisableTraceHint(f, ic); #endif // Even though ExecuteTree() bypasses the interpreter, it should propagate // error failures correctly. JS_ASSERT_IF(cx->isExceptionPending(), tpa == TPA_Error); f.fp() = cx->fp(); JS_ASSERT(f.fp() == cx->fp()); @@ -1089,19 +1096,19 @@ RunTracer(VMFrame &f) goto restart; } #endif /* JS_TRACER */ #if defined JS_TRACER # if defined JS_MONOIC void *JS_FASTCALL -stubs::InvokeTracer(VMFrame &f, ic::TraceICInfo *tic) +stubs::InvokeTracer(VMFrame &f, ic::TraceICInfo *ic) { - return RunTracer(f, *tic); + return RunTracer(f, *ic); } # else void *JS_FASTCALL stubs::InvokeTracer(VMFrame &f) { return RunTracer(f);
--- a/js/src/methodjit/MethodJIT.h +++ b/js/src/methodjit/MethodJIT.h @@ -419,19 +419,22 @@ struct CallSite this->id = id; } bool isTrap() const { return id == MAGIC_TRAP_ID; } }; -/* Re-enables a tracepoint in the method JIT. */ +/* + * Re-enables a tracepoint in the method JIT. When full is true, we + * also reset the iteration counter. + */ void -EnableTraceHint(JSScript *script, jsbytecode *pc, uint16_t index); +ResetTraceHint(JSScript *script, jsbytecode *pc, uint16_t index, bool full); uintN GetCallTargetCount(JSScript *script, jsbytecode *pc); inline void * bsearch_nmap(NativeMapEntry *nmap, size_t nPairs, size_t bcOff) { size_t lo = 1, hi = nPairs; while (1) {