diff --git a/src/heap/base/worklist.h b/src/heap/base/worklist.h index be2ecf158b..e2d33616ad 100644 --- a/src/heap/base/worklist.h +++ b/src/heap/base/worklist.h @@ -285,6 +285,9 @@ class Worklist::Local { void Publish(); void Merge(Worklist::Local* other); + bool IsEmpty() const; + void Clear(); + size_t PushSegmentSize() const { return push_segment_->Size(); } private: @@ -445,6 +448,17 @@ bool Worklist::Local::StealPopSegment() { return false; } +template +bool Worklist::Local::IsEmpty() const { + return push_segment_->IsEmpty() && pop_segment_->IsEmpty(); +} + +template +void Worklist::Local::Clear() { + push_segment_->Clear(); + pop_segment_->Clear(); +} + } // namespace base } // namespace heap diff --git a/test/unittests/heap/base/worklist-unittest.cc b/test/unittests/heap/base/worklist-unittest.cc index ae737a7aa3..fe9be18ecd 100644 --- a/test/unittests/heap/base/worklist-unittest.cc +++ b/test/unittests/heap/base/worklist-unittest.cc @@ -110,21 +110,45 @@ TEST(CppgcWorkListTest, LocalPushPop) { TEST(CppgcWorkListTest, LocalPushStaysPrivate) { TestWorklist worklist; - TestWorklist::Local worklist_view1(&worklist); - TestWorklist::Local worklist_view2(&worklist); + TestWorklist::Local worklist_local1(&worklist); + TestWorklist::Local worklist_local2(&worklist); SomeObject dummy; SomeObject* retrieved = nullptr; EXPECT_TRUE(worklist.IsEmpty()); EXPECT_EQ(0U, worklist.Size()); - worklist_view1.Push(&dummy); + worklist_local1.Push(&dummy); EXPECT_EQ(0U, worklist.Size()); - EXPECT_FALSE(worklist_view2.Pop(&retrieved)); + EXPECT_FALSE(worklist_local2.Pop(&retrieved)); EXPECT_EQ(nullptr, retrieved); - EXPECT_TRUE(worklist_view1.Pop(&retrieved)); + EXPECT_TRUE(worklist_local1.Pop(&retrieved)); EXPECT_EQ(&dummy, retrieved); EXPECT_EQ(0U, worklist.Size()); } +TEST(CppgcWorkListTest, LocalClear) { + TestWorklist worklist; + TestWorklist::Local worklist_local(&worklist); + SomeObject* object; + object = reinterpret_cast(&object); + // Check push segment: + EXPECT_TRUE(worklist_local.IsEmpty()); + worklist_local.Push(object); + EXPECT_FALSE(worklist_local.IsEmpty()); + worklist_local.Clear(); + EXPECT_TRUE(worklist_local.IsEmpty()); + // Check pop segment: + worklist_local.Push(object); + worklist_local.Push(object); + EXPECT_FALSE(worklist_local.IsEmpty()); + worklist_local.Publish(); + EXPECT_TRUE(worklist_local.IsEmpty()); + SomeObject* retrieved; + worklist_local.Pop(&retrieved); + EXPECT_FALSE(worklist_local.IsEmpty()); + worklist_local.Clear(); + EXPECT_TRUE(worklist_local.IsEmpty()); +} + TEST(CppgcWorkListTest, GlobalUpdateNull) { TestWorklist worklist; TestWorklist::Local worklist_local(&worklist);