Bug 1610193 - Do not proxy-preserve weakmap keys with a darker color than the map itself r=jonco a=pascalc DEVEDITION_74_0b3_BUILD1 DEVEDITION_74_0b3_RELEASE FIREFOX_74_0b3_BUILD1 FIREFOX_74_0b3_RELEASE
authorSteve Fink <sfink@mozilla.com>
Tue, 11 Feb 2020 11:26:14 +0000
changeset 575722 64dab3403abc272111d36fb8e9f7c37d6058ea05
parent 575721 997fc6647f1e2966d1d457cde1bef0d42c22806b
child 575723 0da03ca89cd05e7b94947b048d2019ff0fb3bb80
push id12700
push userryanvm@gmail.com
push dateFri, 14 Feb 2020 01:51:26 +0000
treeherdermozilla-beta@64dab3403abc [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersjonco, pascalc
bugs1610193
milestone74.0
Bug 1610193 - Do not proxy-preserve weakmap keys with a darker color than the map itself r=jonco a=pascalc Differential Revision: https://phabricator.services.mozilla.com/D62077
js/src/gc/WeakMap-inl.h
--- a/js/src/gc/WeakMap-inl.h
+++ b/js/src/gc/WeakMap-inl.h
@@ -143,25 +143,28 @@ void WeakMap<K, V>::markKey(GCMarker* ma
 // the key is at least as marked as the delegate, so it cannot get discarded
 // and then recreated by rewrapping the delegate.
 template <class K, class V>
 bool WeakMap<K, V>::markEntry(GCMarker* marker, K& key, V& value) {
   bool marked = false;
   JSRuntime* rt = zone()->runtimeFromAnyThread();
   CellColor keyColor = gc::detail::GetEffectiveColor(rt, key);
   JSObject* delegate = gc::detail::GetDelegate(key);
+
   if (delegate) {
     CellColor delegateColor = gc::detail::GetEffectiveColor(rt, delegate);
-    if (keyColor < delegateColor) {
-      gc::AutoSetMarkColor autoColor(*marker, delegateColor);
+    // The key needs to stay alive while both the delegate and map are live.
+    CellColor proxyPreserveColor = std::min(delegateColor, mapColor);
+    if (keyColor < proxyPreserveColor) {
+      gc::AutoSetMarkColor autoColor(*marker, proxyPreserveColor);
       TraceWeakMapKeyEdge(marker, zone(), &key,
                           "proxy-preserved WeakMap entry key");
-      MOZ_ASSERT(key->color() >= delegateColor);
+      MOZ_ASSERT(key->color() >= proxyPreserveColor);
       marked = true;
-      keyColor = delegateColor;
+      keyColor = proxyPreserveColor;
     }
   }
 
   if (keyColor) {
     gc::Cell* cellValue = gc::ToMarkable(&value);
     if (cellValue) {
       gc::AutoSetMarkColor autoColor(*marker, std::min(mapColor, keyColor));
       CellColor valueColor = gc::detail::GetEffectiveColor(rt, cellValue);