OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 // Weak pointers are pointers to an object that do not affect its lifetime, | 5 // Weak pointers are pointers to an object that do not affect its lifetime, |
6 // and which may be invalidated (i.e. reset to NULL) by the object, or its | 6 // and which may be invalidated (i.e. reset to nullptr) by the object, or its |
7 // owner, at any time, most commonly when the object is about to be deleted. | 7 // owner, at any time, most commonly when the object is about to be deleted. |
8 | 8 |
9 // Weak pointers are useful when an object needs to be accessed safely by one | 9 // Weak pointers are useful when an object needs to be accessed safely by one |
10 // or more objects other than its owner, and those callers can cope with the | 10 // or more objects other than its owner, and those callers can cope with the |
11 // object vanishing and e.g. tasks posted to it being silently dropped. | 11 // object vanishing and e.g. tasks posted to it being silently dropped. |
12 // Reference-counting such an object would complicate the ownership graph and | 12 // Reference-counting such an object would complicate the ownership graph and |
13 // make it harder to reason about the object's lifetime. | 13 // make it harder to reason about the object's lifetime. |
14 | 14 |
15 // EXAMPLE: | 15 // EXAMPLE: |
16 // | 16 // |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
63 // unbound from the SequencedTaskRunner/Thread. The WeakPtrFactory may then be | 63 // unbound from the SequencedTaskRunner/Thread. The WeakPtrFactory may then be |
64 // destroyed, or new WeakPtr objects may be used, from a different sequence. | 64 // destroyed, or new WeakPtr objects may be used, from a different sequence. |
65 // | 65 // |
66 // Thus, at least one WeakPtr object must exist and have been dereferenced on | 66 // Thus, at least one WeakPtr object must exist and have been dereferenced on |
67 // the correct thread to enforce that other WeakPtr objects will enforce they | 67 // the correct thread to enforce that other WeakPtr objects will enforce they |
68 // are used on the desired thread. | 68 // are used on the desired thread. |
69 | 69 |
70 #ifndef BASE_MEMORY_WEAK_PTR_H_ | 70 #ifndef BASE_MEMORY_WEAK_PTR_H_ |
71 #define BASE_MEMORY_WEAK_PTR_H_ | 71 #define BASE_MEMORY_WEAK_PTR_H_ |
72 | 72 |
| 73 #include <cstddef> |
73 #include <type_traits> | 74 #include <type_traits> |
74 | 75 |
75 #include "base/base_export.h" | 76 #include "base/base_export.h" |
76 #include "base/logging.h" | 77 #include "base/logging.h" |
77 #include "base/macros.h" | 78 #include "base/macros.h" |
78 #include "base/memory/ref_counted.h" | 79 #include "base/memory/ref_counted.h" |
79 #include "base/sequence_checker.h" | 80 #include "base/sequence_checker.h" |
80 | 81 |
81 namespace base { | 82 namespace base { |
82 | 83 |
(...skipping 109 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
192 // EXAMPLE: | 193 // EXAMPLE: |
193 // | 194 // |
194 // class Foo { ... }; | 195 // class Foo { ... }; |
195 // WeakPtr<Foo> foo; | 196 // WeakPtr<Foo> foo; |
196 // if (foo) | 197 // if (foo) |
197 // foo->method(); | 198 // foo->method(); |
198 // | 199 // |
199 template <typename T> | 200 template <typename T> |
200 class WeakPtr : public internal::WeakPtrBase { | 201 class WeakPtr : public internal::WeakPtrBase { |
201 public: | 202 public: |
202 WeakPtr() : ptr_(NULL) { | 203 WeakPtr() : ptr_(nullptr) {} |
203 } | 204 |
| 205 WeakPtr(std::nullptr_t) : ptr_(nullptr) {} |
204 | 206 |
205 // Allow conversion from U to T provided U "is a" T. Note that this | 207 // Allow conversion from U to T provided U "is a" T. Note that this |
206 // is separate from the (implicit) copy constructor. | 208 // is separate from the (implicit) copy constructor. |
207 template <typename U> | 209 template <typename U> |
208 WeakPtr(const WeakPtr<U>& other) : WeakPtrBase(other), ptr_(other.ptr_) { | 210 WeakPtr(const WeakPtr<U>& other) : WeakPtrBase(other), ptr_(other.ptr_) { |
209 } | 211 } |
210 | 212 |
211 T* get() const { return ref_.is_valid() ? ptr_ : NULL; } | 213 T* get() const { return ref_.is_valid() ? ptr_ : nullptr; } |
212 | 214 |
213 T& operator*() const { | 215 T& operator*() const { |
214 DCHECK(get() != NULL); | 216 DCHECK(get() != nullptr); |
215 return *get(); | 217 return *get(); |
216 } | 218 } |
217 T* operator->() const { | 219 T* operator->() const { |
218 DCHECK(get() != NULL); | 220 DCHECK(get() != nullptr); |
219 return get(); | 221 return get(); |
220 } | 222 } |
221 | 223 |
222 void reset() { | 224 void reset() { |
223 ref_ = internal::WeakReference(); | 225 ref_ = internal::WeakReference(); |
224 ptr_ = NULL; | 226 ptr_ = nullptr; |
225 } | 227 } |
226 | 228 |
227 // Implement "Safe Bool Idiom" | 229 // Implement "Safe Bool Idiom" |
228 // https://en.wikibooks.org/wiki/More_C%2B%2B_Idioms/Safe_bool | 230 // https://en.wikibooks.org/wiki/More_C%2B%2B_Idioms/Safe_bool |
229 // | 231 // |
230 // Allow WeakPtr<element_type> to be used in boolean expressions such as | 232 // Allow WeakPtr<element_type> to be used in boolean expressions such as |
231 // if (weak_ptr_instance) | 233 // if (weak_ptr_instance) |
232 // But do not become convertible to a real bool (which is dangerous). | 234 // But do not become convertible to a real bool (which is dangerous). |
233 // Implementation requires: | 235 // Implementation requires: |
234 // typedef Testable | 236 // typedef Testable |
235 // operator Testable() const | 237 // operator Testable() const |
236 // operator== | 238 // operator== |
237 // operator!= | 239 // operator!= |
238 // | 240 // |
239 // == and != operators must be declared explicitly or dissallowed, as | 241 // == and != operators must be declared explicitly or dissallowed, as |
240 // otherwise "ptr1 == ptr2" will compile but do the wrong thing (i.e., convert | 242 // otherwise "ptr1 == ptr2" will compile but do the wrong thing (i.e., convert |
241 // to Testable and then do the comparison). | 243 // to Testable and then do the comparison). |
242 // | 244 // |
243 // C++11 provides for "explicit operator bool()", however it is currently | 245 // C++11 provides for "explicit operator bool()", however it is currently |
244 // banned due to MSVS2013. https://chromium-cpp.appspot.com/#core-blacklist | 246 // banned due to MSVS2013. https://chromium-cpp.appspot.com/#core-blacklist |
245 private: | 247 private: |
246 typedef T* WeakPtr::*Testable; | 248 typedef T* WeakPtr::*Testable; |
247 | 249 |
248 public: | 250 public: |
249 operator Testable() const { return get() ? &WeakPtr::ptr_ : NULL; } | 251 operator Testable() const { return get() ? &WeakPtr::ptr_ : nullptr; } |
250 | 252 |
251 private: | 253 private: |
252 // Explicitly declare comparison operators as required by the "Safe Bool | 254 // Explicitly declare comparison operators as required by the "Safe Bool |
253 // Idiom", but keep them private. | 255 // Idiom", but keep them private. |
254 template <class U> bool operator==(WeakPtr<U> const&) const; | 256 template <class U> bool operator==(WeakPtr<U> const&) const; |
255 template <class U> bool operator!=(WeakPtr<U> const&) const; | 257 template <class U> bool operator!=(WeakPtr<U> const&) const; |
256 | 258 |
257 friend class internal::SupportsWeakPtrBase; | 259 friend class internal::SupportsWeakPtrBase; |
258 template <typename U> friend class WeakPtr; | 260 template <typename U> friend class WeakPtr; |
259 friend class SupportsWeakPtr<T>; | 261 friend class SupportsWeakPtr<T>; |
260 friend class WeakPtrFactory<T>; | 262 friend class WeakPtrFactory<T>; |
261 | 263 |
262 WeakPtr(const internal::WeakReference& ref, T* ptr) | 264 WeakPtr(const internal::WeakReference& ref, T* ptr) |
263 : WeakPtrBase(ref), | 265 : WeakPtrBase(ref), |
264 ptr_(ptr) { | 266 ptr_(ptr) { |
265 } | 267 } |
266 | 268 |
267 // This pointer is only valid when ref_.is_valid() is true. Otherwise, its | 269 // This pointer is only valid when ref_.is_valid() is true. Otherwise, its |
268 // value is undefined (as opposed to NULL). | 270 // value is undefined (as opposed to nullptr). |
269 T* ptr_; | 271 T* ptr_; |
270 }; | 272 }; |
271 | 273 |
272 // A class may be composed of a WeakPtrFactory and thereby | 274 // A class may be composed of a WeakPtrFactory and thereby |
273 // control how it exposes weak pointers to itself. This is helpful if you only | 275 // control how it exposes weak pointers to itself. This is helpful if you only |
274 // need weak pointers within the implementation of a class. This class is also | 276 // need weak pointers within the implementation of a class. This class is also |
275 // useful when working with primitive types. For example, you could have a | 277 // useful when working with primitive types. For example, you could have a |
276 // WeakPtrFactory<bool> that is used to pass around a weak reference to a bool. | 278 // WeakPtrFactory<bool> that is used to pass around a weak reference to a bool. |
277 template <class T> | 279 template <class T> |
278 class WeakPtrFactory { | 280 class WeakPtrFactory { |
279 public: | 281 public: |
280 explicit WeakPtrFactory(T* ptr) : ptr_(ptr) { | 282 explicit WeakPtrFactory(T* ptr) : ptr_(ptr) { |
281 } | 283 } |
282 | 284 |
283 ~WeakPtrFactory() { | 285 ~WeakPtrFactory() { ptr_ = nullptr; } |
284 ptr_ = NULL; | |
285 } | |
286 | 286 |
287 WeakPtr<T> GetWeakPtr() { | 287 WeakPtr<T> GetWeakPtr() { |
288 DCHECK(ptr_); | 288 DCHECK(ptr_); |
289 return WeakPtr<T>(weak_reference_owner_.GetRef(), ptr_); | 289 return WeakPtr<T>(weak_reference_owner_.GetRef(), ptr_); |
290 } | 290 } |
291 | 291 |
292 // Call this method to invalidate all existing weak pointers. | 292 // Call this method to invalidate all existing weak pointers. |
293 void InvalidateWeakPtrs() { | 293 void InvalidateWeakPtrs() { |
294 DCHECK(ptr_); | 294 DCHECK(ptr_); |
295 weak_reference_owner_.Invalidate(); | 295 weak_reference_owner_.Invalidate(); |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
348 // base::WeakPtr<Derived> ptr = derived.AsWeakPtr(); // Fails. | 348 // base::WeakPtr<Derived> ptr = derived.AsWeakPtr(); // Fails. |
349 | 349 |
350 template <typename Derived> | 350 template <typename Derived> |
351 WeakPtr<Derived> AsWeakPtr(Derived* t) { | 351 WeakPtr<Derived> AsWeakPtr(Derived* t) { |
352 return internal::SupportsWeakPtrBase::StaticAsWeakPtr<Derived>(t); | 352 return internal::SupportsWeakPtrBase::StaticAsWeakPtr<Derived>(t); |
353 } | 353 } |
354 | 354 |
355 } // namespace base | 355 } // namespace base |
356 | 356 |
357 #endif // BASE_MEMORY_WEAK_PTR_H_ | 357 #endif // BASE_MEMORY_WEAK_PTR_H_ |
OLD | NEW |