@@ -4800,6 +4800,49 @@ void Heap::IterateSmiRoots(ObjectVisitor* v) {
48004800 v->Synchronize (VisitorSynchronization::kSmiRootList );
48014801}
48024802
4803+ // We cannot avoid stale handles to left-trimmed objects, but can only make
4804+ // sure all handles still needed are updated. Filter out a stale pointer
4805+ // and clear the slot to allow post processing of handles (needed because
4806+ // the sweeper might actually free the underlying page).
4807+ class FixStaleLeftTrimmedHandlesVisitor : public ObjectVisitor {
4808+ public:
4809+ explicit FixStaleLeftTrimmedHandlesVisitor (Heap* heap) : heap_(heap) {
4810+ USE (heap_);
4811+ }
4812+
4813+ void VisitPointer (Object** p) override { FixHandle (p); }
4814+
4815+ void VisitPointers (Object** start, Object** end) override {
4816+ for (Object** p = start; p < end; p++) FixHandle (p);
4817+ }
4818+
4819+ private:
4820+ inline void FixHandle (Object** p) {
4821+ HeapObject* current = reinterpret_cast <HeapObject*>(*p);
4822+ if (!current->IsHeapObject ()) return ;
4823+ const MapWord map_word = current->map_word ();
4824+ if (!map_word.IsForwardingAddress () && current->IsFiller ()) {
4825+ #ifdef DEBUG
4826+ // We need to find a FixedArrayBase map after walking the fillers.
4827+ while (current->IsFiller ()) {
4828+ Address next = reinterpret_cast <Address>(current);
4829+ if (current->map () == heap_->one_pointer_filler_map ()) {
4830+ next += kPointerSize ;
4831+ } else if (current->map () == heap_->two_pointer_filler_map ()) {
4832+ next += 2 * kPointerSize ;
4833+ } else {
4834+ next += current->Size ();
4835+ }
4836+ current = reinterpret_cast <HeapObject*>(next);
4837+ }
4838+ DCHECK (current->IsFixedArrayBase ());
4839+ #endif // DEBUG
4840+ *p = nullptr ;
4841+ }
4842+ }
4843+
4844+ Heap* heap_;
4845+ };
48034846
48044847void Heap::IterateStrongRoots (ObjectVisitor* v, VisitMode mode) {
48054848 v->VisitPointers (&roots_[0 ], &roots_[kStrongRootListLength ]);
@@ -4820,6 +4863,8 @@ void Heap::IterateStrongRoots(ObjectVisitor* v, VisitMode mode) {
48204863 v->Synchronize (VisitorSynchronization::kCompilationCache );
48214864
48224865 // Iterate over local handles in handle scopes.
4866+ FixStaleLeftTrimmedHandlesVisitor left_trim_visitor (this );
4867+ isolate_->handle_scope_implementer ()->Iterate (&left_trim_visitor);
48234868 isolate_->handle_scope_implementer ()->Iterate (v);
48244869 isolate_->IterateDeferredHandles (v);
48254870 v->Synchronize (VisitorSynchronization::kHandleScope );
0 commit comments