1 /* 2 * Copyright (C) 2013 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef ART_RUNTIME_GC_REFERENCE_QUEUE_H_ 18 #define ART_RUNTIME_GC_REFERENCE_QUEUE_H_ 19 20 #include <iosfwd> 21 #include <string> 22 #include <vector> 23 24 #include "atomic.h" 25 #include "base/mutex.h" 26 #include "base/timing_logger.h" 27 #include "globals.h" 28 #include "jni.h" 29 #include "object_callbacks.h" 30 #include "offsets.h" 31 #include "thread_pool.h" 32 33 namespace art { 34 namespace mirror { 35 class Reference; 36 } // namespace mirror 37 38 namespace gc { 39 40 namespace collector { 41 class GarbageCollector; 42 } // namespace collector 43 44 class Heap; 45 46 // Used to temporarily store java.lang.ref.Reference(s) during GC and prior to queueing on the 47 // appropriate java.lang.ref.ReferenceQueue. The linked list is maintained as an unordered, 48 // circular, and singly-linked list using the pendingNext fields of the java.lang.ref.Reference 49 // objects. 50 class ReferenceQueue { 51 public: 52 explicit ReferenceQueue(Mutex* lock); 53 54 // Enqueue a reference if it is unprocessed. Thread safe to call from multiple 55 // threads since it uses a lock to avoid a race between checking for the references presence and 56 // adding it. 57 void AtomicEnqueueIfNotEnqueued(Thread* self, mirror::Reference* ref) 58 SHARED_REQUIRES(Locks::mutator_lock_) REQUIRES(!*lock_); 59 60 // Enqueue a reference. The reference must be unprocessed. 61 // Not thread safe, used when mutators are paused to minimize lock overhead. 62 void EnqueueReference(mirror::Reference* ref) SHARED_REQUIRES(Locks::mutator_lock_); 63 64 // Dequeue a reference from the queue and return that dequeued reference. 65 mirror::Reference* DequeuePendingReference() SHARED_REQUIRES(Locks::mutator_lock_); 66 67 // Enqueues finalizer references with white referents. White referents are blackened, moved to 68 // the zombie field, and the referent field is cleared. 69 void EnqueueFinalizerReferences(ReferenceQueue* cleared_references, 70 collector::GarbageCollector* collector) 71 SHARED_REQUIRES(Locks::mutator_lock_); 72 73 // Walks the reference list marking any references subject to the reference clearing policy. 74 // References with a black referent are removed from the list. References with white referents 75 // biased toward saving are blackened and also removed from the list. 76 void ForwardSoftReferences(MarkObjectVisitor* visitor) 77 SHARED_REQUIRES(Locks::mutator_lock_); 78 79 // Unlink the reference list clearing references objects with white referents. Cleared references 80 // registered to a reference queue are scheduled for appending by the heap worker thread. 81 void ClearWhiteReferences(ReferenceQueue* cleared_references, 82 collector::GarbageCollector* collector) 83 SHARED_REQUIRES(Locks::mutator_lock_); 84 85 void Dump(std::ostream& os) const SHARED_REQUIRES(Locks::mutator_lock_); 86 size_t GetLength() const SHARED_REQUIRES(Locks::mutator_lock_); 87 IsEmpty()88 bool IsEmpty() const { 89 return list_ == nullptr; 90 } Clear()91 void Clear() { 92 list_ = nullptr; 93 } GetList()94 mirror::Reference* GetList() SHARED_REQUIRES(Locks::mutator_lock_) { 95 return list_; 96 } 97 98 // Visits list_, currently only used for the mark compact GC. 99 void UpdateRoots(IsMarkedVisitor* visitor) 100 SHARED_REQUIRES(Locks::mutator_lock_); 101 102 private: 103 // Lock, used for parallel GC reference enqueuing. It allows for multiple threads simultaneously 104 // calling AtomicEnqueueIfNotEnqueued. 105 Mutex* const lock_; 106 // The actual reference list. Only a root for the mark compact GC since it will be null for other 107 // GC types. 108 mirror::Reference* list_; 109 110 DISALLOW_IMPLICIT_CONSTRUCTORS(ReferenceQueue); 111 }; 112 113 } // namespace gc 114 } // namespace art 115 116 #endif // ART_RUNTIME_GC_REFERENCE_QUEUE_H_ 117