OLD | NEW |
1 // Copyright 2009 the V8 project authors. All rights reserved. | 1 // Copyright 2009 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
97 // The snapshot semispace size will be the default semispace size if | 97 // The snapshot semispace size will be the default semispace size if |
98 // snapshotting is used and will be the requested semispace size as | 98 // snapshotting is used and will be the requested semispace size as |
99 // set up by ConfigureHeap otherwise. | 99 // set up by ConfigureHeap otherwise. |
100 int Heap::reserved_semispace_size_ = Heap::max_semispace_size_; | 100 int Heap::reserved_semispace_size_ = Heap::max_semispace_size_; |
101 | 101 |
102 List<Heap::GCPrologueCallbackPair> Heap::gc_prologue_callbacks_; | 102 List<Heap::GCPrologueCallbackPair> Heap::gc_prologue_callbacks_; |
103 List<Heap::GCEpilogueCallbackPair> Heap::gc_epilogue_callbacks_; | 103 List<Heap::GCEpilogueCallbackPair> Heap::gc_epilogue_callbacks_; |
104 | 104 |
105 GCCallback Heap::global_gc_prologue_callback_ = NULL; | 105 GCCallback Heap::global_gc_prologue_callback_ = NULL; |
106 GCCallback Heap::global_gc_epilogue_callback_ = NULL; | 106 GCCallback Heap::global_gc_epilogue_callback_ = NULL; |
| 107 HeapObjectCallback Heap::gc_safe_size_of_old_object_ = NULL; |
107 | 108 |
108 // Variables set based on semispace_size_ and old_generation_size_ in | 109 // Variables set based on semispace_size_ and old_generation_size_ in |
109 // ConfigureHeap. | 110 // ConfigureHeap. |
110 | 111 |
111 // Will be 4 * reserved_semispace_size_ to ensure that young | 112 // Will be 4 * reserved_semispace_size_ to ensure that young |
112 // generation can be aligned to its size. | 113 // generation can be aligned to its size. |
113 int Heap::survived_since_last_expansion_ = 0; | 114 int Heap::survived_since_last_expansion_ = 0; |
114 int Heap::external_allocation_limit_ = 0; | 115 int Heap::external_allocation_limit_ = 0; |
115 | 116 |
116 Heap::HeapState Heap::gc_state_ = NOT_IN_GC; | 117 Heap::HeapState Heap::gc_state_ = NOT_IN_GC; |
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
186 bool Heap::HasBeenSetup() { | 187 bool Heap::HasBeenSetup() { |
187 return old_pointer_space_ != NULL && | 188 return old_pointer_space_ != NULL && |
188 old_data_space_ != NULL && | 189 old_data_space_ != NULL && |
189 code_space_ != NULL && | 190 code_space_ != NULL && |
190 map_space_ != NULL && | 191 map_space_ != NULL && |
191 cell_space_ != NULL && | 192 cell_space_ != NULL && |
192 lo_space_ != NULL; | 193 lo_space_ != NULL; |
193 } | 194 } |
194 | 195 |
195 | 196 |
| 197 int Heap::GcSafeSizeOfOldObject(HeapObject* object) { |
| 198 ASSERT(!Heap::InNewSpace(object)); // Code only works for old objects. |
| 199 ASSERT(!MarkCompactCollector::are_map_pointers_encoded()); |
| 200 MapWord map_word = object->map_word(); |
| 201 map_word.ClearMark(); |
| 202 map_word.ClearOverflow(); |
| 203 return object->SizeFromMap(map_word.ToMap()); |
| 204 } |
| 205 |
| 206 |
| 207 int Heap::GcSafeSizeOfOldObjectWithEncodedMap(HeapObject* object) { |
| 208 ASSERT(!Heap::InNewSpace(object)); // Code only works for old objects. |
| 209 ASSERT(MarkCompactCollector::are_map_pointers_encoded()); |
| 210 uint32_t marker = Memory::uint32_at(object->address()); |
| 211 if (marker == MarkCompactCollector::kSingleFreeEncoding) { |
| 212 return kIntSize; |
| 213 } else if (marker == MarkCompactCollector::kMultiFreeEncoding) { |
| 214 return Memory::int_at(object->address() + kIntSize); |
| 215 } else { |
| 216 MapWord map_word = object->map_word(); |
| 217 Address map_address = map_word.DecodeMapAddress(Heap::map_space()); |
| 218 Map* map = reinterpret_cast<Map*>(HeapObject::FromAddress(map_address)); |
| 219 return object->SizeFromMap(map); |
| 220 } |
| 221 } |
| 222 |
| 223 |
196 GarbageCollector Heap::SelectGarbageCollector(AllocationSpace space) { | 224 GarbageCollector Heap::SelectGarbageCollector(AllocationSpace space) { |
197 // Is global GC requested? | 225 // Is global GC requested? |
198 if (space != NEW_SPACE || FLAG_gc_global) { | 226 if (space != NEW_SPACE || FLAG_gc_global) { |
199 Counters::gc_compactor_caused_by_request.Increment(); | 227 Counters::gc_compactor_caused_by_request.Increment(); |
200 return MARK_COMPACTOR; | 228 return MARK_COMPACTOR; |
201 } | 229 } |
202 | 230 |
203 // Is enough data promoted to justify a global GC? | 231 // Is enough data promoted to justify a global GC? |
204 if (OldGenerationPromotionLimitReached()) { | 232 if (OldGenerationPromotionLimitReached()) { |
205 Counters::gc_compactor_caused_by_promoted_data.Increment(); | 233 Counters::gc_compactor_caused_by_promoted_data.Increment(); |
(...skipping 529 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
735 mc_count_++; | 763 mc_count_++; |
736 } else { | 764 } else { |
737 ms_count_++; | 765 ms_count_++; |
738 } | 766 } |
739 tracer->set_full_gc_count(mc_count_ + ms_count_); | 767 tracer->set_full_gc_count(mc_count_ + ms_count_); |
740 | 768 |
741 MarkCompactPrologue(is_compacting); | 769 MarkCompactPrologue(is_compacting); |
742 | 770 |
743 MarkCompactCollector::CollectGarbage(); | 771 MarkCompactCollector::CollectGarbage(); |
744 | 772 |
745 MarkCompactEpilogue(is_compacting); | |
746 | |
747 LOG(ResourceEvent("markcompact", "end")); | 773 LOG(ResourceEvent("markcompact", "end")); |
748 | 774 |
749 gc_state_ = NOT_IN_GC; | 775 gc_state_ = NOT_IN_GC; |
750 | 776 |
751 Shrink(); | 777 Shrink(); |
752 | 778 |
753 Counters::objs_since_last_full.Set(0); | 779 Counters::objs_since_last_full.Set(0); |
754 | 780 |
755 contexts_disposed_ = 0; | 781 contexts_disposed_ = 0; |
756 } | 782 } |
757 | 783 |
758 | 784 |
759 void Heap::MarkCompactPrologue(bool is_compacting) { | 785 void Heap::MarkCompactPrologue(bool is_compacting) { |
760 // At any old GC clear the keyed lookup cache to enable collection of unused | 786 // At any old GC clear the keyed lookup cache to enable collection of unused |
761 // maps. | 787 // maps. |
762 KeyedLookupCache::Clear(); | 788 KeyedLookupCache::Clear(); |
763 ContextSlotCache::Clear(); | 789 ContextSlotCache::Clear(); |
764 DescriptorLookupCache::Clear(); | 790 DescriptorLookupCache::Clear(); |
765 | 791 |
766 CompilationCache::MarkCompactPrologue(); | 792 CompilationCache::MarkCompactPrologue(); |
767 | 793 |
768 Top::MarkCompactPrologue(is_compacting); | |
769 ThreadManager::MarkCompactPrologue(is_compacting); | |
770 | |
771 CompletelyClearInstanceofCache(); | 794 CompletelyClearInstanceofCache(); |
772 | 795 |
773 if (is_compacting) FlushNumberStringCache(); | 796 if (is_compacting) FlushNumberStringCache(); |
774 | 797 |
775 ClearNormalizedMapCaches(); | 798 ClearNormalizedMapCaches(); |
776 } | 799 } |
777 | 800 |
778 | 801 |
779 void Heap::MarkCompactEpilogue(bool is_compacting) { | |
780 Top::MarkCompactEpilogue(is_compacting); | |
781 ThreadManager::MarkCompactEpilogue(is_compacting); | |
782 } | |
783 | |
784 | |
785 Object* Heap::FindCodeObject(Address a) { | 802 Object* Heap::FindCodeObject(Address a) { |
786 Object* obj = code_space_->FindObject(a); | 803 Object* obj = code_space_->FindObject(a); |
787 if (obj->IsFailure()) { | 804 if (obj->IsFailure()) { |
788 obj = lo_space_->FindObject(a); | 805 obj = lo_space_->FindObject(a); |
789 } | 806 } |
790 ASSERT(!obj->IsFailure()); | 807 ASSERT(!obj->IsFailure()); |
791 return obj; | 808 return obj; |
792 } | 809 } |
793 | 810 |
794 | 811 |
(...skipping 3247 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4042 // size) and old-space-size if set or the initial values of semispace_size_ | 4059 // size) and old-space-size if set or the initial values of semispace_size_ |
4043 // and old_generation_size_ otherwise. | 4060 // and old_generation_size_ otherwise. |
4044 if (!heap_configured) { | 4061 if (!heap_configured) { |
4045 if (!ConfigureHeapDefault()) return false; | 4062 if (!ConfigureHeapDefault()) return false; |
4046 } | 4063 } |
4047 | 4064 |
4048 ScavengingVisitor::Initialize(); | 4065 ScavengingVisitor::Initialize(); |
4049 NewSpaceScavenger::Initialize(); | 4066 NewSpaceScavenger::Initialize(); |
4050 MarkCompactCollector::Initialize(); | 4067 MarkCompactCollector::Initialize(); |
4051 | 4068 |
| 4069 MarkMapPointersAsEncoded(false); |
| 4070 |
4052 // Setup memory allocator and reserve a chunk of memory for new | 4071 // Setup memory allocator and reserve a chunk of memory for new |
4053 // space. The chunk is double the size of the requested reserved | 4072 // space. The chunk is double the size of the requested reserved |
4054 // new space size to ensure that we can find a pair of semispaces that | 4073 // new space size to ensure that we can find a pair of semispaces that |
4055 // are contiguous and aligned to their size. | 4074 // are contiguous and aligned to their size. |
4056 if (!MemoryAllocator::Setup(MaxReserved())) return false; | 4075 if (!MemoryAllocator::Setup(MaxReserved())) return false; |
4057 void* chunk = | 4076 void* chunk = |
4058 MemoryAllocator::ReserveInitialChunk(4 * reserved_semispace_size_); | 4077 MemoryAllocator::ReserveInitialChunk(4 * reserved_semispace_size_); |
4059 if (chunk == NULL) return false; | 4078 if (chunk == NULL) return false; |
4060 | 4079 |
4061 // Align the pair of semispaces to their size, which must be a power | 4080 // Align the pair of semispaces to their size, which must be a power |
(...skipping 815 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4877 void ExternalStringTable::TearDown() { | 4896 void ExternalStringTable::TearDown() { |
4878 new_space_strings_.Free(); | 4897 new_space_strings_.Free(); |
4879 old_space_strings_.Free(); | 4898 old_space_strings_.Free(); |
4880 } | 4899 } |
4881 | 4900 |
4882 | 4901 |
4883 List<Object*> ExternalStringTable::new_space_strings_; | 4902 List<Object*> ExternalStringTable::new_space_strings_; |
4884 List<Object*> ExternalStringTable::old_space_strings_; | 4903 List<Object*> ExternalStringTable::old_space_strings_; |
4885 | 4904 |
4886 } } // namespace v8::internal | 4905 } } // namespace v8::internal |
OLD | NEW |