Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(312)

Side by Side Diff: Source/heap/Handle.h

Issue 131803005: Add more oilpan collections support (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Created 6 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « no previous file | Source/heap/Heap.h » ('j') | Source/heap/Heap.h » ('J')
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2014 Google Inc. All rights reserved. 2 * Copyright (C) 2014 Google Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are 5 * modification, are permitted provided that the following conditions are
6 * met: 6 * met:
7 * 7 *
8 * * Redistributions of source code must retain the above copyright 8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above 10 * * Redistributions in binary form must reproduce the above
(...skipping 20 matching lines...) Expand all
31 #ifndef Handle_h 31 #ifndef Handle_h
32 #define Handle_h 32 #define Handle_h
33 33
34 #include "heap/Heap.h" 34 #include "heap/Heap.h"
35 #include "heap/ThreadState.h" 35 #include "heap/ThreadState.h"
36 #include "heap/Visitor.h" 36 #include "heap/Visitor.h"
37 37
38 namespace WebCore { 38 namespace WebCore {
39 39
40 template<typename T> class Member; 40 template<typename T> class Member;
41 template<typename T> struct OffHeapCollectionTraceTrait;
41 42
42 class PersistentNode { 43 class PersistentNode {
43 public: 44 public:
44 explicit PersistentNode(TraceCallback trace) : m_trace(trace) { } 45 explicit PersistentNode(TraceCallback trace)
46 : m_trace(trace)
47 #ifndef NDEBUG
Mads Ager (chromium) 2014/01/15 08:48:17 Thanks for adding verification; that should make f
48 , m_alive(true)
49 #endif
50 {
51 }
45 52
46 virtual ~PersistentNode() { } 53 virtual ~PersistentNode()
54 {
55 #ifndef NDEBUG
56 ASSERT(m_alive);
57 m_alive = false;
58 #endif
59 }
47 60
48 // Ideally the trace method should be virtual and automatically dispatch 61 // Ideally the trace method should be virtual and automatically dispatch
49 // to the most specific implementation. However having a virtual method 62 // to the most specific implementation. However having a virtual method
50 // on PersistentNode leads to too eager template instantiation with MSVC 63 // on PersistentNode leads to too eager template instantiation with MSVC
51 // which leads to include cycles. 64 // which leads to include cycles.
52 // Instead we call the constructor with a TraceCallback which knows the 65 // Instead we call the constructor with a TraceCallback which knows the
53 // type of the most specific child and calls trace directly. See 66 // type of the most specific child and calls trace directly. See
54 // TraceMethodDelegate in Visitor.h for how this is done. 67 // TraceMethodDelegate in Visitor.h for how this is done.
55 void trace(Visitor* visitor) 68 void trace(Visitor* visitor)
56 { 69 {
57 m_trace(visitor, this); 70 m_trace(visitor, this);
58 } 71 }
59 72
60 protected: 73 protected:
61 TraceCallback m_trace; 74 TraceCallback m_trace;
62 75
76 #ifndef NDEBUG
77 bool m_alive;
78 #endif
79
63 private: 80 private:
64 PersistentNode* m_next; 81 PersistentNode* m_next;
65 PersistentNode* m_prev; 82 PersistentNode* m_prev;
66 83
67 template<ThreadAffinity affinity, typename Owner> friend class PersistentBas e; 84 template<ThreadAffinity affinity, typename Owner> friend class PersistentBas e;
68 friend class PersistentAnchor; 85 friend class PersistentAnchor;
69 friend class ThreadState; 86 friend class ThreadState;
70 }; 87 };
71 88
72 template<ThreadAffinity Affinity, typename Owner> 89 template<ThreadAffinity Affinity, typename Owner>
73 class PersistentBase : public PersistentNode { 90 class PersistentBase : public PersistentNode {
74 public: 91 public:
75 ~PersistentBase() 92 ~PersistentBase()
76 { 93 {
77 #ifndef NDEBUG 94 #ifndef NDEBUG
95 ASSERT(m_alive);
96 ASSERT(m_next->m_alive);
97 ASSERT(m_prev->m_alive);
78 m_threadState->checkThread(); 98 m_threadState->checkThread();
79 #endif 99 #endif
80 m_next->m_prev = m_prev; 100 m_next->m_prev = m_prev;
81 m_prev->m_next = m_next; 101 m_prev->m_next = m_next;
82 } 102 }
83 103
84 protected: 104 protected:
85 inline PersistentBase() 105 inline PersistentBase()
86 : PersistentNode(TraceMethodDelegate<Owner, &Owner::trace>::trampoline) 106 : PersistentNode(TraceMethodDelegate<Owner, &Owner::trace>::trampoline)
87 #ifndef NDEBUG 107 #ifndef NDEBUG
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
128 #endif 148 #endif
129 }; 149 };
130 150
131 // A dummy Persistent handle that ensures the list of persistents is never null. 151 // A dummy Persistent handle that ensures the list of persistents is never null.
132 // This removes a test from a hot path. 152 // This removes a test from a hot path.
133 class PersistentAnchor : public PersistentNode { 153 class PersistentAnchor : public PersistentNode {
134 public: 154 public:
135 void trace(Visitor*) { } 155 void trace(Visitor*) { }
136 156
137 private: 157 private:
138 virtual ~PersistentAnchor() { } 158 virtual ~PersistentAnchor()
159 {
160 ASSERT(m_next == this);
161 ASSERT(m_prev == this);
162 }
139 PersistentAnchor() : PersistentNode(TraceMethodDelegate<PersistentAnchor, &P ersistentAnchor::trace>::trampoline) 163 PersistentAnchor() : PersistentNode(TraceMethodDelegate<PersistentAnchor, &P ersistentAnchor::trace>::trampoline)
140 { 164 {
141 m_next = this; 165 m_next = this;
142 m_prev = this; 166 m_prev = this;
143 } 167 }
144 168
145 friend class ThreadState; 169 friend class ThreadState;
146 }; 170 };
147 171
148 // Persistent handles are used to store pointers into the 172 // Persistent handles are used to store pointers into the
(...skipping 165 matching lines...) Expand 10 before | Expand all | Expand 10 after
314 338
315 template<typename U> 339 template<typename U>
316 Member& operator=(U* other) 340 Member& operator=(U* other)
317 { 341 {
318 m_raw = other; 342 m_raw = other;
319 return *this; 343 return *this;
320 } 344 }
321 345
322 void swap(Member<T>& other) { std::swap(m_raw, other.m_raw); } 346 void swap(Member<T>& other) { std::swap(m_raw, other.m_raw); }
323 347
324 protected:
325 T* raw() const { return m_raw; } 348 T* raw() const { return m_raw; }
326 349
350 protected:
haraken 2014/01/15 04:48:35 Don't we want private here?
zerny-chromium 2014/01/15 08:05:27 WeakMember needs access to m_raw. btw, most of th
Mads Ager (chromium) 2014/01/15 08:48:17 Drive-by answer. :-) We don't need private here.
327 T* m_raw; 351 T* m_raw;
328 352
329 template<typename U> friend class Member; 353 template<typename U> friend class Member;
330 template<typename U> friend class Persistent; 354 template<typename U> friend class Persistent;
331 friend class Visitor; 355 friend class Visitor;
332 template<typename U> friend struct WTF::PtrHash; 356 template<typename U> friend struct WTF::PtrHash;
333 // FIXME: Uncomment when HeapObjectHash is moved. 357 // FIXME: Uncomment when HeapObjectHash is moved.
334 // friend struct HeapObjectHash<T>; 358 // friend struct HeapObjectHash<T>;
335 friend struct ObjectAliveTrait<Member<T> >; 359 friend struct ObjectAliveTrait<Member<T> >;
336 template<bool x, bool y, bool z, typename U, typename V> friend struct Colle ctionBackingTraceTrait; 360 template<bool x, bool y, bool z, typename U, typename V> friend struct Colle ctionBackingTraceTrait;
337 template<typename U, typename V> friend bool operator==(const Member<U>&, co nst Persistent<V>&); 361 template<typename U, typename V> friend bool operator==(const Member<U>&, co nst Persistent<V>&);
Mads Ager (chromium) 2014/01/15 08:48:17 Let's git rid of all of these operator friend decl
338 template<typename U, typename V> friend bool operator!=(const Member<U>&, co nst Persistent<V>&); 362 template<typename U, typename V> friend bool operator!=(const Member<U>&, co nst Persistent<V>&);
339 template<typename U, typename V> friend bool operator==(const Persistent<U>& , const Member<V>&); 363 template<typename U, typename V> friend bool operator==(const Persistent<U>& , const Member<V>&);
340 template<typename U, typename V> friend bool operator!=(const Persistent<U>& , const Member<V>&); 364 template<typename U, typename V> friend bool operator!=(const Persistent<U>& , const Member<V>&);
341 template<typename U, typename V> friend bool operator==(const Member<U>&, co nst Member<V>&); 365 template<typename U, typename V> friend bool operator==(const Member<U>&, co nst Member<V>&);
342 template<typename U, typename V> friend bool operator!=(const Member<U>&, co nst Member<V>&); 366 template<typename U, typename V> friend bool operator!=(const Member<U>&, co nst Member<V>&);
343 }; 367 };
344 368
345 template<typename T> 369 template<typename T>
346 class TraceTrait<Member<T> > { 370 class TraceTrait<Member<T> > {
347 public: 371 public:
(...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after
410 friend class Visitor; 434 friend class Visitor;
411 template<typename U> friend struct WTF::PtrHash; 435 template<typename U> friend struct WTF::PtrHash;
412 // FIXME: Uncomment when moving HeapObjectHash to trunk. 436 // FIXME: Uncomment when moving HeapObjectHash to trunk.
413 // friend struct HeapObjectHash<T>; 437 // friend struct HeapObjectHash<T>;
414 friend struct ObjectAliveTrait<WeakMember<T> >; 438 friend struct ObjectAliveTrait<WeakMember<T> >;
415 }; 439 };
416 440
417 // Comparison operators between (Weak)Members and Persistents 441 // Comparison operators between (Weak)Members and Persistents
418 template<typename T, typename U> inline bool operator==(const Member<T>& a, cons t Member<U>& b) { return a.m_raw == b.m_raw; } 442 template<typename T, typename U> inline bool operator==(const Member<T>& a, cons t Member<U>& b) { return a.m_raw == b.m_raw; }
419 template<typename T, typename U> inline bool operator!=(const Member<T>& a, cons t Member<U>& b) { return a.m_raw != b.m_raw; } 443 template<typename T, typename U> inline bool operator!=(const Member<T>& a, cons t Member<U>& b) { return a.m_raw != b.m_raw; }
420 template<typename T, typename U> inline bool operator==(const Member<T>& a, cons t Persistent<U>& b) { return a.m_raw == b.m_raw; } 444 template<typename T, typename U> inline bool operator==(const Member<T>& a, cons t Persistent<U>& b) { return a.m_raw == b.raw(); }
Mads Ager (chromium) 2014/01/15 08:48:17 This is a complete mess. Let us just use a.get() =
421 template<typename T, typename U> inline bool operator!=(const Member<T>& a, cons t Persistent<U>& b) { return a.m_raw != b.m_raw; } 445 template<typename T, typename U> inline bool operator!=(const Member<T>& a, cons t Persistent<U>& b) { return a.m_raw != b.raw(); }
422 template<typename T, typename U> inline bool operator==(const Persistent<T>& a, const Member<U>& b) { return a.m_raw == b.m_raw; } 446 template<typename T, typename U> inline bool operator==(const Persistent<T>& a, const Member<U>& b) { return a.raw() == b.m_raw; }
423 template<typename T, typename U> inline bool operator!=(const Persistent<T>& a, const Member<U>& b) { return a.m_raw != b.m_raw; } 447 template<typename T, typename U> inline bool operator!=(const Persistent<T>& a, const Member<U>& b) { return a.raw() != b.m_raw; }
424 template<typename T, typename U> inline bool operator==(const Persistent<T>& a, const Persistent<U>& b) { return a.m_raw == b.m_raw; } 448 template<typename T, typename U> inline bool operator==(const Persistent<T>& a, const Persistent<U>& b) { return a.raw() == b.raw(); }
425 template<typename T, typename U> inline bool operator!=(const Persistent<T>& a, const Persistent<U>& b) { return a.m_raw != b.m_raw; } 449 template<typename T, typename U> inline bool operator!=(const Persistent<T>& a, const Persistent<U>& b) { return a.raw() != b.raw(); }
450
451 template<typename Collection, ThreadAffinity Affinity = MainThreadOnly> class Co llectionPersistent;
452
453 // Used to inject correctly typed operator[] into CollectionPersistent when we a re wrapping Vector.
454 template<typename T> class IndexingBehavior { };
455
456 template<typename T, size_t inlineCapacity>
457 class IndexingBehavior<CollectionPersistent<Vector<T, inlineCapacity, WTF::Defau ltAllocator> > > {
458 typedef CollectionPersistent<Vector<T, inlineCapacity, WTF::DefaultAllocator > > CollectionPersistentType;
459 public:
460 T& operator[] (size_t i) { return (**static_cast<CollectionPersistentType*>( this))[i]; }
461 const T& operator[] (size_t i) const { return (**static_cast<const Collectio nPersistentType*>(this))[i]; }
462 };
463
464 template<typename Collection, ThreadAffinity Affinity>
465 class CollectionPersistent
466 : public PersistentBase<Affinity, CollectionPersistent<Collection, Affinity> >
467 , public IndexingBehavior<CollectionPersistent<Collection, Affinity> > {
468 public:
469 typedef Collection CollectionType;
470 typedef typename Collection::iterator iterator;
471 typedef typename Collection::const_iterator const_iterator;
472
473 CollectionPersistent() { }
474 explicit CollectionPersistent(size_t size) : m_collection(Collection(size)) { }
475 explicit CollectionPersistent(const Collection& collection) : m_collection(c ollection) { }
476 CollectionPersistent& operator=(const Collection& collection) { m_collection = collection; return *this; }
477 Collection* operator->() { return &m_collection; }
478 const Collection* operator->() const { return &m_collection; }
479 Collection& operator*() { return m_collection; }
480 const Collection& operator*() const { return m_collection; }
481
482 void trace(Visitor* visitor)
483 {
484 OffHeapCollectionTraceTrait<Collection>::mark(visitor, m_collection); }
haraken 2014/01/15 04:48:35 Write } in the next line.
Erik Corry 2014/01/15 09:27:32 Done.
485
486 #if defined(TRACE_GC_MARKING) && TRACE_GC_MARKING
487 virtual const char* name() OVERRIDE
488 {
489 ASSERT(this == static_cast<PersistentNode*>(this));
490 const char* n = FieldAnnotationBase::fromAddress(this);
491 return n ? n : "CollectionPersistent";
492 }
493 #endif
494
495 private:
496 Collection m_collection;
497 };
426 498
427 } // namespace WebCore 499 } // namespace WebCore
428 500
429 namespace WTF { 501 namespace WTF {
430 502
431 template <typename T> struct VectorTraits<WebCore::Member<T> > : VectorTraitsBas e<false, WebCore::Member<T> > { 503 template <typename T> struct VectorTraits<WebCore::Member<T> > : VectorTraitsBas e<false, WebCore::Member<T> > {
432 static const bool needsDestruction = false; 504 static const bool needsDestruction = false;
433 static const bool canInitializeWithMemset = true; 505 static const bool canInitializeWithMemset = true;
434 static const bool canMoveWithMemcpy = true; 506 static const bool canMoveWithMemcpy = true;
435 }; 507 };
436 508
437 template <typename T> struct VectorTraits<WebCore::WeakMember<T> > : VectorTrait sBase<false, WebCore::WeakMember<T> > { 509 template <typename T> struct VectorTraits<WebCore::WeakMember<T> > : VectorTrait sBase<false, WebCore::WeakMember<T> > {
438 static const bool needsDestruction = false; 510 static const bool needsDestruction = false;
439 static const bool canInitializeWithMemset = true; 511 static const bool canInitializeWithMemset = true;
440 static const bool canMoveWithMemcpy = true; 512 static const bool canMoveWithMemcpy = true;
441 }; 513 };
442 514
443 template<typename T> struct HashTraits<WebCore::Member<T> > : SimpleClassHashTra its<WebCore::Member<T> > { 515 template<typename T> struct HashTraits<WebCore::Member<T> > : SimpleClassHashTra its<WebCore::Member<T> > {
444 static const bool needsDestruction = false; 516 static const bool needsDestruction = false;
445 // FIXME: The distinction between PeekInType and PassInType is there for 517 // FIXME: The distinction between PeekInType and PassInType is there for
446 // the sake of the reference counting handles. When they are gone the two 518 // the sake of the reference counting handles. When they are gone the two
447 // types can be merged into PassInType. 519 // types can be merged into PassInType.
448 // FIXME: Implement proper const'ness for iterator types. Requires support 520 // FIXME: Implement proper const'ness for iterator types. Requires support
449 // in the marking Visitor. 521 // in the marking Visitor.
450 typedef T* PeekInType; 522 typedef T* PeekInType;
451 typedef T* PassInType; 523 typedef T* PassInType;
452 typedef T* IteratorGetType; 524 typedef WebCore::Member<T>* IteratorGetType;
453 typedef T* IteratorConstGetType; 525 typedef const WebCore::Member<T>* IteratorConstGetType;
454 typedef T* IteratorReferenceType; 526 typedef T* IteratorReferenceType;
455 typedef T* IteratorConstReferenceType; 527 typedef T* IteratorConstReferenceType;
456 static IteratorConstGetType getToConstGetConversion(const WebCore::Member<T> * x) { return x->raw(); } 528 static IteratorConstGetType getToConstGetConversion(const WebCore::Member<T> * x) { return x->raw(); }
457 static IteratorReferenceType getToReferenceConversion(IteratorGetType x) { r eturn x; } 529 static IteratorReferenceType getToReferenceConversion(IteratorGetType x) { r eturn x->raw(); }
458 static IteratorConstReferenceType getToReferenceConstConversion(IteratorCons tGetType x) { return x; } 530 static IteratorConstReferenceType getToReferenceConstConversion(IteratorCons tGetType x) { return x->raw(); }
459 // FIXME: Similarly, there is no need for a distinction between PeekOutType 531 // FIXME: Similarly, there is no need for a distinction between PeekOutType
460 // and PassOutType without reference counting. 532 // and PassOutType without reference counting.
461 typedef T* PeekOutType; 533 typedef T* PeekOutType;
462 typedef T* PassOutType; 534 typedef T* PassOutType;
463 535
464 template<typename U> 536 template<typename U>
465 static void store(const U& value, WebCore::Member<T>& storage) { storage = v alue; } 537 static void store(const U& value, WebCore::Member<T>& storage) { storage = v alue; }
466 538
467 static PeekOutType peek(const WebCore::Member<T>& value) { return value; } 539 static PeekOutType peek(const WebCore::Member<T>& value) { return value; }
468 static PassOutType passOut(const WebCore::Member<T>& value) { return value; } 540 static PassOutType passOut(const WebCore::Member<T>& value) { return value; }
469 }; 541 };
470 542
471 template<typename T> struct HashTraits<WebCore::WeakMember<T> > : SimpleClassHas hTraits<WebCore::WeakMember<T> > { 543 template<typename T> struct HashTraits<WebCore::WeakMember<T> > : SimpleClassHas hTraits<WebCore::WeakMember<T> > {
472 static const bool needsDestruction = false; 544 static const bool needsDestruction = false;
473 // FIXME: The distinction between PeekInType and PassInType is there for 545 // FIXME: The distinction between PeekInType and PassInType is there for
474 // the sake of the reference counting handles. When they are gone the two 546 // the sake of the reference counting handles. When they are gone the two
475 // types can be merged into PassInType. 547 // types can be merged into PassInType.
476 // FIXME: Implement proper const'ness for iterator types. Requires support 548 // FIXME: Implement proper const'ness for iterator types. Requires support
477 // in the marking Visitor. 549 // in the marking Visitor.
478 typedef T* PeekInType; 550 typedef T* PeekInType;
479 typedef T* PassInType; 551 typedef T* PassInType;
480 typedef T* IteratorGetType; 552 typedef WebCore::WeakMember<T>* IteratorGetType;
481 typedef T* IteratorConstGetType; 553 typedef const WebCore::WeakMember<T>* IteratorConstGetType;
482 typedef T* IteratorReferenceType; 554 typedef T* IteratorReferenceType;
483 typedef T* IteratorConstReferenceType; 555 typedef T* IteratorConstReferenceType;
484 static IteratorConstGetType getToConstGetConversion(const WebCore::WeakMembe r<T>* x) { return x->raw(); } 556 static IteratorConstGetType getToConstGetConversion(const WebCore::WeakMembe r<T>* x) { return x->raw(); }
485 static IteratorReferenceType getToReferenceConversion(IteratorGetType x) { r eturn x; } 557 static IteratorReferenceType getToReferenceConversion(IteratorGetType x) { r eturn x->raw(); }
486 static IteratorConstReferenceType getToReferenceConstConversion(IteratorCons tGetType x) { return x; } 558 static IteratorConstReferenceType getToReferenceConstConversion(IteratorCons tGetType x) { return x->raw(); }
487 // FIXME: Similarly, there is no need for a distinction between PeekOutType 559 // FIXME: Similarly, there is no need for a distinction between PeekOutType
488 // and PassOutType without reference counting. 560 // and PassOutType without reference counting.
489 typedef T* PeekOutType; 561 typedef T* PeekOutType;
490 typedef T* PassOutType; 562 typedef T* PassOutType;
491 563
492 template<typename U> 564 template<typename U>
493 static void store(const U& value, WebCore::WeakMember<T>& storage) { storage = value; } 565 static void store(const U& value, WebCore::WeakMember<T>& storage) { storage = value; }
494 566
495 static PeekOutType peek(const WebCore::WeakMember<T>& value) { return value; } 567 static PeekOutType peek(const WebCore::WeakMember<T>& value) { return value; }
496 static PassOutType passOut(const WebCore::WeakMember<T>& value) { return val ue; } 568 static PassOutType passOut(const WebCore::WeakMember<T>& value) { return val ue; }
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
528 }; 600 };
529 601
530 template<typename Key, typename Value, typename Extractor, typename Traits, type name KeyTraits> 602 template<typename Key, typename Value, typename Extractor, typename Traits, type name KeyTraits>
531 struct IsWeak<WebCore::HeapHashTableBacking<Key, Value, Extractor, Traits, KeyTr aits> > { 603 struct IsWeak<WebCore::HeapHashTableBacking<Key, Value, Extractor, Traits, KeyTr aits> > {
532 static const bool value = Traits::isWeak; 604 static const bool value = Traits::isWeak;
533 }; 605 };
534 606
535 } // namespace WTF 607 } // namespace WTF
536 608
537 #endif 609 #endif
OLDNEW
« no previous file with comments | « no previous file | Source/heap/Heap.h » ('j') | Source/heap/Heap.h » ('J')

Powered by Google App Engine
This is Rietveld 408576698