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
3 // found in the LICENSE file.
4 
5 #include "src/heap/incremental-marking-job.h"
6 
7 #include "src/base/platform/time.h"
8 #include "src/heap/heap-inl.h"
9 #include "src/heap/heap.h"
10 #include "src/heap/incremental-marking.h"
11 #include "src/isolate.h"
12 #include "src/v8.h"
13 
14 namespace v8 {
15 namespace internal {
16 
Start(Heap * heap)17 void IncrementalMarkingJob::Start(Heap* heap) {
18   DCHECK(!heap->incremental_marking()->IsStopped());
19   ScheduleTask(heap);
20 }
21 
NotifyTask()22 void IncrementalMarkingJob::NotifyTask() { task_pending_ = false; }
23 
ScheduleTask(Heap * heap)24 void IncrementalMarkingJob::ScheduleTask(Heap* heap) {
25   if (!task_pending_) {
26     v8::Isolate* isolate = reinterpret_cast<v8::Isolate*>(heap->isolate());
27     task_pending_ = true;
28     auto task = new Task(heap->isolate(), this);
29     V8::GetCurrentPlatform()->CallOnForegroundThread(isolate, task);
30   }
31 }
32 
Step(Heap * heap)33 void IncrementalMarkingJob::Task::Step(Heap* heap) {
34   const int kIncrementalMarkingDelayMs = 1;
35   double deadline =
36       heap->MonotonicallyIncreasingTimeInMs() + kIncrementalMarkingDelayMs;
37   heap->incremental_marking()->AdvanceIncrementalMarking(
38       deadline, i::IncrementalMarking::NO_GC_VIA_STACK_GUARD,
39       i::IncrementalMarking::FORCE_COMPLETION, i::StepOrigin::kTask);
40   heap->FinalizeIncrementalMarkingIfComplete(
41       GarbageCollectionReason::kFinalizeMarkingViaTask);
42 }
43 
RunInternal()44 void IncrementalMarkingJob::Task::RunInternal() {
45   Heap* heap = isolate()->heap();
46   job_->NotifyTask();
47   IncrementalMarking* incremental_marking = heap->incremental_marking();
48   if (incremental_marking->IsStopped()) {
49     if (heap->IncrementalMarkingLimitReached() !=
50         Heap::IncrementalMarkingLimit::kNoLimit) {
51       heap->StartIncrementalMarking(Heap::kNoGCFlags,
52                                     GarbageCollectionReason::kIdleTask,
53                                     kNoGCCallbackFlags);
54     }
55   }
56   if (!incremental_marking->IsStopped()) {
57     Step(heap);
58     if (!incremental_marking->IsStopped()) {
59       job_->ScheduleTask(heap);
60     }
61   }
62 }
63 
64 }  // namespace internal
65 }  // namespace v8
66