зеркало из https://github.com/mozilla/gecko-dev.git
Bug 633016 - Notify debug hooks of script lifetime when pulling script from the eval cache (r=luke)
--HG-- extra : rebase_source : cec97d3ad0bcbad52bda31fb6148ce1e6a1a3b95
This commit is contained in:
Родитель
d738f7dcea
Коммит
f054d767fb
|
@ -1850,7 +1850,7 @@ js_DestroyScriptsToGC(JSContext *cx, JSCompartment *comp)
|
|||
while ((script = *listp) != NULL) {
|
||||
*listp = script->u.nextToGC;
|
||||
script->u.nextToGC = NULL;
|
||||
js_DestroyScriptFromGC(cx, script);
|
||||
js_DestroyCachedScript(cx, script);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1249,9 +1249,23 @@ EvalKernel(JSContext *cx, uintN argc, Value *vp, EvalType evalType, JSStackFrame
|
|||
|
||||
JSScript *script = NULL;
|
||||
JSScript **bucket = EvalCacheHash(cx, linearStr);
|
||||
if (evalType == DIRECT_EVAL && caller->isFunctionFrame() && !caller->isEvalFrame())
|
||||
if (evalType == DIRECT_EVAL && caller->isFunctionFrame() && !caller->isEvalFrame()) {
|
||||
script = EvalCacheLookup(cx, linearStr, caller, staticLevel, principals, scopeobj, bucket);
|
||||
|
||||
/*
|
||||
* Although the eval cache keeps a script alive from the perspective of
|
||||
* the JS engine, from a jsdbgapi user's perspective each eval()
|
||||
* creates and destroys a script. This hides implementation details and
|
||||
* allows jsdbgapi clients to avoid calling JS_GetScriptObject after a
|
||||
* script has been returned to the eval cache, which is invalid since
|
||||
* script->u.object aliases script->u.nextToGC.
|
||||
*/
|
||||
if (script) {
|
||||
js_CallNewScriptHook(cx, script, NULL);
|
||||
MUST_FLOW_THROUGH("destroy");
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* We can't have a callerFrame (down in js::Execute's terms) if we're in
|
||||
* global code (or if we're an indirect eval).
|
||||
|
@ -1280,6 +1294,9 @@ EvalKernel(JSContext *cx, uintN argc, Value *vp, EvalType evalType, JSStackFrame
|
|||
cx->runtime->atomState.evalAtom) &&
|
||||
Execute(cx, scopeobj, script, callerFrame, JSFRAME_EVAL, vp);
|
||||
|
||||
MUST_FLOW_LABEL(destroy);
|
||||
js_CallDestroyScriptHook(cx, script);
|
||||
|
||||
script->u.nextToGC = *bucket;
|
||||
*bucket = script;
|
||||
#ifdef CHECK_SCRIPT_OWNER
|
||||
|
|
|
@ -1561,7 +1561,7 @@ js_CallNewScriptHook(JSContext *cx, JSScript *script, JSFunction *fun)
|
|||
}
|
||||
}
|
||||
|
||||
JS_FRIEND_API(void)
|
||||
void
|
||||
js_CallDestroyScriptHook(JSContext *cx, JSScript *script)
|
||||
{
|
||||
JSDestroyScriptHook hook;
|
||||
|
@ -1569,6 +1569,7 @@ js_CallDestroyScriptHook(JSContext *cx, JSScript *script)
|
|||
hook = cx->debugHooks->destroyScriptHook;
|
||||
if (hook)
|
||||
hook(cx, script, cx->debugHooks->destroyScriptHookData);
|
||||
JS_ClearScriptTraps(cx, script);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -1581,9 +1582,6 @@ DestroyScript(JSContext *cx, JSScript *script)
|
|||
JS_RUNTIME_UNMETER(cx->runtime, liveScripts);
|
||||
#endif
|
||||
|
||||
js_CallDestroyScriptHook(cx, script);
|
||||
JS_ClearScriptTraps(cx, script);
|
||||
|
||||
if (script->principals)
|
||||
JSPRINCIPALS_DROP(cx, script->principals);
|
||||
|
||||
|
@ -1646,11 +1644,20 @@ void
|
|||
js_DestroyScript(JSContext *cx, JSScript *script)
|
||||
{
|
||||
JS_ASSERT(!cx->runtime->gcRunning);
|
||||
js_CallDestroyScriptHook(cx, script);
|
||||
DestroyScript(cx, script);
|
||||
}
|
||||
|
||||
void
|
||||
js_DestroyScriptFromGC(JSContext *cx, JSScript *script)
|
||||
{
|
||||
JS_ASSERT(cx->runtime->gcRunning);
|
||||
js_CallDestroyScriptHook(cx, script);
|
||||
DestroyScript(cx, script);
|
||||
}
|
||||
|
||||
void
|
||||
js_DestroyCachedScript(JSContext *cx, JSScript *script)
|
||||
{
|
||||
JS_ASSERT(cx->runtime->gcRunning);
|
||||
DestroyScript(cx, script);
|
||||
|
|
|
@ -649,7 +649,7 @@ js_SweepScriptFilenames(JSRuntime *rt);
|
|||
extern JS_FRIEND_API(void)
|
||||
js_CallNewScriptHook(JSContext *cx, JSScript *script, JSFunction *fun);
|
||||
|
||||
extern JS_FRIEND_API(void)
|
||||
extern void
|
||||
js_CallDestroyScriptHook(JSContext *cx, JSScript *script);
|
||||
|
||||
/*
|
||||
|
@ -659,13 +659,18 @@ js_CallDestroyScriptHook(JSContext *cx, JSScript *script);
|
|||
extern void
|
||||
js_DestroyScript(JSContext *cx, JSScript *script);
|
||||
|
||||
/*
|
||||
* If data is not null, it indicates that the script could been accessed only
|
||||
* from that thread.
|
||||
*/
|
||||
extern void
|
||||
js_DestroyScriptFromGC(JSContext *cx, JSScript *script);
|
||||
|
||||
/*
|
||||
* Script objects may be cached and reused, in which case their JSD-visible
|
||||
* lifetimes may be shorter than their actual lifetimes. Destroy one such
|
||||
* script for real as part of a GC pass. From JSD's point of view, the script
|
||||
* is already dead.
|
||||
*/
|
||||
extern void
|
||||
js_DestroyCachedScript(JSContext *cx, JSScript *script);
|
||||
|
||||
extern void
|
||||
js_TraceScript(JSTracer *trc, JSScript *script);
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче