Changeset 250762 in webkit
- Timestamp:
- Oct 4, 2019 6:59:35 PM (5 years ago)
- Location:
- trunk/Source/WTF
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WTF/ChangeLog
r250747 r250762 1 2019-10-04 Ryosuke Niwa <rniwa@webkit.org> 2 3 Make a ThreadSafeRefCounted object safe to ref & deref inside its destructor 4 https://bugs.webkit.org/show_bug.cgi?id=201576 5 6 Reviewed by Geoffrey Garen. 7 8 This patch leaves m_refCount 1 inside the last deref call to ThreadSafeRefCounted 9 such that ref'ing and deref'ing it again inside its destructor would never try 10 to double delete the object. 11 12 Also added m_deletionHasBegun like RefCounted. 13 14 * wtf/ThreadSafeRefCounted.h: 15 (WTF::ThreadSafeRefCountedBase::ref const): 16 (WTF::ThreadSafeRefCountedBase::hasOneRef const): 17 (WTF::ThreadSafeRefCountedBase::derefBase const): 18 1 19 2019-10-04 Heiko Becker <heirecka@exherbo.org> 2 20 -
trunk/Source/WTF/wtf/ThreadSafeRefCounted.h
r247078 r250762 33 33 namespace WTF { 34 34 35 #if defined(NDEBUG) && !ENABLE(SECURITY_ASSERTIONS) 36 #define CHECK_THREAD_SAFE_REF_COUNTED_LIFECYCLE 0 37 #else 38 #define CHECK_THREAD_SAFE_REF_COUNTED_LIFECYCLE 1 39 #endif 40 35 41 class ThreadSafeRefCountedBase { 36 42 WTF_MAKE_NONCOPYABLE(ThreadSafeRefCountedBase); … … 39 45 ThreadSafeRefCountedBase() = default; 40 46 47 #if CHECK_THREAD_SAFE_REF_COUNTED_LIFECYCLE 48 ~ThreadSafeRefCountedBase() 49 { 50 // When this ThreadSafeRefCounted object is a part of another object, derefBase() is never called on this object. 51 m_deletionHasBegun = true; 52 } 53 #endif 54 41 55 void ref() const 42 56 { 57 #if CHECK_THREAD_SAFE_REF_COUNTED_LIFECYCLE 58 ASSERT_WITH_SECURITY_IMPLICATION(!m_deletionHasBegun); 59 #endif 43 60 ++m_refCount; 44 61 } … … 46 63 bool hasOneRef() const 47 64 { 65 #if CHECK_THREAD_SAFE_REF_COUNTED_LIFECYCLE 66 ASSERT(!m_deletionHasBegun); 67 #endif 48 68 return refCount() == 1; 49 69 } … … 58 78 bool derefBase() const 59 79 { 60 return !--m_refCount; 80 ASSERT(m_refCount); 81 82 #if CHECK_THREAD_SAFE_REF_COUNTED_LIFECYCLE 83 ASSERT_WITH_SECURITY_IMPLICATION(!m_deletionHasBegun); 84 #endif 85 86 if (UNLIKELY(!--m_refCount)) { 87 // Setting m_refCount to 1 here prevents double delete within the destructor but not from another thread 88 // since such a thread could have ref'ed this object long after it had been deleted. See webkit.org/b/201576. 89 m_refCount = 1; 90 #if CHECK_THREAD_SAFE_REF_COUNTED_LIFECYCLE 91 m_deletionHasBegun = true; 92 #endif 93 return true; 94 } 95 96 return false; 61 97 } 62 98 63 99 private: 64 100 mutable std::atomic<unsigned> m_refCount { 1 }; 101 102 #if CHECK_THREAD_SAFE_REF_COUNTED_LIFECYCLE 103 mutable std::atomic<bool> m_deletionHasBegun { false }; 104 #endif 65 105 }; 66 106
Note: See TracChangeset
for help on using the changeset viewer.