Bug 1364528 - Don't synchronously finalize native objects if an exception is pending. r=smaug

MozReview-Commit-ID: 6OY3ftH1aWu

--HG--
extra : rebase_source : 54da36f422af673762aa31e5a1225783e5f776e4
This commit is contained in:
Andrew McCreight 2017-05-12 11:16:16 -07:00
parent c132de25a8
commit bc3190039b
2 changed files with 15 additions and 5 deletions

View File

@ -819,7 +819,7 @@ CycleCollectedJSRuntime::GCCallback(JSContext* aContext,
MOZ_ASSERT(CycleCollectedJSContext::Get()->Context() == aContext);
MOZ_ASSERT(CycleCollectedJSContext::Get()->Runtime() == self);
self->OnGC(aStatus);
self->OnGC(aContext, aStatus);
}
/* static */ void
@ -1423,7 +1423,8 @@ CycleCollectedJSRuntime::AnnotateAndSetOutOfMemory(OOMState* aStatePtr,
}
void
CycleCollectedJSRuntime::OnGC(JSGCStatus aStatus)
CycleCollectedJSRuntime::OnGC(JSContext* aContext,
JSGCStatus aStatus)
{
switch (aStatus) {
case JSGC_BEGIN:
@ -1440,10 +1441,19 @@ CycleCollectedJSRuntime::OnGC(JSGCStatus aStatus)
}
#endif
// Do any deferred finalization of native objects.
FinalizeDeferredThings(JS::WasIncrementalGC(mJSRuntime)
// Do any deferred finalization of native objects. Normally we do this
// incrementally for an incremental GC, and immediately for a
// non-incremental GC, on the basis that the type of GC reflects how
// urgently resources should be destroyed. However under some circumstances
// (such as in js::InternalCallOrConstruct) we can end up running a
// non-incremental GC when there is a pending exception, and the finalizers
// are not set up to handle that. In that case, just run them later, after
// we've returned to the event loop.
bool finalizeIncrementally = JS::WasIncrementalGC(mJSRuntime) || JS_IsExceptionPending(aContext);
FinalizeDeferredThings(finalizeIncrementally
? CycleCollectedJSContext::FinalizeIncrementally
: CycleCollectedJSContext::FinalizeNow);
break;
}
default:

View File

@ -236,7 +236,7 @@ public:
void SetLargeAllocationFailure(OOMState aNewState);
void AnnotateAndSetOutOfMemory(OOMState* aStatePtr, OOMState aNewState);
void OnGC(JSGCStatus aStatus);
void OnGC(JSContext* aContext, JSGCStatus aStatus);
void OnOutOfMemory();
void OnLargeAllocationFailure();