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 2089 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2100 GCTracer::Scope gc_scope(heap()->tracer(), GCTracer::Scope::MC_MARK); | 2100 GCTracer::Scope gc_scope(heap()->tracer(), GCTracer::Scope::MC_MARK); |
2101 double start_time = 0.0; | 2101 double start_time = 0.0; |
2102 if (FLAG_print_cumulative_gc_stat) { | 2102 if (FLAG_print_cumulative_gc_stat) { |
2103 start_time = base::OS::TimeCurrentMillis(); | 2103 start_time = base::OS::TimeCurrentMillis(); |
2104 } | 2104 } |
2105 // The recursive GC marker detects when it is nearing stack overflow, | 2105 // The recursive GC marker detects when it is nearing stack overflow, |
2106 // and switches to a different marking system. JS interrupts interfere | 2106 // and switches to a different marking system. JS interrupts interfere |
2107 // with the C stack limit check. | 2107 // with the C stack limit check. |
2108 PostponeInterruptsScope postpone(isolate()); | 2108 PostponeInterruptsScope postpone(isolate()); |
2109 | 2109 |
2110 IncrementalMarking* incremental_marking = heap_->incremental_marking(); | 2110 { |
2111 if (was_marked_incrementally_) { | 2111 GCTracer::Scope gc_scope(heap()->tracer(), |
2112 incremental_marking->Finalize(); | 2112 GCTracer::Scope::MC_MARK_FINISH_INCREMENTAL); |
2113 } else { | 2113 IncrementalMarking* incremental_marking = heap_->incremental_marking(); |
2114 // Abort any pending incremental activities e.g. incremental sweeping. | 2114 if (was_marked_incrementally_) { |
2115 incremental_marking->Stop(); | 2115 incremental_marking->Finalize(); |
2116 if (marking_deque_.in_use()) { | 2116 } else { |
2117 marking_deque_.Uninitialize(true); | 2117 // Abort any pending incremental activities e.g. incremental sweeping. |
| 2118 incremental_marking->Stop(); |
| 2119 if (marking_deque_.in_use()) { |
| 2120 marking_deque_.Uninitialize(true); |
| 2121 } |
2118 } | 2122 } |
2119 } | 2123 } |
2120 | 2124 |
2121 #ifdef DEBUG | 2125 #ifdef DEBUG |
2122 DCHECK(state_ == PREPARE_GC); | 2126 DCHECK(state_ == PREPARE_GC); |
2123 state_ = MARK_LIVE_OBJECTS; | 2127 state_ = MARK_LIVE_OBJECTS; |
2124 #endif | 2128 #endif |
2125 | 2129 |
2126 EnsureMarkingDequeIsCommittedAndInitialize( | 2130 EnsureMarkingDequeIsCommittedAndInitialize( |
2127 MarkCompactCollector::kMaxMarkingDequeSize); | 2131 MarkCompactCollector::kMaxMarkingDequeSize); |
2128 | 2132 |
2129 PrepareForCodeFlushing(); | 2133 { |
| 2134 GCTracer::Scope gc_scope(heap()->tracer(), |
| 2135 GCTracer::Scope::MC_MARK_PREPARE_CODE_FLUSH); |
| 2136 PrepareForCodeFlushing(); |
| 2137 } |
2130 | 2138 |
2131 RootMarkingVisitor root_visitor(heap()); | 2139 RootMarkingVisitor root_visitor(heap()); |
2132 MarkRoots(&root_visitor); | |
2133 | 2140 |
2134 ProcessTopOptimizedFrame(&root_visitor); | 2141 { |
| 2142 GCTracer::Scope gc_scope(heap()->tracer(), GCTracer::Scope::MC_MARK_ROOT); |
| 2143 MarkRoots(&root_visitor); |
| 2144 } |
| 2145 |
| 2146 { |
| 2147 GCTracer::Scope gc_scope(heap()->tracer(), GCTracer::Scope::MC_MARK_TOPOPT); |
| 2148 ProcessTopOptimizedFrame(&root_visitor); |
| 2149 } |
2135 | 2150 |
2136 // Retaining dying maps should happen before or during ephemeral marking | 2151 // Retaining dying maps should happen before or during ephemeral marking |
2137 // because a map could keep the key of an ephemeron alive. Note that map | 2152 // because a map could keep the key of an ephemeron alive. Note that map |
2138 // aging is imprecise: maps that are kept alive only by ephemerons will age. | 2153 // aging is imprecise: maps that are kept alive only by ephemerons will age. |
2139 RetainMaps(); | 2154 { |
| 2155 GCTracer::Scope gc_scope(heap()->tracer(), |
| 2156 GCTracer::Scope::MC_MARK_RETAIN_MAPS); |
| 2157 RetainMaps(); |
| 2158 } |
2140 | 2159 |
2141 { | 2160 { |
2142 GCTracer::Scope gc_scope(heap()->tracer(), GCTracer::Scope::MC_WEAKCLOSURE); | 2161 GCTracer::Scope gc_scope(heap()->tracer(), |
| 2162 GCTracer::Scope::MC_MARK_WEAK_CLOSURE); |
2143 | 2163 |
2144 // The objects reachable from the roots are marked, yet unreachable | 2164 // The objects reachable from the roots are marked, yet unreachable |
2145 // objects are unmarked. Mark objects reachable due to host | 2165 // objects are unmarked. Mark objects reachable due to host |
2146 // application specific logic or through Harmony weak maps. | 2166 // application specific logic or through Harmony weak maps. |
2147 ProcessEphemeralMarking(&root_visitor, false); | 2167 ProcessEphemeralMarking(&root_visitor, false); |
2148 | 2168 |
2149 // The objects reachable from the roots, weak maps or object groups | 2169 // The objects reachable from the roots, weak maps or object groups |
2150 // are marked. Objects pointed to only by weak global handles cannot be | 2170 // are marked. Objects pointed to only by weak global handles cannot be |
2151 // immediately reclaimed. Instead, we have to mark them as pending and mark | 2171 // immediately reclaimed. Instead, we have to mark them as pending and mark |
2152 // objects reachable from them. | 2172 // objects reachable from them. |
(...skipping 16 matching lines...) Expand all Loading... |
2169 | 2189 |
2170 AfterMarking(); | 2190 AfterMarking(); |
2171 | 2191 |
2172 if (FLAG_print_cumulative_gc_stat) { | 2192 if (FLAG_print_cumulative_gc_stat) { |
2173 heap_->tracer()->AddMarkingTime(base::OS::TimeCurrentMillis() - start_time); | 2193 heap_->tracer()->AddMarkingTime(base::OS::TimeCurrentMillis() - start_time); |
2174 } | 2194 } |
2175 } | 2195 } |
2176 | 2196 |
2177 | 2197 |
2178 void MarkCompactCollector::AfterMarking() { | 2198 void MarkCompactCollector::AfterMarking() { |
2179 // Prune the string table removing all strings only pointed to by the | 2199 { |
2180 // string table. Cannot use string_table() here because the string | 2200 GCTracer::Scope gc_scope(heap()->tracer(), |
2181 // table is marked. | 2201 GCTracer::Scope::MC_MARK_STRING_TABLE); |
2182 StringTable* string_table = heap()->string_table(); | |
2183 InternalizedStringTableCleaner internalized_visitor(heap()); | |
2184 string_table->IterateElements(&internalized_visitor); | |
2185 string_table->ElementsRemoved(internalized_visitor.PointersRemoved()); | |
2186 | 2202 |
2187 ExternalStringTableCleaner external_visitor(heap()); | 2203 // Prune the string table removing all strings only pointed to by the |
2188 heap()->external_string_table_.Iterate(&external_visitor); | 2204 // string table. Cannot use string_table() here because the string |
2189 heap()->external_string_table_.CleanUp(); | 2205 // table is marked. |
| 2206 StringTable* string_table = heap()->string_table(); |
| 2207 InternalizedStringTableCleaner internalized_visitor(heap()); |
| 2208 string_table->IterateElements(&internalized_visitor); |
| 2209 string_table->ElementsRemoved(internalized_visitor.PointersRemoved()); |
2190 | 2210 |
2191 // Process the weak references. | 2211 ExternalStringTableCleaner external_visitor(heap()); |
2192 MarkCompactWeakObjectRetainer mark_compact_object_retainer; | 2212 heap()->external_string_table_.Iterate(&external_visitor); |
2193 heap()->ProcessAllWeakReferences(&mark_compact_object_retainer); | 2213 heap()->external_string_table_.CleanUp(); |
| 2214 } |
2194 | 2215 |
2195 // Remove object groups after marking phase. | 2216 { |
2196 heap()->isolate()->global_handles()->RemoveObjectGroups(); | 2217 GCTracer::Scope gc_scope(heap()->tracer(), |
2197 heap()->isolate()->global_handles()->RemoveImplicitRefGroups(); | 2218 GCTracer::Scope::MC_MARK_WEAK_REFERENCES); |
| 2219 |
| 2220 // Process the weak references. |
| 2221 MarkCompactWeakObjectRetainer mark_compact_object_retainer; |
| 2222 heap()->ProcessAllWeakReferences(&mark_compact_object_retainer); |
| 2223 } |
| 2224 |
| 2225 { |
| 2226 GCTracer::Scope gc_scope(heap()->tracer(), |
| 2227 GCTracer::Scope::MC_MARK_GLOBAL_HANDLES); |
| 2228 |
| 2229 // Remove object groups after marking phase. |
| 2230 heap()->isolate()->global_handles()->RemoveObjectGroups(); |
| 2231 heap()->isolate()->global_handles()->RemoveImplicitRefGroups(); |
| 2232 } |
2198 | 2233 |
2199 // Flush code from collected candidates. | 2234 // Flush code from collected candidates. |
2200 if (is_code_flushing_enabled()) { | 2235 if (is_code_flushing_enabled()) { |
| 2236 GCTracer::Scope gc_scope(heap()->tracer(), |
| 2237 GCTracer::Scope::MC_MARK_CODE_FLUSH); |
2201 code_flusher_->ProcessCandidates(); | 2238 code_flusher_->ProcessCandidates(); |
2202 } | 2239 } |
2203 | 2240 |
2204 if (FLAG_track_gc_object_stats) { | 2241 if (FLAG_track_gc_object_stats) { |
2205 if (FLAG_trace_gc_object_stats) { | 2242 if (FLAG_trace_gc_object_stats) { |
2206 heap()->object_stats_->TraceObjectStats(); | 2243 heap()->object_stats_->TraceObjectStats(); |
2207 } | 2244 } |
2208 heap()->object_stats_->CheckpointObjectStats(); | 2245 heap()->object_stats_->CheckpointObjectStats(); |
2209 } | 2246 } |
2210 } | 2247 } |
(...skipping 2391 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4602 MarkBit mark_bit = Marking::MarkBitFrom(host); | 4639 MarkBit mark_bit = Marking::MarkBitFrom(host); |
4603 if (Marking::IsBlack(mark_bit)) { | 4640 if (Marking::IsBlack(mark_bit)) { |
4604 RelocInfo rinfo(pc, RelocInfo::CODE_TARGET, 0, host); | 4641 RelocInfo rinfo(pc, RelocInfo::CODE_TARGET, 0, host); |
4605 RecordRelocSlot(&rinfo, target); | 4642 RecordRelocSlot(&rinfo, target); |
4606 } | 4643 } |
4607 } | 4644 } |
4608 } | 4645 } |
4609 | 4646 |
4610 } // namespace internal | 4647 } // namespace internal |
4611 } // namespace v8 | 4648 } // namespace v8 |
OLD | NEW |