Bug 1580921 - Do more thread-safety checks in mozilla::WeakPtr, r=froydnj

Differential Revision: https://phabricator.services.mozilla.com/D45872

--HG--
extra : moz-landing-system : lando
This commit is contained in:
Honza Bambas 2019-09-13 17:23:16 +00:00
Родитель b7d09ae90b
Коммит 1c65af06ec
1 изменённых файлов: 24 добавлений и 1 удалений

Просмотреть файл

@ -118,6 +118,12 @@
} while (false) } while (false)
# define MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED(that) \ # define MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED(that) \
(that)->AssertThreadSafety(); (that)->AssertThreadSafety();
# define MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED_IF(that) \
do { \
if (that) { \
(that)->AssertThreadSafety(); \
} \
} while (false)
# define MOZ_WEAKPTR_THREAD_SAFETY_CHECKING 1 # define MOZ_WEAKPTR_THREAD_SAFETY_CHECKING 1
@ -133,6 +139,9 @@
# define MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED(that) \ # define MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED(that) \
do { \ do { \
} while (false) } while (false)
# define MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED_IF(that) \
do { \
} while (false)
#endif #endif
@ -243,8 +252,13 @@ class WeakPtr {
public: public:
WeakPtr& operator=(const WeakPtr& aOther) { WeakPtr& operator=(const WeakPtr& aOther) {
// We must make sure the reference we have now is safe to be dereferenced
// before we throw it away... (this can be called from a ctor)
MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED_IF(mRef);
// ...and make sure the new reference is used on a single thread as well.
MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED(aOther.mRef);
mRef = aOther.mRef; mRef = aOther.mRef;
MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED(mRef);
return *this; return *this;
} }
@ -254,6 +268,9 @@ class WeakPtr {
} }
WeakPtr& operator=(decltype(nullptr)) { WeakPtr& operator=(decltype(nullptr)) {
// We must make sure the reference we have now is safe to be dereferenced
// before we throw it away.
MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED_IF(mRef);
if (!mRef || mRef->get()) { if (!mRef || mRef->get()) {
// Ensure that mRef is dereferenceable in the uninitialized state. // Ensure that mRef is dereferenceable in the uninitialized state.
mRef = new WeakReference(nullptr); mRef = new WeakReference(nullptr);
@ -262,6 +279,9 @@ class WeakPtr {
} }
WeakPtr& operator=(SupportsWeakPtr<NonConstT> const* aOther) { WeakPtr& operator=(SupportsWeakPtr<NonConstT> const* aOther) {
// We must make sure the reference we have now is safe to be dereferenced
// before we throw it away.
MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED_IF(mRef);
if (aOther) { if (aOther) {
*this = aOther->SelfReferencingWeakPtr(); *this = aOther->SelfReferencingWeakPtr();
} else if (!mRef || mRef->get()) { } else if (!mRef || mRef->get()) {
@ -274,6 +294,9 @@ class WeakPtr {
} }
WeakPtr& operator=(SupportsWeakPtr<NonConstT>* aOther) { WeakPtr& operator=(SupportsWeakPtr<NonConstT>* aOther) {
// We must make sure the reference we have now is safe to be dereferenced
// before we throw it away.
MOZ_WEAKPTR_ASSERT_THREAD_SAFETY_DELEGATED_IF(mRef);
if (aOther) { if (aOther) {
*this = aOther->SelfReferencingWeakPtr(); *this = aOther->SelfReferencingWeakPtr();
} else if (!mRef || mRef->get()) { } else if (!mRef || mRef->get()) {