OLD | NEW |
---|---|
1 /* | 1 /* |
2 * Copyright (C) 2010 Google Inc. All rights reserved. | 2 * Copyright (C) 2010 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 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
46 namespace blink { | 46 namespace blink { |
47 | 47 |
48 // By default, the destruction of a WebPrivatePtr<> must happen on the same | 48 // By default, the destruction of a WebPrivatePtr<> must happen on the same |
49 // thread that created it, but can optionally be allowed to happen on | 49 // thread that created it, but can optionally be allowed to happen on |
50 // another thread. | 50 // another thread. |
51 enum WebPrivatePtrDestruction { | 51 enum WebPrivatePtrDestruction { |
52 WebPrivatePtrDestructionSameThread, | 52 WebPrivatePtrDestructionSameThread, |
53 WebPrivatePtrDestructionCrossThread, | 53 WebPrivatePtrDestructionCrossThread, |
54 }; | 54 }; |
55 | 55 |
56 // The WebPrivatePtr<> holds by default a strong reference to its Blink object, | |
57 // but Blink GC managed objects also support keeping a weak reference by | |
58 // way of WebPrivatePtr<>. | |
59 enum class WebPrivatePtrStrength { | |
60 Normal, | |
61 Weak, | |
62 }; | |
63 | |
56 #if INSIDE_BLINK | 64 #if INSIDE_BLINK |
57 enum LifetimeManagementType { | 65 enum LifetimeManagementType { |
58 RefCountedLifetime, | 66 RefCountedLifetime, |
59 GarbageCollectedLifetime, | 67 GarbageCollectedLifetime, |
60 RefCountedGarbageCollectedLifetime | 68 RefCountedGarbageCollectedLifetime |
61 }; | 69 }; |
62 | 70 |
63 template<typename T> | 71 template<typename T> |
64 class LifetimeOf { | 72 class LifetimeOf { |
65 static const bool isGarbageCollected = WTF::IsSubclassOfTemplate<T, GarbageC ollected>::value || IsGarbageCollectedMixin<T>::value; | 73 static const bool isGarbageCollected = WTF::IsSubclassOfTemplate<T, GarbageC ollected>::value || IsGarbageCollectedMixin<T>::value; |
66 static const bool isRefCountedGarbageCollected = WTF::IsSubclassOfTemplate<T , RefCountedGarbageCollected>::value; | 74 static const bool isRefCountedGarbageCollected = WTF::IsSubclassOfTemplate<T , RefCountedGarbageCollected>::value; |
67 public: | 75 public: |
68 static const LifetimeManagementType value = | 76 static const LifetimeManagementType value = |
69 !isGarbageCollected ? RefCountedLifetime : | 77 !isGarbageCollected ? RefCountedLifetime : |
70 isRefCountedGarbageCollected ? RefCountedGarbageCollectedLifetime : Garb ageCollectedLifetime; | 78 isRefCountedGarbageCollected ? RefCountedGarbageCollectedLifetime : Garb ageCollectedLifetime; |
71 }; | 79 }; |
72 | 80 |
73 template<typename T, WebPrivatePtrDestruction crossThreadDestruction, LifetimeMa nagementType lifetime> | 81 template<typename T, WebPrivatePtrDestruction crossThreadDestruction, WebPrivate PtrStrength strongOrWeak, LifetimeManagementType lifetime> |
74 class PtrStorageImpl; | 82 class PtrStorageImpl; |
75 | 83 |
76 template<typename T, WebPrivatePtrDestruction crossThreadDestruction> | 84 template<typename T, WebPrivatePtrDestruction crossThreadDestruction, WebPrivate PtrStrength strongOrWeak> |
77 class PtrStorageImpl<T, crossThreadDestruction, RefCountedLifetime> { | 85 class PtrStorageImpl<T, crossThreadDestruction, strongOrWeak, RefCountedLifetime > { |
78 public: | 86 public: |
79 typedef PassRefPtr<T> BlinkPtrType; | 87 typedef PassRefPtr<T> BlinkPtrType; |
80 | 88 |
81 void assign(const BlinkPtrType& val) | 89 void assign(const BlinkPtrType& val) |
82 { | 90 { |
83 static_assert(crossThreadDestruction == WebPrivatePtrDestructionSameThre ad || WTF::IsSubclassOfTemplate<T, WTF::ThreadSafeRefCounted>::value, "Cross thr ead destructible class must derive from ThreadSafeRefCounted<>"); | 91 static_assert(crossThreadDestruction == WebPrivatePtrDestructionSameThre ad || WTF::IsSubclassOfTemplate<T, WTF::ThreadSafeRefCounted>::value, "Cross thr ead destructible class must derive from ThreadSafeRefCounted<>"); |
92 static_assert(strongOrWeak == WebPrivatePtrStrength::Normal, "Ref-counte d classes do not support weak WebPrivatePtr<> references"); | |
84 release(); | 93 release(); |
85 m_ptr = val.leakRef(); | 94 m_ptr = val.leakRef(); |
86 } | 95 } |
87 | 96 |
88 void assign(const PtrStorageImpl& other) | 97 void assign(const PtrStorageImpl& other) |
89 { | 98 { |
90 release(); | 99 release(); |
91 T* val = other.get(); | 100 T* val = other.get(); |
92 WTF::refIfNotNull(val); | 101 WTF::refIfNotNull(val); |
93 m_ptr = val; | 102 m_ptr = val; |
(...skipping 11 matching lines...) Expand all Loading... | |
105 void release() | 114 void release() |
106 { | 115 { |
107 WTF::derefIfNotNull(m_ptr); | 116 WTF::derefIfNotNull(m_ptr); |
108 m_ptr = 0; | 117 m_ptr = 0; |
109 } | 118 } |
110 | 119 |
111 private: | 120 private: |
112 T* m_ptr; | 121 T* m_ptr; |
113 }; | 122 }; |
114 | 123 |
115 template <typename T, WebPrivatePtrDestruction> | 124 template <typename T, WebPrivatePtrDestruction, WebPrivatePtrStrength> |
116 struct WebPrivatePtrPersistentStorageType { | 125 struct WebPrivatePtrPersistentStorageType { |
117 public: | 126 public: |
118 using Type = Persistent<T>; | 127 using Type = Persistent<T>; |
119 }; | 128 }; |
120 | 129 |
121 template <typename T> | 130 template <typename T> |
122 struct WebPrivatePtrPersistentStorageType<T, WebPrivatePtrDestructionCrossThread > { | 131 struct WebPrivatePtrPersistentStorageType<T, WebPrivatePtrDestructionSameThread, WebPrivatePtrStrength::Weak> { |
132 public: | |
133 using Type = WeakPersistent<T>; | |
134 }; | |
135 | |
136 template <typename T> | |
137 struct WebPrivatePtrPersistentStorageType<T, WebPrivatePtrDestructionCrossThread , WebPrivatePtrStrength::Normal> { | |
123 public: | 138 public: |
124 using Type = CrossThreadPersistent<T>; | 139 using Type = CrossThreadPersistent<T>; |
125 }; | 140 }; |
126 | 141 |
127 template<typename T, WebPrivatePtrDestruction crossThreadDestruction> | 142 template <typename T> |
128 class PtrStorageImpl<T, crossThreadDestruction, GarbageCollectedLifetime> { | 143 struct WebPrivatePtrPersistentStorageType<T, WebPrivatePtrDestructionCrossThread , WebPrivatePtrStrength::Weak> { |
144 public: | |
145 using Type = CrossThreadWeakPersistent<T>; | |
146 }; | |
147 | |
148 template<typename T, WebPrivatePtrDestruction crossThreadDestruction, WebPrivate PtrStrength strongOrWeak> | |
149 class PtrStorageImpl<T, crossThreadDestruction, strongOrWeak, GarbageCollect edLifetime> { | |
hiroshige
2016/01/27 03:55:01
nit: no indent needed here.
sof
2016/01/29 09:12:23
oops, thanks for catching that.
| |
129 public: | 150 public: |
130 void assign(const RawPtr<T>& val) | 151 void assign(const RawPtr<T>& val) |
131 { | 152 { |
132 if (!val) { | 153 if (!val) { |
133 release(); | 154 release(); |
134 return; | 155 return; |
135 } | 156 } |
136 | 157 |
137 if (!m_handle) | 158 if (!m_handle) |
138 m_handle = new (typename WebPrivatePtrPersistentStorageType<T, cross ThreadDestruction>::Type)(); | 159 m_handle = new (typename WebPrivatePtrPersistentStorageType<T, cross ThreadDestruction, strongOrWeak>::Type)(); |
139 | 160 |
140 (*m_handle) = val; | 161 (*m_handle) = val; |
141 } | 162 } |
142 | 163 |
143 void assign(T* ptr) { assign(RawPtr<T>(ptr)); } | 164 void assign(T* ptr) { assign(RawPtr<T>(ptr)); } |
144 template<typename U> void assign(const RawPtr<U>& val) { assign(RawPtr<T>(va l)); } | 165 template<typename U> void assign(const RawPtr<U>& val) { assign(RawPtr<T>(va l)); } |
145 | 166 |
146 void assign(const PtrStorageImpl& other) { assign(other.get()); } | 167 void assign(const PtrStorageImpl& other) { assign(other.get()); } |
147 | 168 |
148 void moveFrom(PtrStorageImpl& other) | 169 void moveFrom(PtrStorageImpl& other) |
149 { | 170 { |
150 release(); | 171 release(); |
151 m_handle = other.m_handle; | 172 m_handle = other.m_handle; |
152 other.m_handle = 0; | 173 other.m_handle = 0; |
153 } | 174 } |
154 | 175 |
155 T* get() const { return m_handle ? m_handle->get() : 0; } | 176 T* get() const { return m_handle ? m_handle->get() : 0; } |
156 | 177 |
157 void release() | 178 void release() |
158 { | 179 { |
159 delete m_handle; | 180 delete m_handle; |
160 m_handle = 0; | 181 m_handle = 0; |
161 } | 182 } |
162 | 183 |
163 private: | 184 private: |
164 typename WebPrivatePtrPersistentStorageType<T, crossThreadDestruction>::Type * m_handle; | 185 typename WebPrivatePtrPersistentStorageType<T, crossThreadDestruction, stron gOrWeak>::Type* m_handle; |
165 }; | 186 }; |
166 | 187 |
167 template<typename T, WebPrivatePtrDestruction crossThreadDestruction> | 188 template<typename T, WebPrivatePtrDestruction crossThreadDestruction, WebPrivate PtrStrength strongOrWeak> |
168 class PtrStorageImpl<T, crossThreadDestruction, RefCountedGarbageCollectedLifeti me> : public PtrStorageImpl<T, crossThreadDestruction, GarbageCollectedLifetime> { | 189 class PtrStorageImpl<T, crossThreadDestruction, strongOrWeak, RefCountedGarbageC ollectedLifetime> : public PtrStorageImpl<T, crossThreadDestruction, strongOrWea k, GarbageCollectedLifetime> { |
169 public: | 190 public: |
170 void assign(const PassRefPtrWillBeRawPtr<T>& val) { PtrStorageImpl<T, crossT hreadDestruction, GarbageCollectedLifetime>::assign(val.get()); } | 191 void assign(const PassRefPtrWillBeRawPtr<T>& val) { PtrStorageImpl<T, crossT hreadDestruction, strongOrWeak, GarbageCollectedLifetime>::assign(val.get()); } |
171 | 192 |
172 void assign(const PtrStorageImpl& other) { PtrStorageImpl<T, crossThreadDest ruction, GarbageCollectedLifetime>::assign(other.get()); } | 193 void assign(const PtrStorageImpl& other) { PtrStorageImpl<T, crossThreadDest ruction, strongOrWeak, GarbageCollectedLifetime>::assign(other.get()); } |
173 }; | 194 }; |
174 | 195 |
175 template<typename T, WebPrivatePtrDestruction crossThreadDestruction> | 196 template<typename T, WebPrivatePtrDestruction crossThreadDestruction, WebPrivate PtrStrength strongOrWeak> |
176 class PtrStorage : public PtrStorageImpl<T, crossThreadDestruction, LifetimeOf<T >::value> { | 197 class PtrStorage : public PtrStorageImpl<T, crossThreadDestruction, strongOrWeak , LifetimeOf<T>::value> { |
177 public: | 198 public: |
178 static PtrStorage& fromSlot(void** slot) | 199 static PtrStorage& fromSlot(void** slot) |
179 { | 200 { |
180 static_assert(sizeof(PtrStorage) == sizeof(void*), "PtrStorage must be t he size of a pointer"); | 201 static_assert(sizeof(PtrStorage) == sizeof(void*), "PtrStorage must be t he size of a pointer"); |
181 return *reinterpret_cast<PtrStorage*>(slot); | 202 return *reinterpret_cast<PtrStorage*>(slot); |
182 } | 203 } |
183 | 204 |
184 static const PtrStorage& fromSlot(void* const* slot) | 205 static const PtrStorage& fromSlot(void* const* slot) |
185 { | 206 { |
186 static_assert(sizeof(PtrStorage) == sizeof(void*), "PtrStorage must be t he size of a pointer"); | 207 static_assert(sizeof(PtrStorage) == sizeof(void*), "PtrStorage must be t he size of a pointer"); |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
223 // #endif | 244 // #endif |
224 // | 245 // |
225 // private: | 246 // private: |
226 // WebPrivatePtr<Foo> m_private; | 247 // WebPrivatePtr<Foo> m_private; |
227 // }; | 248 // }; |
228 // | 249 // |
229 // // WebFoo.cpp | 250 // // WebFoo.cpp |
230 // WebFoo::~WebFoo() { m_private.reset(); } | 251 // WebFoo::~WebFoo() { m_private.reset(); } |
231 // void WebFoo::assign(const WebFoo& other) { ... } | 252 // void WebFoo::assign(const WebFoo& other) { ... } |
232 // | 253 // |
233 template <typename T, WebPrivatePtrDestruction crossThreadDestruction = WebPriva tePtrDestructionSameThread> | 254 template <typename T, WebPrivatePtrDestruction crossThreadDestruction = WebPriva tePtrDestructionSameThread, WebPrivatePtrStrength strongOrWeak = WebPrivatePtrSt rength::Normal> |
234 class WebPrivatePtr { | 255 class WebPrivatePtr { |
235 public: | 256 public: |
236 WebPrivatePtr() : m_storage(0) { } | 257 WebPrivatePtr() : m_storage(0) { } |
237 ~WebPrivatePtr() | 258 ~WebPrivatePtr() |
238 { | 259 { |
239 // We don't destruct the object pointed by m_ptr here because we don't | 260 // We don't destruct the object pointed by m_ptr here because we don't |
240 // want to expose destructors of core classes to embedders. We should | 261 // want to expose destructors of core classes to embedders. We should |
241 // call reset() manually in destructors of classes with WebPrivatePtr | 262 // call reset() manually in destructors of classes with WebPrivatePtr |
242 // members. | 263 // members. |
243 BLINK_ASSERT(!m_storage); | 264 BLINK_ASSERT(!m_storage); |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
284 | 305 |
285 T* operator->() const | 306 T* operator->() const |
286 { | 307 { |
287 ASSERT(m_storage); | 308 ASSERT(m_storage); |
288 return get(); | 309 return get(); |
289 } | 310 } |
290 #endif | 311 #endif |
291 | 312 |
292 private: | 313 private: |
293 #if INSIDE_BLINK | 314 #if INSIDE_BLINK |
294 PtrStorage<T, crossThreadDestruction>& storage() { return PtrStorage<T, cros sThreadDestruction>::fromSlot(&m_storage); } | 315 PtrStorage<T, crossThreadDestruction, strongOrWeak>& storage() { return PtrS torage<T, crossThreadDestruction, strongOrWeak>::fromSlot(&m_storage); } |
295 const PtrStorage<T, crossThreadDestruction>& storage() const { return PtrSto rage<T, crossThreadDestruction>::fromSlot(&m_storage); } | 316 const PtrStorage<T, crossThreadDestruction, strongOrWeak>& storage() const { return PtrStorage<T, crossThreadDestruction, strongOrWeak>::fromSlot(&m_storage ); } |
296 #endif | 317 #endif |
297 | 318 |
298 #if !INSIDE_BLINK | 319 #if !INSIDE_BLINK |
299 // Disable the assignment operator; we define it above for when | 320 // Disable the assignment operator; we define it above for when |
300 // INSIDE_BLINK is set, but we need to make sure that it is not | 321 // INSIDE_BLINK is set, but we need to make sure that it is not |
301 // used outside there; the compiler-provided version won't handle reference | 322 // used outside there; the compiler-provided version won't handle reference |
302 // counting properly. | 323 // counting properly. |
303 WebPrivatePtr& operator=(const WebPrivatePtr& other); | 324 WebPrivatePtr& operator=(const WebPrivatePtr& other); |
304 #endif | 325 #endif |
305 // Disable the copy constructor; classes that contain a WebPrivatePtr | 326 // Disable the copy constructor; classes that contain a WebPrivatePtr |
306 // should implement their copy constructor using assign(). | 327 // should implement their copy constructor using assign(). |
307 WebPrivatePtr(const WebPrivatePtr&); | 328 WebPrivatePtr(const WebPrivatePtr&); |
308 | 329 |
309 void* m_storage; | 330 void* m_storage; |
310 }; | 331 }; |
311 | 332 |
312 } // namespace blink | 333 } // namespace blink |
313 | 334 |
314 #endif | 335 #endif // WebPrivatePtr_h |
OLD | NEW |