OLD | NEW |
---|---|
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #ifndef TraceTraits_h | 5 #ifndef TraceTraits_h |
6 #define TraceTraits_h | 6 #define TraceTraits_h |
7 | 7 |
8 #include "platform/heap/GCInfo.h" | 8 #include "platform/heap/GCInfo.h" |
9 #include "platform/heap/Heap.h" | 9 #include "platform/heap/Heap.h" |
10 #include "platform/heap/InlinedGlobalMarkingVisitor.h" | 10 #include "platform/heap/InlinedGlobalMarkingVisitor.h" |
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
94 self->adjustAndMark(visitor); | 94 self->adjustAndMark(visitor); |
95 } | 95 } |
96 }; | 96 }; |
97 | 97 |
98 template<typename T, bool needsTracing> | 98 template<typename T, bool needsTracing> |
99 struct TraceIfEnabled; | 99 struct TraceIfEnabled; |
100 | 100 |
101 template<typename T> | 101 template<typename T> |
102 struct TraceIfEnabled<T, false> { | 102 struct TraceIfEnabled<T, false> { |
103 template<typename VisitorDispatcher> | 103 template<typename VisitorDispatcher> |
104 static void trace(VisitorDispatcher, T&) { } | 104 static void trace(VisitorDispatcher, T&) |
105 { | |
106 static_assert(!WTF::NeedsTracing<T>::value, "T should not be traced"); | |
107 } | |
105 }; | 108 }; |
106 | 109 |
107 template<typename T> | 110 template<typename T> |
108 struct TraceIfEnabled<T, true> { | 111 struct TraceIfEnabled<T, true> { |
109 template<typename VisitorDispatcher> | 112 template<typename VisitorDispatcher> |
110 static void trace(VisitorDispatcher visitor, T& t) | 113 static void trace(VisitorDispatcher visitor, T& t) |
111 { | 114 { |
115 static_assert(WTF::NeedsTracing<T>::value || WTF::IsWeak<T>::value, "T s hould be traced"); | |
112 visitor->trace(t); | 116 visitor->trace(t); |
113 } | 117 } |
114 }; | 118 }; |
115 | 119 |
116 template<bool needsTracing, WTF::WeakHandlingFlag weakHandlingFlag, WTF::ShouldW eakPointersBeMarkedStrongly strongify, typename T, typename Traits> struct Trace CollectionIfEnabled; | 120 template<bool needsTracing, WTF::WeakHandlingFlag weakHandlingFlag, WTF::ShouldW eakPointersBeMarkedStrongly strongify, typename T, typename Traits> struct Trace CollectionIfEnabled; |
117 | 121 |
118 template<WTF::ShouldWeakPointersBeMarkedStrongly strongify, typename T, typename Traits> | 122 template<WTF::ShouldWeakPointersBeMarkedStrongly strongify, typename T, typename Traits> |
119 struct TraceCollectionIfEnabled<false, WTF::NoWeakHandlingInCollections, strongi fy, T, Traits> { | 123 struct TraceCollectionIfEnabled<false, WTF::NoWeakHandlingInCollections, strongi fy, T, Traits> { |
120 template<typename VisitorDispatcher> | 124 template<typename VisitorDispatcher> |
121 static bool trace(VisitorDispatcher, T&) { return false; } | 125 static bool trace(VisitorDispatcher, T&) |
126 { | |
127 static_assert(!WTF::NeedsTracingTrait<Traits>::value, "Traits should not be traced"); | |
128 return false; | |
129 } | |
122 }; | 130 }; |
123 | 131 |
124 template<bool needsTracing, WTF::WeakHandlingFlag weakHandlingFlag, WTF::ShouldW eakPointersBeMarkedStrongly strongify, typename T, typename Traits> | 132 template<bool needsTracing, WTF::WeakHandlingFlag weakHandlingFlag, WTF::ShouldW eakPointersBeMarkedStrongly strongify, typename T, typename Traits> |
125 struct TraceCollectionIfEnabled { | 133 struct TraceCollectionIfEnabled { |
126 template<typename VisitorDispatcher> | 134 template<typename VisitorDispatcher> |
127 static bool trace(VisitorDispatcher visitor, T& t) | 135 static bool trace(VisitorDispatcher visitor, T& t) |
128 { | 136 { |
137 static_assert(WTF::NeedsTracingTrait<Traits>::value || weakHandlingFlag == WTF::WeakHandlingInCollections, "Traits should be traced"); | |
129 return WTF::TraceInCollectionTrait<weakHandlingFlag, strongify, T, Trait s>::trace(visitor, t); | 138 return WTF::TraceInCollectionTrait<weakHandlingFlag, strongify, T, Trait s>::trace(visitor, t); |
130 } | 139 } |
131 }; | 140 }; |
132 | 141 |
133 // The TraceTrait is used to specify how to mark an object pointer and | 142 // The TraceTrait is used to specify how to mark an object pointer and |
134 // how to trace all of the pointers in the object. | 143 // how to trace all of the pointers in the object. |
135 // | 144 // |
136 // By default, the 'trace' method implemented on an object itself is | 145 // By default, the 'trace' method implemented on an object itself is |
137 // used to trace the pointers to other heap objects inside the object. | 146 // used to trace the pointers to other heap objects inside the object. |
138 // | 147 // |
(...skipping 13 matching lines...) Expand all Loading... | |
152 { | 161 { |
153 AdjustAndMarkTrait<T>::mark(visitor, t); | 162 AdjustAndMarkTrait<T>::mark(visitor, t); |
154 } | 163 } |
155 }; | 164 }; |
156 | 165 |
157 template<typename T> class TraceTrait<const T> : public TraceTrait<T> { }; | 166 template<typename T> class TraceTrait<const T> : public TraceTrait<T> { }; |
158 | 167 |
159 template<typename T> | 168 template<typename T> |
160 void TraceTrait<T>::trace(Visitor* visitor, void* self) | 169 void TraceTrait<T>::trace(Visitor* visitor, void* self) |
161 { | 170 { |
171 static_assert(WTF::NeedsTracing<T>::value || WTF::IsWeak<T>::value, "T shoul d be traced"); | |
162 if (visitor->markingMode() == Visitor::GlobalMarking) { | 172 if (visitor->markingMode() == Visitor::GlobalMarking) { |
163 // Switch to inlined global marking dispatch. | 173 // Switch to inlined global marking dispatch. |
164 static_cast<T*>(self)->trace(InlinedGlobalMarkingVisitor(visitor)); | 174 static_cast<T*>(self)->trace(InlinedGlobalMarkingVisitor(visitor)); |
165 } else { | 175 } else { |
166 static_cast<T*>(self)->trace(visitor); | 176 static_cast<T*>(self)->trace(visitor); |
167 } | 177 } |
168 } | 178 } |
169 | 179 |
170 template<typename T> | 180 template<typename T> |
171 void TraceTrait<T>::trace(InlinedGlobalMarkingVisitor visitor, void* self) | 181 void TraceTrait<T>::trace(InlinedGlobalMarkingVisitor visitor, void* self) |
172 { | 182 { |
183 static_assert(WTF::NeedsTracing<T>::value || WTF::IsWeak<T>::value, "T shoul d be traced"); | |
sof
2015/10/19 06:33:18
What is this assert for (in this context)? NeedsTr
| |
173 static_cast<T*>(self)->trace(visitor); | 184 static_cast<T*>(self)->trace(visitor); |
174 } | 185 } |
175 | 186 |
176 template<typename T, typename Traits> | 187 template<typename T, typename Traits> |
177 struct TraceTrait<HeapVectorBacking<T, Traits>> { | 188 struct TraceTrait<HeapVectorBacking<T, Traits>> { |
178 using Backing = HeapVectorBacking<T, Traits>; | 189 using Backing = HeapVectorBacking<T, Traits>; |
179 | 190 |
180 template<typename VisitorDispatcher> | 191 template<typename VisitorDispatcher> |
181 static void trace(VisitorDispatcher visitor, void* self) | 192 static void trace(VisitorDispatcher visitor, void* self) |
182 { | 193 { |
(...skipping 148 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
331 // handling for weakness in collections. This means that if this type | 342 // handling for weakness in collections. This means that if this type |
332 // contains WeakMember fields, they will simply be zeroed, but the entry | 343 // contains WeakMember fields, they will simply be zeroed, but the entry |
333 // will not be removed from the collection. This always happens for | 344 // will not be removed from the collection. This always happens for |
334 // things in vectors, which don't currently support special handling of | 345 // things in vectors, which don't currently support special handling of |
335 // weak elements. | 346 // weak elements. |
336 template<ShouldWeakPointersBeMarkedStrongly strongify, typename T, typename Trai ts> | 347 template<ShouldWeakPointersBeMarkedStrongly strongify, typename T, typename Trai ts> |
337 struct TraceInCollectionTrait<NoWeakHandlingInCollections, strongify, T, Traits> { | 348 struct TraceInCollectionTrait<NoWeakHandlingInCollections, strongify, T, Traits> { |
338 template<typename VisitorDispatcher> | 349 template<typename VisitorDispatcher> |
339 static bool trace(VisitorDispatcher visitor, T& t) | 350 static bool trace(VisitorDispatcher visitor, T& t) |
340 { | 351 { |
352 ASSERT(NeedsTracingTrait<Traits>::value); | |
341 visitor->trace(t); | 353 visitor->trace(t); |
342 return false; | 354 return false; |
343 } | 355 } |
344 }; | 356 }; |
345 | 357 |
346 // Catch-all for things that have HashTrait support for tracing with weakness. | 358 // Catch-all for things that have HashTrait support for tracing with weakness. |
347 template<ShouldWeakPointersBeMarkedStrongly strongify, typename T, typename Trai ts> | 359 template<ShouldWeakPointersBeMarkedStrongly strongify, typename T, typename Trai ts> |
348 struct TraceInCollectionTrait<WeakHandlingInCollections, strongify, T, Traits> { | 360 struct TraceInCollectionTrait<WeakHandlingInCollections, strongify, T, Traits> { |
349 template<typename VisitorDispatcher> | 361 template<typename VisitorDispatcher> |
350 static bool trace(VisitorDispatcher visitor, T& t) | 362 static bool trace(VisitorDispatcher visitor, T& t) |
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
412 template<ShouldWeakPointersBeMarkedStrongly strongify, typename Table> | 424 template<ShouldWeakPointersBeMarkedStrongly strongify, typename Table> |
413 struct TraceInCollectionTrait<NoWeakHandlingInCollections, strongify, blink::Hea pHashTableBacking<Table>, void> { | 425 struct TraceInCollectionTrait<NoWeakHandlingInCollections, strongify, blink::Hea pHashTableBacking<Table>, void> { |
414 using Value = typename Table::ValueType; | 426 using Value = typename Table::ValueType; |
415 using Traits = typename Table::ValueTraits; | 427 using Traits = typename Table::ValueTraits; |
416 | 428 |
417 template<typename VisitorDispatcher> | 429 template<typename VisitorDispatcher> |
418 static bool trace(VisitorDispatcher visitor, void* self) | 430 static bool trace(VisitorDispatcher visitor, void* self) |
419 { | 431 { |
420 static_assert(strongify == WTF::WeakPointersActStrong, "An on-stack Heap HashTable needs to be visited strongly."); | 432 static_assert(strongify == WTF::WeakPointersActStrong, "An on-stack Heap HashTable needs to be visited strongly."); |
421 | 433 |
434 ASSERT(NeedsTracingTrait<Traits>::value || Traits::weakHandlingFlag == W eakHandlingInCollections); | |
422 Value* array = reinterpret_cast<Value*>(self); | 435 Value* array = reinterpret_cast<Value*>(self); |
423 blink::HeapObjectHeader* header = blink::HeapObjectHeader::fromPayload(s elf); | 436 blink::HeapObjectHeader* header = blink::HeapObjectHeader::fromPayload(s elf); |
424 ASSERT(header->checkHeader()); | 437 ASSERT(header->checkHeader()); |
425 // Use the payload size as recorded by the heap to determine how many | 438 // Use the payload size as recorded by the heap to determine how many |
426 // elements to trace. | 439 // elements to trace. |
427 size_t length = header->payloadSize() / sizeof(Value); | 440 size_t length = header->payloadSize() / sizeof(Value); |
428 for (size_t i = 0; i < length; ++i) { | 441 for (size_t i = 0; i < length; ++i) { |
429 if (!HashTableHelper<Value, typename Table::ExtractorType, typename Table::KeyTraitsType>::isEmptyOrDeletedBucket(array[i])) | 442 if (!HashTableHelper<Value, typename Table::ExtractorType, typename Table::KeyTraitsType>::isEmptyOrDeletedBucket(array[i])) |
430 blink::TraceCollectionIfEnabled<NeedsTracingTrait<Traits>::value , Traits::weakHandlingFlag, strongify, Value, Traits>::trace(visitor, array[i]); | 443 blink::TraceCollectionIfEnabled<NeedsTracingTrait<Traits>::value , Traits::weakHandlingFlag, strongify, Value, Traits>::trace(visitor, array[i]); |
431 } | 444 } |
(...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
542 | 555 |
543 // ListHashSetNode pointers (a ListHashSet is implemented as a hash table of | 556 // ListHashSetNode pointers (a ListHashSet is implemented as a hash table of |
544 // these pointers). | 557 // these pointers). |
545 template<ShouldWeakPointersBeMarkedStrongly strongify, typename Value, size_t in lineCapacity, typename Traits> | 558 template<ShouldWeakPointersBeMarkedStrongly strongify, typename Value, size_t in lineCapacity, typename Traits> |
546 struct TraceInCollectionTrait<NoWeakHandlingInCollections, strongify, ListHashSe tNode<Value, blink::HeapListHashSetAllocator<Value, inlineCapacity>>*, Traits> { | 559 struct TraceInCollectionTrait<NoWeakHandlingInCollections, strongify, ListHashSe tNode<Value, blink::HeapListHashSetAllocator<Value, inlineCapacity>>*, Traits> { |
547 using Node = ListHashSetNode<Value, blink::HeapListHashSetAllocator<Value, i nlineCapacity>>; | 560 using Node = ListHashSetNode<Value, blink::HeapListHashSetAllocator<Value, i nlineCapacity>>; |
548 | 561 |
549 template<typename VisitorDispatcher> | 562 template<typename VisitorDispatcher> |
550 static bool trace(VisitorDispatcher visitor, Node* node) | 563 static bool trace(VisitorDispatcher visitor, Node* node) |
551 { | 564 { |
565 ASSERT(NeedsTracingTrait<Traits>::value); | |
552 traceListHashSetValue(visitor, node->m_value); | 566 traceListHashSetValue(visitor, node->m_value); |
553 // Just mark the node without tracing because we already traced the | 567 // Just mark the node without tracing because we already traced the |
554 // contents, and there is no need to trace the next and prev fields | 568 // contents, and there is no need to trace the next and prev fields |
555 // since iterating over the hash table backing will find the whole | 569 // since iterating over the hash table backing will find the whole |
556 // chain. | 570 // chain. |
557 visitor->markNoTracing(node); | 571 visitor->markNoTracing(node); |
558 return false; | 572 return false; |
559 } | 573 } |
560 }; | 574 }; |
561 | 575 |
562 } // namespace WTF | 576 } // namespace WTF |
563 | 577 |
564 #endif | 578 #endif |
OLD | NEW |