Bug 1510607 - Implement JS::IsCCTraceKind using the JS_FOR_EACH_TRACEKIND data. r=jonco
authorYoshi Huang <allstars.chh@gmail.com>
Fri, 30 Nov 2018 22:27:12 +0100
changeset 508756 2c48655b33ca454f532c9d47b6b386b13b0e7ca0
parent 508755 7dee627d2f740f0190ae1be201ac3bf9eaaa5659
child 508757 65ee8bd1ce811a07e413b20295963a615459f4c7
push id1905
push userffxbld-merge
push dateMon, 21 Jan 2019 12:33:13 +0000
treeherdermozilla-release@c2fca1944d8c [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersjonco
bugs1510607
milestone65.0a1
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
Bug 1510607 - Implement JS::IsCCTraceKind using the JS_FOR_EACH_TRACEKIND data. r=jonco To use the data inside JS_FOR_EACH_TRACEKIND, so we could have a unified source of data to decide whether CC should care about this Trackind.
js/public/TraceKind.h
js/src/gc/Marking.cpp
--- a/js/public/TraceKind.h
+++ b/js/public/TraceKind.h
@@ -63,28 +63,16 @@ enum class TraceKind {
   Scope = 0x3F,
   RegExpShared = 0x4F,
 #ifdef ENABLE_BIGINT
   BigInt = 0x5F
 #endif
 };
 const static uintptr_t OutOfLineTraceKindMask = 0x07;
 
-// Returns true if the JS::TraceKind is one the cycle collector cares about.
-// Everything used as WeakMap key should be listed here, to represent the key
-// in cycle collector's graph, otherwise the key is considered to be pointed
-// from somewhere unknown, and results in leaking the subgraph which contains
-// the key.
-// See the comments in NoteWeakMapsTracer::trace for more details.
-inline constexpr bool IsCCTraceKind(JS::TraceKind aKind) {
-  return aKind == JS::TraceKind::Object || aKind == JS::TraceKind::Script ||
-         aKind == JS::TraceKind::LazyScript || aKind == JS::TraceKind::Scope ||
-         aKind == JS::TraceKind::RegExpShared;
-}
-
 #define ASSERT_TRACE_KIND(tk)                                             \
   static_assert(                                                          \
       (uintptr_t(tk) & OutOfLineTraceKindMask) == OutOfLineTraceKindMask, \
       "mask bits are set")
 ASSERT_TRACE_KIND(JS::TraceKind::BaseShape);
 ASSERT_TRACE_KIND(JS::TraceKind::JitCode);
 ASSERT_TRACE_KIND(JS::TraceKind::LazyScript);
 ASSERT_TRACE_KIND(JS::TraceKind::Scope);
@@ -111,25 +99,49 @@ struct MapTypeToTraceKind {
   D(ObjectGroup, js::ObjectGroup, true)                   \
   D(Script, JSScript, true)                               \
   D(Shape, js::Shape, true)                               \
   D(String, JSString, false)                              \
   D(Symbol, JS::Symbol, false)                            \
   IF_BIGINT(D(BigInt, JS::BigInt, false), )               \
   D(RegExpShared, js::RegExpShared, true)
 
+// Returns true if the JS::TraceKind is one the cycle collector cares about.
+// Everything used as WeakMap key should be listed here, to represent the key
+// in cycle collector's graph, otherwise the key is considered to be pointed
+// from somewhere unknown, and results in leaking the subgraph which contains
+// the key.
+// See the comments in NoteWeakMapsTracer::trace for more details.
+inline constexpr bool IsCCTraceKind(JS::TraceKind aKind)
+{
+  switch (aKind) {
+#define JS_EXPAND_DEF(name, _, isCCTraceKind) \
+    case JS::TraceKind::name: \
+      return isCCTraceKind;
+    JS_FOR_EACH_TRACEKIND(JS_EXPAND_DEF);
+#undef JS_EXPAND_DEF
+    default:
+      return false;
+  }
+}
+
 // Map from all public types to their trace kind.
 #define JS_EXPAND_DEF(name, type, _)                       \
   template <>                                              \
   struct MapTypeToTraceKind<type> {                        \
     static const JS::TraceKind kind = JS::TraceKind::name; \
   };
 JS_FOR_EACH_TRACEKIND(JS_EXPAND_DEF);
 #undef JS_EXPAND_DEF
 
+template <typename T>
+struct TypeParticipatesInCC {
+  static const bool value = IsCCTraceKind(MapTypeToTraceKind<T>::kind);
+};
+
 // RootKind is closely related to TraceKind. Whereas TraceKind's indices are
 // laid out for convenient embedding as a pointer tag, the indicies of RootKind
 // are designed for use as array keys via EnumeratedArray.
 enum class RootKind : int8_t {
 // These map 1:1 with trace kinds.
 #define EXPAND_ROOT_KIND(name, _0, _1) name,
   JS_FOR_EACH_TRACEKIND(EXPAND_ROOT_KIND)
 #undef EXPAND_ROOT_KIND
--- a/js/src/gc/Marking.cpp
+++ b/js/src/gc/Marking.cpp
@@ -909,30 +909,20 @@ struct TraverseEdgeFunctor : public Void
 
 template <typename S, typename T>
 void js::GCMarker::traverseEdge(S source, const T& thing) {
   DispatchTyped(TraverseEdgeFunctor<T, S>(), thing, this, source);
 }
 
 namespace {
 
-template <typename T>
-struct TypeParticipatesInCC {};
-#define EXPAND_PARTICIPATES_IN_CC(_, type, addToCCKind) \
-  template <>                                           \
-  struct TypeParticipatesInCC<type> {                   \
-    static const bool value = addToCCKind;              \
-  };
-JS_FOR_EACH_TRACEKIND(EXPAND_PARTICIPATES_IN_CC)
-#undef EXPAND_PARTICIPATES_IN_CC
-
 struct ParticipatesInCCFunctor {
   template <typename T>
   bool operator()() {
-    return TypeParticipatesInCC<T>::value;
+    return JS::TypeParticipatesInCC<T>::value;
   }
 };
 
 }  // namespace
 
 static bool TraceKindParticipatesInCC(JS::TraceKind kind) {
   return DispatchTraceKindTyped(ParticipatesInCCFunctor(), kind);
 }
@@ -940,17 +930,17 @@ static bool TraceKindParticipatesInCC(JS
 template <typename T>
 bool js::GCMarker::mark(T* thing) {
   if (IsInsideNursery(thing)) {
     return false;
   }
   AssertShouldMarkInZone(thing);
   TenuredCell* cell = TenuredCell::fromPointer(thing);
 
-  if (!TypeParticipatesInCC<T>::value) {
+  if (!JS::TypeParticipatesInCC<T>::value) {
     return cell->markIfUnmarked(MarkColor::Black);
   }
 
   return cell->markIfUnmarked(markColor());
 }
 
 /*** Inline, Eager GC Marking ***********************************************/