Bug 874679 - Clear JS holders when they are unrooted. r=smaug
authorAndrew McCreight <amccreight@mozilla.com>
Wed, 07 Aug 2013 17:22:57 -0700
changeset 141748 34d52be130aadc78dcec6cc1b30f7446f021e131
parent 141747 ab9642207875d08e6351bfe0edaabc165095d4ec
child 141749 e4dfd9facfbdf1378bf4b4f6e36db5b649eb142a
push id1
push userroot
push dateMon, 20 Oct 2014 17:29:22 +0000
reviewerssmaug
bugs874679
milestone26.0a1
Bug 874679 - Clear JS holders when they are unrooted. r=smaug
xpcom/base/CycleCollectedJSRuntime.cpp
--- a/xpcom/base/CycleCollectedJSRuntime.cpp
+++ b/xpcom/base/CycleCollectedJSRuntime.cpp
@@ -847,28 +847,52 @@ CycleCollectedJSRuntime::TraceNativeGray
 }
 
 void
 CycleCollectedJSRuntime::AddJSHolder(void* aHolder, nsScriptObjectTracer* aTracer)
 {
   mJSHolders.Put(aHolder, aTracer);
 }
 
+struct ClearJSHolder : TraceCallbacks
+{
+  virtual void Trace(JS::Heap<JS::Value>* aPtr, const char*, void*) const MOZ_OVERRIDE
+  {
+    *aPtr = JSVAL_VOID;
+  }
+
+  virtual void Trace(JS::Heap<jsid>* aPtr, const char*, void*) const MOZ_OVERRIDE
+  {
+    *aPtr = JSID_VOID;
+  }
+
+  virtual void Trace(JS::Heap<JSObject*>* aPtr, const char*, void*) const MOZ_OVERRIDE
+  {
+    *aPtr = nullptr;
+  }
+
+  virtual void Trace(JS::Heap<JSString*>* aPtr, const char*, void*) const MOZ_OVERRIDE
+  {
+    *aPtr = nullptr;
+  }
+
+  virtual void Trace(JS::Heap<JSScript*>* aPtr, const char*, void*) const MOZ_OVERRIDE
+  {
+    *aPtr = nullptr;
+  }
+};
+
 void
 CycleCollectedJSRuntime::RemoveJSHolder(void* aHolder)
 {
-#ifdef DEBUG
-  // Assert that the holder doesn't try to keep any GC things alive.
-  // In case of unlinking cycle collector calls AssertNoObjectsToTrace
-  // manually because we don't want to check the holder before we are
-  // finished unlinking it
-  if (aHolder != mObjectToUnlink) {
-    AssertNoObjectsToTrace(aHolder);
+  nsScriptObjectTracer* tracer = mJSHolders.Get(aHolder);
+  if (!tracer) {
+    return;
   }
-#endif
+  tracer->Trace(aHolder, ClearJSHolder(), nullptr);
   mJSHolders.Remove(aHolder);
 }
 
 #ifdef DEBUG
 bool
 CycleCollectedJSRuntime::TestJSHolder(void* aHolder)
 {
   return mJSHolders.Get(aHolder, nullptr);