From 738f85c7d887a501070f98e1d9eb8884ce34587f Mon Sep 17 00:00:00 2001 From: "hpayer@chromium.org" Date: Thu, 24 Apr 2014 09:04:12 +0000 Subject: [PATCH] Don't move the object start of objects on non-swept pages. BUG= R=mstarzinger@chromium.org Review URL: https://codereview.chromium.org/255603002 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@20929 ce2b1a6d-e550-0410-aec6-3dcde31c8c00 --- src/heap.cc | 15 +++++++++++---- test/cctest/test-heap.cc | 27 +++++++++++++++++++++++++++ 2 files changed, 38 insertions(+), 4 deletions(-) diff --git a/src/heap.cc b/src/heap.cc index 7f23886..a1070fa 100644 --- a/src/heap.cc +++ b/src/heap.cc @@ -3426,11 +3426,18 @@ bool Heap::CanMoveObjectStart(HeapObject* object) { if (lo_space()->Contains(object)) return false; - // We cannot move the object start if the given old space page is - // concurrently swept. + Page* page = Page::FromAddress(address); + // We can move the object start if: + // (1) the object is not in old pointer or old data space, + // (2) the page of the object was already swept, + // (3) the page was already concurrently swept. This case is an optimization + // for concurrent sweeping. The WasSwept predicate for concurrently swept + // pages is set after sweeping all pages. return (!is_in_old_pointer_space && !is_in_old_data_space) || - Page::FromAddress(address)->parallel_sweeping() <= - MemoryChunk::PARALLEL_SWEEPING_FINALIZE; + page->WasSwept() || + (mark_compact_collector()->AreSweeperThreadsActivated() && + page->parallel_sweeping() <= + MemoryChunk::PARALLEL_SWEEPING_FINALIZE); } diff --git a/test/cctest/test-heap.cc b/test/cctest/test-heap.cc index dfb4105..0b0c704 100644 --- a/test/cctest/test-heap.cc +++ b/test/cctest/test-heap.cc @@ -4197,3 +4197,30 @@ TEST(Regress357137) { "f()()"); CHECK_EQ(42.0, result->ToNumber()->Value()); } + + +TEST(ArrayShiftLazySweeping) { + i::FLAG_expose_gc = true; + i::FLAG_parallel_sweeping = false; + i::FLAG_concurrent_sweeping = false; + i::FLAG_lazy_sweeping = true; + CcTest::InitializeVM(); + v8::HandleScope scope(CcTest::isolate()); + Isolate* isolate = CcTest::i_isolate(); + Heap* heap = isolate->heap(); + + v8::Local result = CompileRun( + "var array = new Array(40000);" + "var tmp = new Array(100000);" + "gc();" + "array.shift();" + "array;"); + + Handle o = + v8::Utils::OpenHandle(*v8::Handle::Cast(result)); + CHECK(heap->InOldPointerSpace(o->elements())); + CHECK(heap->InOldPointerSpace(*o)); + Page* page = Page::FromAddress(o->elements()->address()); + CHECK(page->WasSwept() || + Marking::IsBlack(Marking::MarkBitFrom(o->elements()))); +} -- 2.7.4