diff --git a/runtime/vm/heap.cc b/runtime/vm/heap.cc index eb3f79633d2..4ac395c9c66 100644 --- a/runtime/vm/heap.cc +++ b/runtime/vm/heap.cc @@ -231,12 +231,15 @@ HeapIterationScope::HeapIterationScope() MonitorLocker ml(old_space_->tasks_lock()); #if defined(DEBUG) // We currently don't support nesting of HeapIterationScopes. - ASSERT(!old_space_->is_iterating_); - old_space_->is_iterating_ = true; + ASSERT(old_space_->iterating_thread_ != thread()); #endif while (old_space_->tasks() > 0) { ml.Wait(); } +#if defined(DEBUG) + ASSERT(old_space_->iterating_thread_ == NULL); + old_space_->iterating_thread_ = thread(); +#endif old_space_->set_tasks(1); } @@ -244,8 +247,8 @@ HeapIterationScope::HeapIterationScope() HeapIterationScope::~HeapIterationScope() { MonitorLocker ml(old_space_->tasks_lock()); #if defined(DEBUG) - ASSERT(old_space_->is_iterating_); - old_space_->is_iterating_ = false; + ASSERT(old_space_->iterating_thread_ == thread()); + old_space_->iterating_thread_ = NULL; #endif ASSERT(old_space_->tasks() == 1); old_space_->set_tasks(0); diff --git a/runtime/vm/isolate.cc b/runtime/vm/isolate.cc index fcbf9c48377..e0f8752c1d1 100644 --- a/runtime/vm/isolate.cc +++ b/runtime/vm/isolate.cc @@ -1598,14 +1598,6 @@ void Isolate::VisitObjectPointers(ObjectPointerVisitor* visitor, // Visit objects in isolate specific handles area. reusable_handles_.VisitObjectPointers(visitor); - // Iterate over all the stack frames and visit objects on the stack. - StackFrameIterator frames_iterator(validate_frames); - StackFrame* frame = frames_iterator.NextFrame(); - while (frame != NULL) { - frame->VisitObjectPointers(visitor); - frame = frames_iterator.NextFrame(); - } - // Visit the dart api state for all local and persistent handles. if (api_state() != NULL) { api_state()->VisitObjectPointers(visitor, visit_prologue_weak_handles); diff --git a/runtime/vm/pages.cc b/runtime/vm/pages.cc index b6f0b2ed4e2..0457b3d8104 100644 --- a/runtime/vm/pages.cc +++ b/runtime/vm/pages.cc @@ -161,7 +161,7 @@ PageSpace::PageSpace(Heap* heap, tasks_lock_(new Monitor()), tasks_(0), #if defined(DEBUG) - is_iterating_(false), + iterating_thread_(NULL), #endif page_space_controller_(heap, FLAG_old_gen_growth_space_ratio, diff --git a/runtime/vm/pages.h b/runtime/vm/pages.h index ca10ee0f5e8..cb5c1dc2b8b 100644 --- a/runtime/vm/pages.h +++ b/runtime/vm/pages.h @@ -427,7 +427,7 @@ class PageSpace { Monitor* tasks_lock_; intptr_t tasks_; #if defined(DEBUG) - bool is_iterating_; + Thread* iterating_thread_; #endif PageSpaceController page_space_controller_; diff --git a/runtime/vm/thread.h b/runtime/vm/thread.h index c0721d9b1da..69cc4ecd17b 100644 --- a/runtime/vm/thread.h +++ b/runtime/vm/thread.h @@ -262,6 +262,7 @@ CACHED_CONSTANTS_LIST(DECLARE_MEMBERS) friend class ApiZone; friend class Isolate; friend class StackZone; + friend class ThreadRegistry; DISALLOW_COPY_AND_ASSIGN(Thread); }; diff --git a/runtime/vm/thread_registry.h b/runtime/vm/thread_registry.h index f8f324dc752..b7d3e1a8a08 100644 --- a/runtime/vm/thread_registry.h +++ b/runtime/vm/thread_registry.h @@ -9,6 +9,7 @@ #include "vm/growable_array.h" #include "vm/isolate.h" #include "vm/lockers.h" +#include "vm/stack_frame.h" #include "vm/thread.h" namespace dart { @@ -118,9 +119,19 @@ class ThreadRegistry { MonitorLocker ml(monitor_); for (int i = 0; i < entries_.length(); ++i) { const Entry& entry = entries_[i]; - Zone* zone = entry.scheduled ? entry.thread->zone() : entry.state.zone; - if (zone != NULL) { - zone->VisitObjectPointers(visitor); + const Thread::State& state = + entry.scheduled ? entry.thread->state_ : entry.state; + if (state.zone != NULL) { + state.zone->VisitObjectPointers(visitor); + } + // Iterate over all the stack frames and visit objects on the stack. + uword efi = state.top_exit_frame_info; + if (efi == 0) continue; + StackFrameIterator frames_iterator(efi, false); + StackFrame* frame = frames_iterator.NextFrame(); + while (frame != NULL) { + frame->VisitObjectPointers(visitor); + frame = frames_iterator.NextFrame(); } } } diff --git a/runtime/vm/thread_test.cc b/runtime/vm/thread_test.cc index 37d0c0ea04b..9290d637d30 100644 --- a/runtime/vm/thread_test.cc +++ b/runtime/vm/thread_test.cc @@ -133,8 +133,9 @@ class TaskWithZoneAllocation : public ThreadPool::Task { EXPECT(smi.Value() == unique_smi); ObjectCounter counter(isolate_, &smi); // Ensure that our particular zone is visited. - // TODO(koda): Remove "->thread_registry()" after updating stack walker. - isolate_->thread_registry()->VisitObjectPointers(&counter); + isolate_->IterateObjectPointers(&counter, + /* visit_prologue_weak_handles = */ true, + /* validate_frames = */ true); EXPECT_EQ(1, counter.count()); char* unique_chars = zone->PrintToString("unique_str_%" Pd, id_);