OLD | NEW |
---|---|
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "src/heap/mark-compact.h" | 5 #include "src/heap/mark-compact.h" |
6 | 6 |
7 #include "src/base/atomicops.h" | 7 #include "src/base/atomicops.h" |
8 #include "src/base/bits.h" | 8 #include "src/base/bits.h" |
9 #include "src/base/sys-info.h" | 9 #include "src/base/sys-info.h" |
10 #include "src/code-stubs.h" | 10 #include "src/code-stubs.h" |
(...skipping 2863 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2874 void MarkCompactCollector::UpdateSlotsRecordedIn(SlotsBuffer* buffer) { | 2874 void MarkCompactCollector::UpdateSlotsRecordedIn(SlotsBuffer* buffer) { |
2875 while (buffer != NULL) { | 2875 while (buffer != NULL) { |
2876 UpdateSlots(buffer); | 2876 UpdateSlots(buffer); |
2877 buffer = buffer->next(); | 2877 buffer = buffer->next(); |
2878 } | 2878 } |
2879 } | 2879 } |
2880 | 2880 |
2881 | 2881 |
2882 static void UpdatePointer(HeapObject** address, HeapObject* object) { | 2882 static void UpdatePointer(HeapObject** address, HeapObject* object) { |
2883 MapWord map_word = object->map_word(); | 2883 MapWord map_word = object->map_word(); |
2884 // The store buffer can still contain stale pointers in dead large objects. | 2884 // The store buffer can still contain stale pointers in large object |
2885 // or in map spaces. | |
Hannes Payer (out of office)
2016/01/20 19:43:00
Why map space?
ulan
2016/01/28 19:07:22
Clarified the comment.
Since we only filter invali
| |
2885 // Ignore these pointers here. | 2886 // Ignore these pointers here. |
2886 DCHECK(map_word.IsForwardingAddress() || | 2887 DCHECK(map_word.IsForwardingAddress() || |
2887 object->GetHeap()->lo_space()->FindPage( | 2888 !object->GetHeap()->old_space()->Contains( |
2888 reinterpret_cast<Address>(address)) != NULL); | 2889 reinterpret_cast<Address>(address))); |
2889 if (map_word.IsForwardingAddress()) { | 2890 if (map_word.IsForwardingAddress()) { |
2890 // Update the corresponding slot. | 2891 // Update the corresponding slot. |
2891 *address = map_word.ToForwardingAddress(); | 2892 *address = map_word.ToForwardingAddress(); |
2892 } | 2893 } |
2893 } | 2894 } |
2894 | 2895 |
2895 | 2896 |
2896 static String* UpdateReferenceInExternalStringTableEntry(Heap* heap, | 2897 static String* UpdateReferenceInExternalStringTableEntry(Heap* heap, |
2897 Object** p) { | 2898 Object** p) { |
2898 MapWord map_word = HeapObject::cast(*p)->map_word(); | 2899 MapWord map_word = HeapObject::cast(*p)->map_word(); |
(...skipping 312 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3211 // - Rescan the page as slot recording in the migration buffer only | 3212 // - Rescan the page as slot recording in the migration buffer only |
3212 // happens upon moving (which we potentially didn't do). | 3213 // happens upon moving (which we potentially didn't do). |
3213 // - Leave the page in the list of pages of a space since we could not | 3214 // - Leave the page in the list of pages of a space since we could not |
3214 // fully evacuate it. | 3215 // fully evacuate it. |
3215 // - Mark them for rescanning for store buffer entries as we otherwise | 3216 // - Mark them for rescanning for store buffer entries as we otherwise |
3216 // might have stale store buffer entries that become "valid" again | 3217 // might have stale store buffer entries that become "valid" again |
3217 // after reusing the memory. Note that all existing store buffer | 3218 // after reusing the memory. Note that all existing store buffer |
3218 // entries of such pages are filtered before rescanning. | 3219 // entries of such pages are filtered before rescanning. |
3219 DCHECK(p->IsEvacuationCandidate()); | 3220 DCHECK(p->IsEvacuationCandidate()); |
3220 p->SetFlag(Page::COMPACTION_WAS_ABORTED); | 3221 p->SetFlag(Page::COMPACTION_WAS_ABORTED); |
3221 p->set_scan_on_scavenge(true); | |
3222 abandoned_pages++; | 3222 abandoned_pages++; |
3223 break; | 3223 break; |
3224 case MemoryChunk::kCompactingFinalize: | 3224 case MemoryChunk::kCompactingFinalize: |
3225 DCHECK(p->IsEvacuationCandidate()); | 3225 DCHECK(p->IsEvacuationCandidate()); |
3226 p->SetWasSwept(); | 3226 p->SetWasSwept(); |
3227 p->Unlink(); | 3227 p->Unlink(); |
3228 break; | 3228 break; |
3229 case MemoryChunk::kCompactingDone: | 3229 case MemoryChunk::kCompactingDone: |
3230 DCHECK(p->IsFlagSet(Page::POPULAR_PAGE)); | 3230 DCHECK(p->IsFlagSet(Page::POPULAR_PAGE)); |
3231 DCHECK(p->IsFlagSet(Page::RESCAN_ON_EVACUATION)); | 3231 DCHECK(p->IsFlagSet(Page::RESCAN_ON_EVACUATION)); |
(...skipping 269 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3501 | 3501 |
3502 LiveObjectIterator<kBlackObjects> it(page); | 3502 LiveObjectIterator<kBlackObjects> it(page); |
3503 HeapObject* object = nullptr; | 3503 HeapObject* object = nullptr; |
3504 while ((object = it.Next()) != nullptr) { | 3504 while ((object = it.Next()) != nullptr) { |
3505 DCHECK(Marking::IsBlack(Marking::MarkBitFrom(object))); | 3505 DCHECK(Marking::IsBlack(Marking::MarkBitFrom(object))); |
3506 if (!visitor->Visit(object)) { | 3506 if (!visitor->Visit(object)) { |
3507 if (mode == kClearMarkbits) { | 3507 if (mode == kClearMarkbits) { |
3508 page->markbits()->ClearRange( | 3508 page->markbits()->ClearRange( |
3509 page->AddressToMarkbitIndex(page->area_start()), | 3509 page->AddressToMarkbitIndex(page->area_start()), |
3510 page->AddressToMarkbitIndex(object->address())); | 3510 page->AddressToMarkbitIndex(object->address())); |
3511 if (page->old_to_new_slots() != nullptr) { | |
3512 page->old_to_new_slots()->RemoveRange( | |
3513 0, static_cast<int>(object->address() - page->address())); | |
3514 } | |
3511 RecomputeLiveBytes(page); | 3515 RecomputeLiveBytes(page); |
3512 } | 3516 } |
3513 return false; | 3517 return false; |
3514 } | 3518 } |
3515 } | 3519 } |
3516 if (mode == kClearMarkbits) { | 3520 if (mode == kClearMarkbits) { |
3517 Bitmap::Clear(page); | 3521 Bitmap::Clear(page); |
3518 } | 3522 } |
3519 return true; | 3523 return true; |
3520 } | 3524 } |
(...skipping 145 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3666 SemiSpaceIterator to_it(heap()->new_space()); | 3670 SemiSpaceIterator to_it(heap()->new_space()); |
3667 for (HeapObject* object = to_it.Next(); object != NULL; | 3671 for (HeapObject* object = to_it.Next(); object != NULL; |
3668 object = to_it.Next()) { | 3672 object = to_it.Next()) { |
3669 Map* map = object->map(); | 3673 Map* map = object->map(); |
3670 object->IterateBody(map->instance_type(), object->SizeFromMap(map), | 3674 object->IterateBody(map->instance_type(), object->SizeFromMap(map), |
3671 &updating_visitor); | 3675 &updating_visitor); |
3672 } | 3676 } |
3673 // Update roots. | 3677 // Update roots. |
3674 heap_->IterateRoots(&updating_visitor, VISIT_ALL_IN_SWEEP_NEWSPACE); | 3678 heap_->IterateRoots(&updating_visitor, VISIT_ALL_IN_SWEEP_NEWSPACE); |
3675 | 3679 |
3676 StoreBufferRebuildScope scope(heap_, heap_->store_buffer(), | |
3677 &Heap::ScavengeStoreBufferCallback); | |
3678 heap_->store_buffer()->IteratePointersToNewSpace(&UpdatePointer); | 3680 heap_->store_buffer()->IteratePointersToNewSpace(&UpdatePointer); |
3679 } | 3681 } |
3680 | 3682 |
3681 int npages = evacuation_candidates_.length(); | 3683 int npages = evacuation_candidates_.length(); |
3682 { | 3684 { |
3683 GCTracer::Scope gc_scope( | 3685 GCTracer::Scope gc_scope( |
3684 heap()->tracer(), | 3686 heap()->tracer(), |
3685 GCTracer::Scope::MC_EVACUATE_UPDATE_POINTERS_BETWEEN_EVACUATED); | 3687 GCTracer::Scope::MC_EVACUATE_UPDATE_POINTERS_BETWEEN_EVACUATED); |
3686 for (int i = 0; i < npages; i++) { | 3688 for (int i = 0; i < npages; i++) { |
3687 Page* p = evacuation_candidates_[i]; | 3689 Page* p = evacuation_candidates_[i]; |
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3769 } | 3771 } |
3770 | 3772 |
3771 | 3773 |
3772 void MarkCompactCollector::ReleaseEvacuationCandidates() { | 3774 void MarkCompactCollector::ReleaseEvacuationCandidates() { |
3773 int npages = evacuation_candidates_.length(); | 3775 int npages = evacuation_candidates_.length(); |
3774 for (int i = 0; i < npages; i++) { | 3776 for (int i = 0; i < npages; i++) { |
3775 Page* p = evacuation_candidates_[i]; | 3777 Page* p = evacuation_candidates_[i]; |
3776 if (!p->IsEvacuationCandidate()) continue; | 3778 if (!p->IsEvacuationCandidate()) continue; |
3777 PagedSpace* space = static_cast<PagedSpace*>(p->owner()); | 3779 PagedSpace* space = static_cast<PagedSpace*>(p->owner()); |
3778 space->Free(p->area_start(), p->area_size()); | 3780 space->Free(p->area_start(), p->area_size()); |
3779 p->set_scan_on_scavenge(false); | |
3780 p->ResetLiveBytes(); | 3781 p->ResetLiveBytes(); |
3781 CHECK(p->WasSwept()); | 3782 CHECK(p->WasSwept()); |
3782 space->ReleasePage(p); | 3783 space->ReleasePage(p); |
3783 } | 3784 } |
3784 evacuation_candidates_.Rewind(0); | 3785 evacuation_candidates_.Rewind(0); |
3785 compacting_ = false; | 3786 compacting_ = false; |
3786 heap()->FilterStoreBufferEntriesOnAboutToBeFreedPages(); | 3787 heap()->FilterStoreBufferEntriesOnAboutToBeFreedPages(); |
3787 heap()->FreeQueuedChunks(); | 3788 heap()->FreeQueuedChunks(); |
3788 } | 3789 } |
3789 | 3790 |
(...skipping 274 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4064 MarkBit mark_bit = Marking::MarkBitFrom(host); | 4065 MarkBit mark_bit = Marking::MarkBitFrom(host); |
4065 if (Marking::IsBlack(mark_bit)) { | 4066 if (Marking::IsBlack(mark_bit)) { |
4066 RelocInfo rinfo(isolate(), pc, RelocInfo::CODE_TARGET, 0, host); | 4067 RelocInfo rinfo(isolate(), pc, RelocInfo::CODE_TARGET, 0, host); |
4067 RecordRelocSlot(&rinfo, target); | 4068 RecordRelocSlot(&rinfo, target); |
4068 } | 4069 } |
4069 } | 4070 } |
4070 } | 4071 } |
4071 | 4072 |
4072 } // namespace internal | 4073 } // namespace internal |
4073 } // namespace v8 | 4074 } // namespace v8 |
OLD | NEW |