syscall(__NR_futex, m, FUTEX_WAKE, 1, 0, 0, 0);
}
+void BlockingMutex::CheckLocked() {
+ atomic_uint32_t *m = reinterpret_cast<atomic_uint32_t *>(&opaque_storage_);
+ CHECK_NE(MtxUnlocked, atomic_load(m, memory_order_relaxed));
+}
+
// ----------------- sanitizer_linux.h
// The actual size of this structure is specified by d_reclen.
// Note that getdents64 uses a different structure format. We only provide the
OSSpinLockUnlock((OSSpinLock*)&opaque_storage_);
}
+void BlockingMutex::CheckLocked() {
+ CHECK_EQ((uptr)pthread_self(), owner_);
+}
+
} // namespace __sanitizer
#endif // __APPLE__
explicit BlockingMutex(LinkerInitialized);
void Lock();
void Unlock();
+ void CheckLocked();
private:
uptr opaque_storage_[10];
uptr owner_; // for debugging
LeaveCriticalSection((LPCRITICAL_SECTION)opaque_storage_);
}
+void BlockingMutex::CheckLocked() {
+ CHECK_EQ(owner_, GetThreadSelf());
+}
+
} // namespace __sanitizer
#endif // _WIN32
return 0;
}
+template<typename MutexType>
+static void check_locked(MutexType *mtx) {
+ GenericScopedLock<MutexType> l(mtx);
+ mtx->CheckLocked();
+}
+
TEST(SanitizerCommon, SpinMutex) {
SpinMutex mtx;
mtx.Init();
pthread_create(&threads[i], 0, lock_thread<BlockingMutex>, &data);
for (int i = 0; i < kThreads; i++)
pthread_join(threads[i], 0);
+ check_locked(mtx);
}
} // namespace __sanitizer