Chromium Code Reviews| 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 2793 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2804 Object** p) { | 2804 Object** p) { |
| 2805 MapWord map_word = HeapObject::cast(*p)->map_word(); | 2805 MapWord map_word = HeapObject::cast(*p)->map_word(); |
| 2806 | 2806 |
| 2807 if (map_word.IsForwardingAddress()) { | 2807 if (map_word.IsForwardingAddress()) { |
| 2808 return String::cast(map_word.ToForwardingAddress()); | 2808 return String::cast(map_word.ToForwardingAddress()); |
| 2809 } | 2809 } |
| 2810 | 2810 |
| 2811 return String::cast(*p); | 2811 return String::cast(*p); |
| 2812 } | 2812 } |
| 2813 | 2813 |
| 2814 | 2814 bool MarkCompactCollector::IsSlotInBlackObject(MemoryChunk* p, Address slot) { |
| 2815 bool MarkCompactCollector::IsSlotInBlackObject(Page* p, Address slot, | |
| 2816 HeapObject** out_object) { | |
| 2817 Space* owner = p->owner(); | 2815 Space* owner = p->owner(); |
| 2818 if (owner == heap_->lo_space() || owner == NULL) { | 2816 DCHECK(owner != heap_->lo_space() && owner != nullptr); |
| 2819 Object* large_object = heap_->lo_space()->FindObject(slot); | |
| 2820 // This object has to exist, otherwise we would not have recorded a slot | |
| 2821 // for it. | |
| 2822 CHECK(large_object->IsHeapObject()); | |
| 2823 HeapObject* large_heap_object = HeapObject::cast(large_object); | |
| 2824 if (IsMarked(large_heap_object)) { | |
| 2825 *out_object = large_heap_object; | |
| 2826 return true; | |
| 2827 } | |
| 2828 return false; | |
| 2829 } | |
| 2830 | 2817 |
| 2831 // If we are on a black page, we cannot find the actual object start | 2818 // If we are on a black page, we cannot find the actual object start |
| 2832 // easiliy. We just return true but do not set the out_object. | 2819 // easiliy. We just return true but do not set the out_object. |
| 2833 if (p->IsFlagSet(Page::BLACK_PAGE)) { | 2820 if (p->IsFlagSet(Page::BLACK_PAGE)) { |
| 2834 return true; | 2821 return true; |
| 2835 } | 2822 } |
| 2836 | 2823 |
| 2837 uint32_t mark_bit_index = p->AddressToMarkbitIndex(slot); | 2824 uint32_t mark_bit_index = p->AddressToMarkbitIndex(slot); |
| 2838 unsigned int cell_index = mark_bit_index >> Bitmap::kBitsPerCellLog2; | 2825 unsigned int cell_index = mark_bit_index >> Bitmap::kBitsPerCellLog2; |
| 2839 MarkBit::CellType index_mask = 1u << Bitmap::IndexInCell(mark_bit_index); | 2826 MarkBit::CellType index_mask = 1u << Bitmap::IndexInCell(mark_bit_index); |
| (...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2899 Address address = base_address + offset * kPointerSize; | 2886 Address address = base_address + offset * kPointerSize; |
| 2900 HeapObject* object = HeapObject::FromAddress(address); | 2887 HeapObject* object = HeapObject::FromAddress(address); |
| 2901 CHECK(Marking::IsBlack(Marking::MarkBitFrom(object))); | 2888 CHECK(Marking::IsBlack(Marking::MarkBitFrom(object))); |
| 2902 CHECK(object->address() < reinterpret_cast<Address>(slot)); | 2889 CHECK(object->address() < reinterpret_cast<Address>(slot)); |
| 2903 if ((object->address() + kPointerSize) <= slot && | 2890 if ((object->address() + kPointerSize) <= slot && |
| 2904 (object->address() + object->Size()) > slot) { | 2891 (object->address() + object->Size()) > slot) { |
| 2905 // If the slot is within the last found object in the cell, the slot is | 2892 // If the slot is within the last found object in the cell, the slot is |
| 2906 // in a live object. | 2893 // in a live object. |
| 2907 // Slots pointing to the first word of an object are invalid and removed. | 2894 // Slots pointing to the first word of an object are invalid and removed. |
| 2908 // This can happen when we move the object header while left trimming. | 2895 // This can happen when we move the object header while left trimming. |
| 2909 *out_object = object; | |
| 2910 return true; | 2896 return true; |
| 2911 } | 2897 } |
| 2912 return false; | 2898 return false; |
| 2913 } | 2899 } |
| 2914 | 2900 |
| 2915 HeapObject* MarkCompactCollector::FindBlackObjectBySlotSlow(Address slot) { | 2901 HeapObject* MarkCompactCollector::FindBlackObjectBySlotSlow(Address slot) { |
| 2916 Page* p = Page::FromAddress(slot); | 2902 Page* p = Page::FromAddress(slot); |
| 2917 Space* owner = p->owner(); | 2903 Space* owner = p->owner(); |
| 2918 if (owner == heap_->lo_space() || owner == nullptr) { | 2904 if (owner == heap_->lo_space() || owner == nullptr) { |
| 2919 Object* large_object = heap_->lo_space()->FindObject(slot); | 2905 Object* large_object = heap_->lo_space()->FindObject(slot); |
| (...skipping 26 matching lines...) Expand all Loading... | |
| 2946 if (object->address() > slot) return nullptr; | 2932 if (object->address() > slot) return nullptr; |
| 2947 if (object->address() <= slot && slot < (object->address() + size)) { | 2933 if (object->address() <= slot && slot < (object->address() + size)) { |
| 2948 return object; | 2934 return object; |
| 2949 } | 2935 } |
| 2950 } | 2936 } |
| 2951 } | 2937 } |
| 2952 return nullptr; | 2938 return nullptr; |
| 2953 } | 2939 } |
| 2954 | 2940 |
| 2955 | 2941 |
| 2956 bool MarkCompactCollector::IsSlotInLiveObject(Address slot) { | |
| 2957 // The target object is black but we don't know if the source slot is black. | |
| 2958 // The source object could have died and the slot could be part of a free | |
| 2959 // space. Find out based on mark bits if the slot is part of a live object. | |
| 2960 Page* page = Page::FromAddress(slot); | |
| 2961 HeapObject* object = NULL; | |
| 2962 if (!IsSlotInBlackObject(page, slot, &object)) { | |
| 2963 return false; | |
| 2964 } | |
| 2965 | |
| 2966 // If the slot is on a black page, the object will be live. | |
| 2967 DCHECK(object != NULL || page->IsFlagSet(Page::BLACK_PAGE)); | |
| 2968 if (page->IsFlagSet(Page::BLACK_PAGE)) { | |
| 2969 return true; | |
| 2970 } | |
| 2971 | |
| 2972 int offset = static_cast<int>(slot - object->address()); | |
| 2973 return object->IsValidSlot(offset); | |
|
ulan
2016/03/18 14:19:42
This is the main change.
| |
| 2974 } | |
| 2975 | |
| 2976 | |
| 2977 void MarkCompactCollector::EvacuateNewSpacePrologue() { | 2942 void MarkCompactCollector::EvacuateNewSpacePrologue() { |
| 2978 NewSpace* new_space = heap()->new_space(); | 2943 NewSpace* new_space = heap()->new_space(); |
| 2979 NewSpacePageIterator it(new_space->bottom(), new_space->top()); | 2944 NewSpacePageIterator it(new_space->bottom(), new_space->top()); |
| 2980 // Append the list of new space pages to be processed. | 2945 // Append the list of new space pages to be processed. |
| 2981 while (it.has_next()) { | 2946 while (it.has_next()) { |
| 2982 newspace_evacuation_candidates_.Add(it.next()); | 2947 newspace_evacuation_candidates_.Add(it.next()); |
| 2983 } | 2948 } |
| 2984 new_space->Flip(); | 2949 new_space->Flip(); |
| 2985 new_space->ResetAllocationInfo(); | 2950 new_space->ResetAllocationInfo(); |
| 2986 } | 2951 } |
| (...skipping 876 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3863 MarkBit mark_bit = Marking::MarkBitFrom(host); | 3828 MarkBit mark_bit = Marking::MarkBitFrom(host); |
| 3864 if (Marking::IsBlack(mark_bit)) { | 3829 if (Marking::IsBlack(mark_bit)) { |
| 3865 RelocInfo rinfo(isolate(), pc, RelocInfo::CODE_TARGET, 0, host); | 3830 RelocInfo rinfo(isolate(), pc, RelocInfo::CODE_TARGET, 0, host); |
| 3866 RecordRelocSlot(host, &rinfo, target); | 3831 RecordRelocSlot(host, &rinfo, target); |
| 3867 } | 3832 } |
| 3868 } | 3833 } |
| 3869 } | 3834 } |
| 3870 | 3835 |
| 3871 } // namespace internal | 3836 } // namespace internal |
| 3872 } // namespace v8 | 3837 } // namespace v8 |
| OLD | NEW |