Backed out changeset 0064d8949f0c (bug 1102541) for build bustage on a CLOSED TREE
authorWes Kocher <wkocher@mozilla.com>
Fri, 12 Dec 2014 12:39:07 -0800
changeset 219475 93ede5de8bd31bd3316ade72b0731fe11bd4e660
parent 219474 d37c4cbaf41dbc75503d05fd34816c086ebf33eb
child 219476 4c12f753a0049ceac0dbc8f2e72fa892e2b1e150
push id52846
push userkwierso@gmail.com
push dateFri, 12 Dec 2014 20:57:51 +0000
treeherdermozilla-inbound@93ede5de8bd3 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
bugs1102541
milestone37.0a1
backs out0064d8949f0c0cd397696b894a6eeb51107c5315
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
Backed out changeset 0064d8949f0c (bug 1102541) for build bustage on a CLOSED TREE
js/public/UbiNode.h
js/src/vm/Debugger.cpp
js/src/vm/DebuggerMemory.cpp
js/src/vm/UbiNode.cpp
--- a/js/public/UbiNode.h
+++ b/js/public/UbiNode.h
@@ -467,55 +467,49 @@ typedef mozilla::Vector<SimpleEdge, 8, j
 // runtime. Having a single root |ubi::Node| is useful for algorithms written
 // with the assumption that there aren't multiple roots (such as computing
 // dominator trees) and you want a single point of entry. It also ensures that
 // the roots themselves get visited by |ubi::BreadthFirst| (they would otherwise
 // only be used as starting points).
 //
 // RootList::init itself causes a minor collection, but once the list of roots
 // has been created, GC must not occur, as the referent ubi::Nodes are not
-// stable across GC. The init calls emplace on |noGC|'s AutoCheckCannotGC, whose
+// stable across GC. The init calls emplace |gcp|'s AutoCheckCannotGC, whose
 // lifetime must extend at least as long as the RootList itself.
 //
 // Example usage:
 //
 //    {
 //        mozilla::Maybe<JS::AutoCheckCannotGC> maybeNoGC;
 //        JS::ubi::RootList rootList(cx, maybeNoGC);
-//        if (!rootList.init())
+//        if (!rootList.init(cx))
 //            return false;
 //
 //        // The AutoCheckCannotGC is guaranteed to exist if init returned true.
 //        MOZ_ASSERT(maybeNoGC.isSome());
 //
 //        JS::ubi::Node root(&rootList);
 //
 //        ...
 //    }
 class MOZ_STACK_CLASS RootList {
     Maybe<AutoCheckCannotGC> &noGC;
-    JSContext                *cx;
 
   public:
     SimpleEdgeVector edges;
     bool             wantNames;
 
     RootList(JSContext *cx, Maybe<AutoCheckCannotGC> &noGC, bool wantNames = false);
 
     // Find all GC roots.
-    bool init();
+    bool init(JSContext *cx);
     // Find only GC roots in the provided set of |Zone|s.
-    bool init(ZoneSet &debuggees);
+    bool init(JSContext *cx, ZoneSet &debuggees);
     // Find only GC roots in the given Debugger object's set of debuggee zones.
-    bool init(HandleObject debuggees);
-
-    // Explicitly add the given Node as a root in this RootList. If wantNames is
-    // true, you must pass an edgeName. The RootList does not take ownership of
-    // edgeName.
-    bool addRoot(Node node, const char16_t *edgeName = nullptr);
+    bool init(JSContext *cx, HandleObject debuggees);
 };
 
 
 // Concrete classes for ubi::Node referent types.
 
 template<>
 struct Concrete<RootList> : public Base {
     EdgeRange *edges(JSContext *cx, bool wantNames) const MOZ_OVERRIDE;
--- a/js/src/vm/Debugger.cpp
+++ b/js/src/vm/Debugger.cpp
@@ -3554,25 +3554,33 @@ class MOZ_STACK_CLASS Debugger::ObjectQu
     /*
      * Traverse the heap to find all relevant objects and add them to the
      * provided vector.
      */
     bool findObjects(AutoObjectVector &objs) {
         if (!prepareQuery())
             return false;
 
+        // Ensure that all of our debuggee globals are rooted so that they are
+        // visible in the RootList.
+        JS::AutoObjectVector debuggees(cx);
+        for (GlobalObjectSet::Range r = dbg->allDebuggees(); !r.empty(); r.popFront()) {
+            if (!debuggees.append(r.front()))
+                return false;
+        }
+
         {
             /*
              * We can't tolerate the GC moving things around while we're
              * searching the heap. Check that nothing we do causes a GC.
              */
             Maybe<JS::AutoCheckCannotGC> maybeNoGC;
             RootedObject dbgObj(cx, dbg->object);
             JS::ubi::RootList rootList(cx, maybeNoGC);
-            if (!rootList.init(dbgObj))
+            if (!rootList.init(cx, dbgObj))
                 return false;
 
             Traversal traversal(cx, *this, maybeNoGC.ref());
             if (!traversal.init())
                 return false;
             traversal.wantNames = false;
 
             if (!traversal.addStart(JS::ubi::Node(&rootList)) ||
--- a/js/src/vm/DebuggerMemory.cpp
+++ b/js/src/vm/DebuggerMemory.cpp
@@ -752,28 +752,32 @@ DebuggerMemory::takeCensus(JSContext *cx
     if (!census.init())
         return false;
 
     dbg::DefaultCensusHandler handler(census);
     if (!handler.init(census))
         return false;
 
     Debugger *dbg = memory->getDebugger();
-    RootedObject dbgObj(cx, dbg->object);
 
-    // Populate our target set of debuggee zones.
+    // Populate census.debuggeeZones and ensure that all of our debuggee globals
+    // are rooted so that they are visible in the RootList.
+    JS::AutoObjectVector debuggees(cx);
     for (GlobalObjectSet::Range r = dbg->allDebuggees(); !r.empty(); r.popFront()) {
-        if (!census.debuggeeZones.put(r.front()->zone()))
+        if (!census.debuggeeZones.put(r.front()->zone()) ||
+            !debuggees.append(static_cast<JSObject *>(r.front())))
+        {
             return false;
+        }
     }
 
     {
         Maybe<JS::AutoCheckCannotGC> maybeNoGC;
         JS::ubi::RootList rootList(cx, maybeNoGC);
-        if (!rootList.init(dbgObj))
+        if (!rootList.init(cx, census.debuggeeZones))
             return false;
 
         dbg::DefaultCensusTraversal traversal(cx, handler, maybeNoGC.ref());
         if (!traversal.init())
             return false;
         traversal.wantNames = false;
 
         if (!traversal.addStart(JS::ubi::Node(&rootList)) ||
--- a/js/src/vm/UbiNode.cpp
+++ b/js/src/vm/UbiNode.cpp
@@ -4,23 +4,21 @@
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #include "js/UbiNode.h"
 
 #include "mozilla/Assertions.h"
 #include "mozilla/Attributes.h"
 #include "mozilla/Scoped.h"
-#include "mozilla/UniquePtr.h"
 
 #include "jscntxt.h"
 #include "jsinfer.h"
 #include "jsobj.h"
 #include "jsscript.h"
-#include "jsstr.h"
 
 #include "jit/IonCode.h"
 #include "js/Debug.h"
 #include "js/TracingAPI.h"
 #include "js/TypeDecls.h"
 #include "js/Utility.h"
 #include "js/Vector.h"
 #include "vm/GlobalObject.h"
@@ -260,35 +258,34 @@ template class TracerConcrete<js::types:
 }
 
 
 namespace JS {
 namespace ubi {
 
 RootList::RootList(JSContext *cx, Maybe<AutoCheckCannotGC> &noGC, bool wantNames /* = false */)
   : noGC(noGC),
-    cx(cx),
     edges(cx),
     wantNames(wantNames)
 { }
 
 
 bool
-RootList::init()
+RootList::init(JSContext *cx)
 {
     SimpleEdgeVectorTracer tracer(cx, &edges, wantNames);
     JS_TraceRuntime(&tracer);
     if (!tracer.okay)
         return false;
     noGC.emplace(cx->runtime());
     return true;
 }
 
 bool
-RootList::init(ZoneSet &debuggees)
+RootList::init(JSContext *cx, ZoneSet &debuggees)
 {
     SimpleEdgeVector allRootEdges(cx);
     SimpleEdgeVectorTracer tracer(cx, &allRootEdges, wantNames);
 
     JS_TraceRuntime(&tracer);
     if (!tracer.okay)
         return false;
     JS_TraceIncomingCCWs(&tracer, debuggees);
@@ -304,59 +301,31 @@ RootList::init(ZoneSet &debuggees)
             return false;
     }
 
     noGC.emplace(cx->runtime());
     return true;
 }
 
 bool
-RootList::init(HandleObject debuggees)
+RootList::init(JSContext *cx, HandleObject debuggees)
 {
     MOZ_ASSERT(debuggees && JS::dbg::IsDebugger(ObjectValue(*debuggees)));
     js::Debugger *dbg = js::Debugger::fromJSObject(debuggees);
 
     ZoneSet debuggeeZones;
     if (!debuggeeZones.init())
         return false;
 
     for (js::GlobalObjectSet::Range r = dbg->allDebuggees(); !r.empty(); r.popFront()) {
         if (!debuggeeZones.put(r.front()->zone()))
             return false;
     }
 
-    if (!init(debuggeeZones))
-        return false;
-
-    // Ensure that each of our debuggee globals are in the root list.
-    for (GlobalObjectSet::Range r = dbg->allDebuggees(); !r.empty(); r.popFront()) {
-        if (!addRoot(JS::ubi::Node(static_cast<JSObject *>(r.front())),
-                     MOZ_UTF16("debuggee global")))
-        {
-            return false;
-        }
-    }
-
-    return true;
-}
-
-bool
-RootList::addRoot(Node node, const char16_t *edgeName)
-{
-    MOZ_ASSERT(noGC.isSome());
-    MOZ_ASSERT_IF(wantNames, edgeName);
-
-    mozilla::UniquePtr<char16_t[], JS::FreePolicy> name;
-    if (edgeName) {
-        name = DuplicateString(cx, edgeName);
-        if (!name)
-            return false;
-    }
-
-    return edges.append(mozilla::Move(SimpleEdge(name.release(), node)));
+    return init(cx, debuggeeZones);
 }
 
 // An EdgeRange concrete class that holds a pre-existing vector of SimpleEdges.
 class PreComputedEdgeRange : public EdgeRange {
     SimpleEdgeVector &edges;
     size_t           i;
 
     void settle() {