Commit 3fc2c275 authored by Michael Lippautz's avatar Michael Lippautz Committed by Commit Bot

[heap] MinorMC: Fix page promotion during incremental marking

During incremental marking we need to clear to old generation
mark bits for promoted pages.

Bug: chromium:651354
Change-Id: I986de08d6a123b2eff3dd7824729cc1cfe29aeba
Reviewed-on: https://chromium-review.googlesource.com/522665Reviewed-by: 's avatarHannes Payer <hpayer@chromium.org>
Commit-Queue: Michael Lippautz <mlippautz@chromium.org>
Cr-Commit-Position: refs/heads/master@{#45683}
parent 7b7a7164
......@@ -1532,6 +1532,8 @@ class RecordMigratedSlotVisitor : public ObjectVisitor {
if (value->IsHeapObject()) {
Page* p = Page::FromAddress(reinterpret_cast<Address>(value));
if (p->InNewSpace()) {
DCHECK_IMPLIES(p->InToSpace(),
p->IsFlagSet(Page::PAGE_NEW_NEW_PROMOTION));
RememberedSet<OLD_TO_NEW>::Insert(Page::FromAddress(slot), slot);
} else if (p->IsEvacuationCandidate()) {
RememberedSet<OLD_TO_OLD>::Insert(Page::FromAddress(slot), slot);
......@@ -1630,6 +1632,8 @@ class YoungGenerationRecordMigratedSlotVisitor final
if (value->IsHeapObject()) {
Page* p = Page::FromAddress(reinterpret_cast<Address>(value));
if (p->InNewSpace()) {
DCHECK_IMPLIES(p->InToSpace(),
p->IsFlagSet(Page::PAGE_NEW_NEW_PROMOTION));
RememberedSet<OLD_TO_NEW>::Insert(Page::FromAddress(slot), slot);
} else if (p->IsEvacuationCandidate() && IsLive(host)) {
RememberedSet<OLD_TO_OLD>::Insert(Page::FromAddress(slot), slot);
......@@ -1918,6 +1922,7 @@ class EvacuateNewSpacePageVisitor final : public HeapObjectVisitor {
case NEW_TO_OLD: {
page->Unlink();
Page* new_page = Page::ConvertNewToOld(page);
DCHECK(!new_page->InNewSpace());
new_page->SetFlag(Page::PAGE_NEW_OLD_PROMOTION);
break;
}
......@@ -2767,11 +2772,11 @@ void MinorMarkCompactCollector::MakeIterable(
if (free_end != free_start) {
CHECK_GT(free_end, free_start);
size_t size = static_cast<size_t>(free_end - free_start);
full_collector->marking_state(p).bitmap()->ClearRange(
p->AddressToMarkbitIndex(free_start),
p->AddressToMarkbitIndex(free_end));
if (free_space_mode == ZAP_FREE_SPACE) {
memset(free_start, 0xcc, size);
full_collector->marking_state(p).bitmap()->ClearRange(
p->AddressToMarkbitIndex(free_start),
p->AddressToMarkbitIndex(free_end));
}
p->heap()->CreateFillerObjectAt(free_start, static_cast<int>(size),
ClearRecordedSlots::kNo);
......@@ -2784,11 +2789,11 @@ void MinorMarkCompactCollector::MakeIterable(
if (free_start != p->area_end()) {
CHECK_GT(p->area_end(), free_start);
size_t size = static_cast<size_t>(p->area_end() - free_start);
full_collector->marking_state(p).bitmap()->ClearRange(
p->AddressToMarkbitIndex(free_start),
p->AddressToMarkbitIndex(p->area_end()));
if (free_space_mode == ZAP_FREE_SPACE) {
memset(free_start, 0xcc, size);
full_collector->marking_state(p).bitmap()->ClearRange(
p->AddressToMarkbitIndex(free_start),
p->AddressToMarkbitIndex(p->area_end()));
}
p->heap()->CreateFillerObjectAt(free_start, static_cast<int>(size),
ClearRecordedSlots::kNo);
......@@ -3754,9 +3759,16 @@ bool YoungGenerationEvacuator::RawEvacuatePage(Page* page,
// TODO(mlippautz): If cleaning array buffers is too slow here we can
// delay it until the next GC.
ArrayBufferTracker::FreeDead(page, state);
if (heap()->ShouldZapGarbage())
if (heap()->ShouldZapGarbage()) {
collector_->MakeIterable(page, MarkingTreatmentMode::KEEP,
ZAP_FREE_SPACE);
} else if (heap()->incremental_marking()->IsMarking()) {
// When incremental marking is on, we need to clear the mark bits of
// the full collector. Make the page completely iterable and clear also
// the young generation mark bits in the case.
collector_->MakeIterable(page, MarkingTreatmentMode::CLEAR,
IGNORE_FREE_SPACE);
}
break;
case kPageNewToNew:
success = object_visitor.VisitGreyObjectsNoFail(
......@@ -3767,9 +3779,16 @@ bool YoungGenerationEvacuator::RawEvacuatePage(Page* page,
// TODO(mlippautz): If cleaning array buffers is too slow here we can
// delay it until the next GC.
ArrayBufferTracker::FreeDead(page, state);
if (heap()->ShouldZapGarbage())
if (heap()->ShouldZapGarbage()) {
collector_->MakeIterable(page, MarkingTreatmentMode::KEEP,
ZAP_FREE_SPACE);
} else if (heap()->incremental_marking()->IsMarking()) {
// When incremental marking is on, we need to clear the mark bits of
// the full collector. Make the page completely iterable and clear also
// the young generation mark bits in the case.
collector_->MakeIterable(page, MarkingTreatmentMode::CLEAR,
IGNORE_FREE_SPACE);
}
break;
case kObjectsOldToOld:
UNREACHABLE();
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment