1 // Copyright 2020 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 #ifndef V8_HEAP_COLLECTION_BARRIER_H_ 6 #define V8_HEAP_COLLECTION_BARRIER_H_ 7 8 #include <atomic> 9 10 #include "src/base/optional.h" 11 #include "src/base/platform/elapsed-timer.h" 12 #include "src/base/platform/mutex.h" 13 #include "src/logging/counters.h" 14 15 namespace v8 { 16 namespace internal { 17 18 class Heap; 19 20 // This class stops and resumes all background threads waiting for GC. 21 class CollectionBarrier { 22 Heap* heap_; 23 base::Mutex mutex_; 24 base::ConditionVariable cond_; 25 base::ElapsedTimer timer_; 26 27 enum class RequestState { 28 // Default state, no collection requested and tear down wasn't initated 29 // yet. 30 kDefault, 31 32 // Collection was already requested 33 kCollectionRequested, 34 35 // Collection was already started 36 kCollectionStarted, 37 38 // This state is reached after isolate starts to shut down. The main 39 // thread can't perform any GCs anymore, so all allocations need to be 40 // allowed from here on until background thread finishes. 41 kShutdown, 42 }; 43 44 // The current state. 45 std::atomic<RequestState> state_; 46 47 // Request GC by activating stack guards and posting a task to perform the 48 // GC. 49 void ActivateStackGuardAndPostTask(); 50 51 // Returns true when state was successfully updated from kDefault to 52 // kCollection. FirstCollectionRequest()53 bool FirstCollectionRequest() { 54 RequestState expected = RequestState::kDefault; 55 return state_.compare_exchange_strong(expected, 56 RequestState::kCollectionRequested); 57 } 58 59 // Sets state back to kDefault - invoked at end of GC. ClearCollectionRequested()60 void ClearCollectionRequested() { 61 RequestState old_state = 62 state_.exchange(RequestState::kDefault, std::memory_order_relaxed); 63 USE(old_state); 64 DCHECK_EQ(old_state, RequestState::kCollectionStarted); 65 } 66 67 public: CollectionBarrier(Heap * heap)68 explicit CollectionBarrier(Heap* heap) 69 : heap_(heap), state_(RequestState::kDefault) {} 70 71 // Checks whether any background thread requested GC. CollectionRequested()72 bool CollectionRequested() { 73 return state_.load(std::memory_order_relaxed) == 74 RequestState::kCollectionRequested; 75 } 76 77 void StopTimeToCollectionTimer(); 78 void BlockUntilCollected(); 79 80 // Resumes threads waiting for collection. 81 void ResumeThreadsAwaitingCollection(); 82 83 // Sets current state to kShutdown. 84 void ShutdownRequested(); 85 86 // This is the method use by background threads to request and wait for GC. 87 void AwaitCollectionBackground(); 88 }; 89 90 } // namespace internal 91 } // namespace v8 92 93 #endif // V8_HEAP_COLLECTION_BARRIER_H_ 94