OLD | NEW |
---|---|
1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "vm/scavenger.h" | 5 #include "vm/scavenger.h" |
6 | 6 |
7 #include "vm/dart.h" | 7 #include "vm/dart.h" |
8 #include "vm/dart_api_state.h" | 8 #include "vm/dart_api_state.h" |
9 #include "vm/isolate.h" | 9 #include "vm/isolate.h" |
10 #include "vm/lockers.h" | 10 #include "vm/lockers.h" |
(...skipping 175 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
186 RawObject* visiting_old_object_; | 186 RawObject* visiting_old_object_; |
187 | 187 |
188 friend class Scavenger; | 188 friend class Scavenger; |
189 | 189 |
190 DISALLOW_COPY_AND_ASSIGN(ScavengerVisitor); | 190 DISALLOW_COPY_AND_ASSIGN(ScavengerVisitor); |
191 }; | 191 }; |
192 | 192 |
193 | 193 |
194 class ScavengerWeakVisitor : public HandleVisitor { | 194 class ScavengerWeakVisitor : public HandleVisitor { |
195 public: | 195 public: |
196 explicit ScavengerWeakVisitor(Scavenger* scavenger) | 196 explicit ScavengerWeakVisitor( |
197 : HandleVisitor(Thread::Current()), | 197 Thread* thread, |
198 scavenger_(scavenger) { | 198 Scavenger* scavenger, |
199 ASSERT(scavenger->heap_->isolate() == Thread::Current()->isolate()); | 199 MallocGrowableArray<FinalizablePersistentHandle*>* finalization_queue) |
200 : HandleVisitor(thread), | |
201 scavenger_(scavenger), | |
202 finalization_queue_(finalization_queue) { | |
203 ASSERT(scavenger->heap_->isolate() == thread->isolate()); | |
200 } | 204 } |
201 | 205 |
202 void VisitHandle(uword addr) { | 206 void VisitHandle(uword addr) { |
203 FinalizablePersistentHandle* handle = | 207 FinalizablePersistentHandle* handle = |
204 reinterpret_cast<FinalizablePersistentHandle*>(addr); | 208 reinterpret_cast<FinalizablePersistentHandle*>(addr); |
205 RawObject** p = handle->raw_addr(); | 209 RawObject** p = handle->raw_addr(); |
206 if (scavenger_->IsUnreachable(p)) { | 210 if (scavenger_->IsUnreachable(p)) { |
207 handle->UpdateUnreachable(thread()->isolate()); | 211 handle->UpdateUnreachableFinalizeLater(thread()->isolate()); |
212 finalization_queue_->Add(handle); | |
siva
2016/06/02 20:18:05
handle->UpdateUnreachable(thread()->isolate(), fin
| |
208 } else { | 213 } else { |
209 handle->UpdateRelocated(thread()->isolate()); | 214 handle->UpdateRelocated(thread()->isolate()); |
210 } | 215 } |
211 } | 216 } |
212 | 217 |
213 private: | 218 private: |
214 Scavenger* scavenger_; | 219 Scavenger* scavenger_; |
220 MallocGrowableArray<FinalizablePersistentHandle*>* finalization_queue_; | |
siva
2016/06/02 20:18:05
Maybe typedef MallocGrowableArray<FinalizablePersi
rmacnak
2016/06/03 01:08:31
Done.
| |
215 | 221 |
216 DISALLOW_COPY_AND_ASSIGN(ScavengerWeakVisitor); | 222 DISALLOW_COPY_AND_ASSIGN(ScavengerWeakVisitor); |
217 }; | 223 }; |
218 | 224 |
219 | 225 |
226 class BackgroundFinalizer : public ThreadPool::Task { | |
227 public: | |
228 explicit BackgroundFinalizer( | |
siva
2016/06/02 20:18:05
Why explicit? seems to have more than 1 argument.
rmacnak
2016/06/03 01:08:31
Removed.
| |
229 Isolate* isolate, | |
230 MallocGrowableArray<FinalizablePersistentHandle*>* handles) : | |
231 isolate_(isolate), | |
232 handles_(handles) { | |
233 MonitorLocker ml(isolate->heap()->finalization_tasks_lock()); | |
234 isolate->heap()->set_finalization_tasks( | |
235 isolate->heap()->finalization_tasks() + 1); | |
236 ml.Notify(); | |
237 } | |
238 | |
239 virtual ~BackgroundFinalizer() { } | |
240 | |
241 void Run() { | |
242 bool result = Thread::EnterIsolateAsHelper(isolate_, | |
243 Thread::kFinalizerTask, | |
244 true /* bypass_safepoint */); | |
245 ASSERT(result); | |
246 | |
247 { | |
248 TIMELINE_FUNCTION_GC_DURATION(Thread::Current(), | |
249 "BackgroundFinalization"); | |
250 | |
251 for (intptr_t i = 0; i < handles_->length(); i++) { | |
252 FinalizablePersistentHandle* handle = (*handles_)[i]; | |
253 FinalizablePersistentHandle::Finalize(isolate_, handle); | |
254 } | |
255 delete handles_; | |
256 } | |
257 | |
258 // Exit isolate cleanly *before* notifying it, to avoid shutdown race. | |
siva
2016/06/02 20:18:05
notifying it? (what is it).
| |
259 Thread::ExitIsolateAsHelper(); | |
260 | |
261 { | |
262 Heap* heap = isolate_->heap(); | |
263 MonitorLocker ml(heap->finalization_tasks_lock()); | |
264 heap->set_finalization_tasks(heap->finalization_tasks() - 1); | |
265 ml.Notify(); | |
siva
2016/06/02 20:18:05
seems odd that the thread has exited the isolate b
rmacnak
2016/06/03 01:08:31
This pattern comes from the sweeper task. This avo
| |
266 } | |
267 } | |
268 | |
269 private: | |
270 Isolate* isolate_; | |
271 MallocGrowableArray<FinalizablePersistentHandle*>* handles_; | |
272 | |
273 DISALLOW_IMPLICIT_CONSTRUCTORS(BackgroundFinalizer); | |
274 }; | |
275 | |
276 | |
220 // Visitor used to verify that all old->new references have been added to the | 277 // Visitor used to verify that all old->new references have been added to the |
221 // StoreBuffers. | 278 // StoreBuffers. |
222 class VerifyStoreBufferPointerVisitor : public ObjectPointerVisitor { | 279 class VerifyStoreBufferPointerVisitor : public ObjectPointerVisitor { |
223 public: | 280 public: |
224 VerifyStoreBufferPointerVisitor(Isolate* isolate, | 281 VerifyStoreBufferPointerVisitor(Isolate* isolate, |
225 const SemiSpace* to) | 282 const SemiSpace* to) |
226 : ObjectPointerVisitor(isolate), to_(to) {} | 283 : ObjectPointerVisitor(isolate), to_(to) {} |
227 | 284 |
228 void VisitPointers(RawObject** first, RawObject** last) { | 285 void VisitPointers(RawObject** first, RawObject** last) { |
229 for (RawObject** current = first; current <= last; current++) { | 286 for (RawObject** current = first; current <= last; current++) { |
(...skipping 575 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
805 StackZone zone(thread); | 862 StackZone zone(thread); |
806 // Setup the visitor and run the scavenge. | 863 // Setup the visitor and run the scavenge. |
807 ScavengerVisitor visitor(isolate, this, from); | 864 ScavengerVisitor visitor(isolate, this, from); |
808 page_space->AcquireDataLock(); | 865 page_space->AcquireDataLock(); |
809 IterateRoots(isolate, &visitor); | 866 IterateRoots(isolate, &visitor); |
810 int64_t start = OS::GetCurrentTimeMicros(); | 867 int64_t start = OS::GetCurrentTimeMicros(); |
811 ProcessToSpace(&visitor); | 868 ProcessToSpace(&visitor); |
812 int64_t middle = OS::GetCurrentTimeMicros(); | 869 int64_t middle = OS::GetCurrentTimeMicros(); |
813 { | 870 { |
814 TIMELINE_FUNCTION_GC_DURATION(thread, "WeakHandleProcessing"); | 871 TIMELINE_FUNCTION_GC_DURATION(thread, "WeakHandleProcessing"); |
815 ScavengerWeakVisitor weak_visitor(this); | 872 MallocGrowableArray<FinalizablePersistentHandle*>* finalization_queue = |
873 new MallocGrowableArray<FinalizablePersistentHandle*>(); | |
874 ScavengerWeakVisitor weak_visitor(thread, this, finalization_queue); | |
816 IterateWeakRoots(isolate, &weak_visitor); | 875 IterateWeakRoots(isolate, &weak_visitor); |
876 if (finalization_queue->length() > 0) { | |
877 Dart::thread_pool()->Run(new BackgroundFinalizer(isolate, | |
878 finalization_queue)); | |
siva
2016/06/02 20:18:05
I am assuming the BackgroundFinalizer object creat
rmacnak
2016/06/03 01:08:31
Yes, tasks are deleted by the thread pool after th
| |
879 } else { | |
880 delete finalization_queue; | |
881 } | |
817 } | 882 } |
818 ProcessWeakReferences(); | 883 ProcessWeakReferences(); |
819 page_space->ReleaseDataLock(); | 884 page_space->ReleaseDataLock(); |
820 | 885 |
821 // Scavenge finished. Run accounting. | 886 // Scavenge finished. Run accounting. |
822 int64_t end = OS::GetCurrentTimeMicros(); | 887 int64_t end = OS::GetCurrentTimeMicros(); |
823 heap_->RecordTime(kProcessToSpace, middle - start); | 888 heap_->RecordTime(kProcessToSpace, middle - start); |
824 heap_->RecordTime(kIterateWeaks, end - middle); | 889 heap_->RecordTime(kIterateWeaks, end - middle); |
825 stats_history_.Add( | 890 stats_history_.Add( |
826 ScavengeStats(start, end, | 891 ScavengeStats(start, end, |
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
884 } | 949 } |
885 | 950 |
886 | 951 |
887 void Scavenger::FreeExternal(intptr_t size) { | 952 void Scavenger::FreeExternal(intptr_t size) { |
888 ASSERT(size >= 0); | 953 ASSERT(size >= 0); |
889 external_size_ -= size; | 954 external_size_ -= size; |
890 ASSERT(external_size_ >= 0); | 955 ASSERT(external_size_ >= 0); |
891 } | 956 } |
892 | 957 |
893 } // namespace dart | 958 } // namespace dart |
OLD | NEW |