Skip to content

Commit 8606664

Browse files
hannespayerCommit bot
authored andcommitted
Filter out slot buffer slots, that point to SMIs in dead objects.
The following situation may happen which reproduces this bug: (1) We allocate JSObject A on an evacuation candidate. (2) We allocate JSObject B on a non-evacuation candidate. (3) Incremental marking starts and marks object A and B. (4) We create a reference from B.field = A; which records the slot B.field since A is on an evacuation candidate. (5) After that we write a SMI into B.field. (6) After that B goes into dictionary mode and shrinks its original size. B.field is now outside of the JSObject, i.e B.field is in memory that will be freed by the sweeper threads. (7) GC is triggered. (8) BUG: Slots buffer filtering walks over the slots buffer, SMIs are not filtered out because we assumed that SMIs are just ignored when the slots get updated later. However, recorded SMI slots of dead objects may be overwritten by double values at evacuation time. (9) During evacuation, a heap number that looks like a valid pointer is moved over B.field. (10) The slots buffer is scanned for updates, follows B.field since it looks like a pointer (the double value looks like a pointer), and crashes. BUG=chromium:519577,chromium:454297 LOG=y Review URL: https://codereview.chromium.org/1286343004 Cr-Commit-Position: refs/heads/master@{#30200}
1 parent 40f6e80 commit 8606664

1 file changed

Lines changed: 4 additions & 6 deletions

File tree

src/heap/mark-compact.cc

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4497,12 +4497,10 @@ void SlotsBuffer::RemoveInvalidSlots(Heap* heap, SlotsBuffer* buffer) {
44974497
ObjectSlot slot = slots[slot_idx];
44984498
if (!IsTypedSlot(slot)) {
44994499
Object* object = *slot;
4500-
if (object->IsHeapObject()) {
4501-
if (heap->InNewSpace(object) ||
4502-
!heap->mark_compact_collector()->IsSlotInLiveObject(
4503-
reinterpret_cast<Address>(slot))) {
4504-
slots[slot_idx] = kRemovedEntry;
4505-
}
4500+
if ((object->IsHeapObject() && heap->InNewSpace(object)) ||
4501+
!heap->mark_compact_collector()->IsSlotInLiveObject(
4502+
reinterpret_cast<Address>(slot))) {
4503+
slots[slot_idx] = kRemovedEntry;
45064504
}
45074505
} else {
45084506
++slot_idx;

0 commit comments

Comments
 (0)