commit 40a21e31ae511494dd4caca4706cf009d3b14984
parent cf425e35dc97a27dec9cf0acd43166d7edf63383
Author: Steve Fink <sfink@mozilla.com>
Date: Mon, 17 Nov 2025 21:37:11 +0000
Bug 1999684 - Remove the surprisingly unused gcNurseryEphemeronEdges r=jonco
Differential Revision: https://phabricator.services.mozilla.com/D272764
Diffstat:
6 files changed, 10 insertions(+), 99 deletions(-)
diff --git a/js/src/gc/GCMarker.h b/js/src/gc/GCMarker.h
@@ -71,21 +71,22 @@ class EphemeronEdge {
uintptr_t taggedTarget;
public:
- EphemeronEdge(MarkColor color, Cell* cell)
+ EphemeronEdge(MarkColor color, TenuredCell* cell)
: taggedTarget(uintptr_t(cell) | uintptr_t(color)) {
MOZ_ASSERT((uintptr_t(cell) & ColorMask) == 0);
}
MarkColor color() const { return MarkColor(taggedTarget & ColorMask); }
- Cell* target() const {
- return reinterpret_cast<Cell*>(taggedTarget & ~ColorMask);
+ TenuredCell* target() const {
+ return reinterpret_cast<TenuredCell*>(taggedTarget & ~ColorMask);
}
};
using EphemeronEdgeVector = Vector<EphemeronEdge, 2, js::SystemAllocPolicy>;
-using EphemeronEdgeTable = HashMap<Cell*, EphemeronEdgeVector,
- PointerHasher<Cell*>, js::SystemAllocPolicy>;
+using EphemeronEdgeTable =
+ HashMap<TenuredCell*, EphemeronEdgeVector, PointerHasher<TenuredCell*>,
+ js::SystemAllocPolicy>;
/*
* The mark stack. Pointers in this stack are "gray" in the GC sense, but
diff --git a/js/src/gc/Marking.cpp b/js/src/gc/Marking.cpp
@@ -780,7 +780,7 @@ void GCMarker::markImplicitEdges(T* markedThing) {
MOZ_ASSERT(!zone->isGCSweeping());
auto& ephemeronTable = zone->gcEphemeronEdges();
- auto p = ephemeronTable.lookup(markedThing);
+ auto p = ephemeronTable.lookup(&markedThing->asTenured());
if (!p) {
return;
}
@@ -2232,7 +2232,6 @@ void GCMarker::start() {
static void ClearEphemeronEdges(JSRuntime* rt) {
for (GCZonesIter zone(rt); !zone.done(); zone.next()) {
zone->gcEphemeronEdges().clearAndCompact();
- zone->gcNurseryEphemeronEdges().clearAndCompact();
}
}
@@ -2399,8 +2398,6 @@ IncrementalProgress JS::Zone::enterWeakMarkingMode(GCMarker* marker,
return IncrementalProgress::Finished;
}
- MOZ_ASSERT(gcNurseryEphemeronEdges().count() == 0);
-
for (auto r = gcEphemeronEdges().all(); !r.empty(); r.popFront()) {
Cell* src = r.front().key();
CellColor srcColor = gc::detail::GetEffectiveColor(marker, src);
diff --git a/js/src/gc/Verifier.cpp b/js/src/gc/Verifier.cpp
@@ -576,7 +576,7 @@ void js::gc::MarkingValidator::nonIncrementalMark(AutoGCSession& session) {
AutoEnterOOMUnsafeRegion oomUnsafe;
for (auto r = zone->gcEphemeronEdges().all(); !r.empty(); r.popFront()) {
- MOZ_ASSERT(r.front().key()->asTenured().zone() == zone);
+ MOZ_ASSERT(r.front().key()->zone() == zone);
if (!savedEphemeronEdges.putNew(r.front().key(),
std::move(r.front().value()))) {
// Notice the std::move -- this could consume the moved-from value even
diff --git a/js/src/gc/WeakMap.cpp b/js/src/gc/WeakMap.cpp
@@ -25,8 +25,6 @@ WeakMapBase::WeakMapBase(JSObject* memOf, Zone* zone)
void WeakMapBase::unmarkZone(JS::Zone* zone) {
zone->gcEphemeronEdges().clearAndCompact();
- MOZ_ASSERT(zone->gcNurseryEphemeronEdges().count() == 0);
-
for (WeakMapBase* m : zone->gcWeakMapList()) {
m->setMapColor(CellColor::White);
}
@@ -98,7 +96,7 @@ bool WeakMapBase::addEphemeronEdge(MarkColor color, gc::TenuredCell* src,
gc::TenuredCell* dst) {
// Add an implicit edge from |src| to |dst|.
- auto& edgeTable = src->zone()->gcEphemeronEdges(src);
+ auto& edgeTable = src->zone()->gcEphemeronEdges();
auto p = edgeTable.lookupForAdd(src);
if (!p) {
if (!edgeTable.add(p, src, EphemeronEdgeVector())) {
diff --git a/js/src/gc/Zone.cpp b/js/src/gc/Zone.cpp
@@ -243,18 +243,7 @@ static void EraseIf(js::gc::EphemeronEdgeVector& entries, Pred pred) {
entries.shrinkBy(removed);
}
-static void SweepEphemeronEdgesWhileMinorSweeping(
- js::gc::EphemeronEdgeVector& entries) {
- EraseIf(entries, [](js::gc::EphemeronEdge& edge) -> bool {
- Cell* target = edge.target();
- bool dead = IsAboutToBeFinalizedDuringMinorSweep(&target);
- edge = js::gc::EphemeronEdge(edge.color(), target);
- return dead;
- });
-}
-
void Zone::sweepAfterMinorGC(JSTracer* trc) {
- sweepEphemeronTablesAfterMinorGC();
crossZoneStringWrappers().sweepAfterMinorGC(trc);
for (CompartmentsInZoneIter comp(this); !comp.done(); comp.next()) {
@@ -262,68 +251,6 @@ void Zone::sweepAfterMinorGC(JSTracer* trc) {
}
}
-void Zone::sweepEphemeronTablesAfterMinorGC() {
- for (auto r = gcNurseryEphemeronEdges().all(); !r.empty(); r.popFront()) {
- // Sweep gcNurseryEphemeronEdges to move live (forwarded) keys to
- // gcEphemeronEdges, scanning through all the entries for such keys to
- // update them.
- //
- // Forwarded and dead keys may also appear in their delegates' entries,
- // so sweep those too (see below.)
-
- // The tricky case is when the key has a delegate that was already
- // tenured. Then it will be in its compartment's gcEphemeronEdges, but we
- // still need to update the key (which will be in the entries
- // associated with it.)
- gc::Cell* key = r.front().key();
- MOZ_ASSERT(!key->isTenured());
- if (!Nursery::getForwardedPointer(&key)) {
- // Dead nursery cell => discard.
- continue;
- }
-
- // Key been moved. The value is an array of <color,cell> pairs; update all
- // cells in that array.
- EphemeronEdgeVector& entries = r.front().value();
- SweepEphemeronEdgesWhileMinorSweeping(entries);
-
- // Live (moved) nursery cell. Append entries to gcEphemeronEdges.
- EphemeronEdgeTable& tenuredEdges = gcEphemeronEdges();
- AutoEnterOOMUnsafeRegion oomUnsafe;
- auto entry = tenuredEdges.lookupForAdd(key);
- if (!entry) {
- if (!tenuredEdges.add(entry, key, EphemeronEdgeVector())) {
- oomUnsafe.crash("Failed to tenure weak keys entry");
- }
- }
- if (!entry->value().appendAll(entries)) {
- oomUnsafe.crash("Failed to tenure weak keys entry");
- }
-
- // If the key has a delegate, then it will map to a WeakKeyEntryVector
- // containing the key that needs to be updated.
-
- JSObject* delegate = gc::detail::GetDelegate(key->as<JSObject>());
- if (!delegate) {
- continue;
- }
- MOZ_ASSERT(delegate->isTenured());
-
- // If delegate was formerly nursery-allocated, we will sweep its entries
- // when we visit its gcNurseryEphemeronEdges (if we haven't already). Note
- // that we don't know the nursery address of the delegate, since the
- // location it was stored in has already been updated.
- //
- // Otherwise, it will be in gcEphemeronEdges and we sweep it here.
- auto p = delegate->zone()->gcEphemeronEdges().lookup(delegate);
- if (p) {
- SweepEphemeronEdgesWhileMinorSweeping(p->value());
- }
- }
-
- gcNurseryEphemeronEdges().clearAndCompact();
-}
-
void Zone::traceWeakCCWEdges(JSTracer* trc) {
crossZoneStringWrappers().traceWeak(trc);
for (CompartmentsInZoneIter comp(this); !comp.done(); comp.next()) {
diff --git a/js/src/gc/Zone.h b/js/src/gc/Zone.h
@@ -478,11 +478,8 @@ class Zone : public js::ZoneAllocator, public js::gc::GraphNodeBase<JS::Zone> {
weakCaches_;
// Mapping from not yet marked keys to a vector of all values that the key
- // maps to in any live weak map. Separate tables for nursery and tenured
- // keys.
+ // maps to in any live weak map.
js::MainThreadOrGCTaskData<js::gc::EphemeronEdgeTable> gcEphemeronEdges_;
- js::MainThreadOrGCTaskData<js::gc::EphemeronEdgeTable>
- gcNurseryEphemeronEdges_;
js::MainThreadData<js::UniquePtr<js::RegExpZone>> regExps_;
@@ -858,13 +855,6 @@ class Zone : public js::ZoneAllocator, public js::gc::GraphNodeBase<JS::Zone> {
js::gc::EphemeronEdgeTable& gcEphemeronEdges() {
return gcEphemeronEdges_.ref();
}
- js::gc::EphemeronEdgeTable& gcNurseryEphemeronEdges() {
- return gcNurseryEphemeronEdges_.ref();
- }
-
- js::gc::EphemeronEdgeTable& gcEphemeronEdges(const js::gc::Cell* cell) {
- return cell->isTenured() ? gcEphemeronEdges() : gcNurseryEphemeronEdges();
- }
// Perform all pending weakmap entry marking for this zone after
// transitioning to weak marking mode.
@@ -977,8 +967,6 @@ class Zone : public js::ZoneAllocator, public js::gc::GraphNodeBase<JS::Zone> {
bool isQueuedForBackgroundSweep() { return isOnList(); }
- void sweepEphemeronTablesAfterMinorGC();
-
js::gc::FinalizationObservers* finalizationObservers() {
return finalizationObservers_.ref().get();
}