1*8975f5c5SAndroid Build Coastguard Worker // 2*8975f5c5SAndroid Build Coastguard Worker // Copyright 2023 The ANGLE Project Authors. All rights reserved. 3*8975f5c5SAndroid Build Coastguard Worker // Use of this source code is governed by a BSD-style license that can be 4*8975f5c5SAndroid Build Coastguard Worker // found in the LICENSE file. 5*8975f5c5SAndroid Build Coastguard Worker // 6*8975f5c5SAndroid Build Coastguard Worker // GlobalMutex.cpp: Defines Global Mutex and utilities. 7*8975f5c5SAndroid Build Coastguard Worker 8*8975f5c5SAndroid Build Coastguard Worker #include "libANGLE/GlobalMutex.h" 9*8975f5c5SAndroid Build Coastguard Worker 10*8975f5c5SAndroid Build Coastguard Worker #include <atomic> 11*8975f5c5SAndroid Build Coastguard Worker 12*8975f5c5SAndroid Build Coastguard Worker #include "common/debug.h" 13*8975f5c5SAndroid Build Coastguard Worker #include "common/system_utils.h" 14*8975f5c5SAndroid Build Coastguard Worker 15*8975f5c5SAndroid Build Coastguard Worker namespace egl 16*8975f5c5SAndroid Build Coastguard Worker { 17*8975f5c5SAndroid Build Coastguard Worker namespace priv 18*8975f5c5SAndroid Build Coastguard Worker { 19*8975f5c5SAndroid Build Coastguard Worker using GlobalMutexType = std::mutex; 20*8975f5c5SAndroid Build Coastguard Worker 21*8975f5c5SAndroid Build Coastguard Worker #if !defined(ANGLE_ENABLE_ASSERTS) && !defined(ANGLE_ENABLE_GLOBAL_MUTEX_RECURSION) 22*8975f5c5SAndroid Build Coastguard Worker // Default version. 23*8975f5c5SAndroid Build Coastguard Worker class GlobalMutex final : angle::NonCopyable 24*8975f5c5SAndroid Build Coastguard Worker { 25*8975f5c5SAndroid Build Coastguard Worker public: lock()26*8975f5c5SAndroid Build Coastguard Worker ANGLE_INLINE void lock() { mMutex.lock(); } unlock()27*8975f5c5SAndroid Build Coastguard Worker ANGLE_INLINE void unlock() { mMutex.unlock(); } 28*8975f5c5SAndroid Build Coastguard Worker 29*8975f5c5SAndroid Build Coastguard Worker protected: 30*8975f5c5SAndroid Build Coastguard Worker GlobalMutexType mMutex; 31*8975f5c5SAndroid Build Coastguard Worker }; 32*8975f5c5SAndroid Build Coastguard Worker #endif 33*8975f5c5SAndroid Build Coastguard Worker 34*8975f5c5SAndroid Build Coastguard Worker #if defined(ANGLE_ENABLE_ASSERTS) && !defined(ANGLE_ENABLE_GLOBAL_MUTEX_RECURSION) 35*8975f5c5SAndroid Build Coastguard Worker // Debug version. 36*8975f5c5SAndroid Build Coastguard Worker class GlobalMutex final : angle::NonCopyable 37*8975f5c5SAndroid Build Coastguard Worker { 38*8975f5c5SAndroid Build Coastguard Worker public: lock()39*8975f5c5SAndroid Build Coastguard Worker ANGLE_INLINE void lock() 40*8975f5c5SAndroid Build Coastguard Worker { 41*8975f5c5SAndroid Build Coastguard Worker const angle::ThreadId threadId = angle::GetCurrentThreadId(); 42*8975f5c5SAndroid Build Coastguard Worker ASSERT(getOwnerThreadId() != threadId); 43*8975f5c5SAndroid Build Coastguard Worker mMutex.lock(); 44*8975f5c5SAndroid Build Coastguard Worker ASSERT(getOwnerThreadId() == angle::InvalidThreadId()); 45*8975f5c5SAndroid Build Coastguard Worker mOwnerThreadId.store(threadId, std::memory_order_relaxed); 46*8975f5c5SAndroid Build Coastguard Worker } 47*8975f5c5SAndroid Build Coastguard Worker unlock()48*8975f5c5SAndroid Build Coastguard Worker ANGLE_INLINE void unlock() 49*8975f5c5SAndroid Build Coastguard Worker { 50*8975f5c5SAndroid Build Coastguard Worker ASSERT(getOwnerThreadId() == angle::GetCurrentThreadId()); 51*8975f5c5SAndroid Build Coastguard Worker mOwnerThreadId.store(angle::InvalidThreadId(), std::memory_order_relaxed); 52*8975f5c5SAndroid Build Coastguard Worker mMutex.unlock(); 53*8975f5c5SAndroid Build Coastguard Worker } 54*8975f5c5SAndroid Build Coastguard Worker 55*8975f5c5SAndroid Build Coastguard Worker private: getOwnerThreadId() const56*8975f5c5SAndroid Build Coastguard Worker ANGLE_INLINE angle::ThreadId getOwnerThreadId() const 57*8975f5c5SAndroid Build Coastguard Worker { 58*8975f5c5SAndroid Build Coastguard Worker return mOwnerThreadId.load(std::memory_order_relaxed); 59*8975f5c5SAndroid Build Coastguard Worker } 60*8975f5c5SAndroid Build Coastguard Worker 61*8975f5c5SAndroid Build Coastguard Worker GlobalMutexType mMutex; 62*8975f5c5SAndroid Build Coastguard Worker std::atomic<angle::ThreadId> mOwnerThreadId{angle::InvalidThreadId()}; 63*8975f5c5SAndroid Build Coastguard Worker }; 64*8975f5c5SAndroid Build Coastguard Worker #endif // defined(ANGLE_ENABLE_ASSERTS) && !defined(ANGLE_ENABLE_GLOBAL_MUTEX_RECURSION) 65*8975f5c5SAndroid Build Coastguard Worker 66*8975f5c5SAndroid Build Coastguard Worker #if defined(ANGLE_ENABLE_GLOBAL_MUTEX_RECURSION) 67*8975f5c5SAndroid Build Coastguard Worker // Recursive version. 68*8975f5c5SAndroid Build Coastguard Worker class GlobalMutex final : angle::NonCopyable 69*8975f5c5SAndroid Build Coastguard Worker { 70*8975f5c5SAndroid Build Coastguard Worker public: lock()71*8975f5c5SAndroid Build Coastguard Worker ANGLE_INLINE void lock() 72*8975f5c5SAndroid Build Coastguard Worker { 73*8975f5c5SAndroid Build Coastguard Worker const angle::ThreadId threadId = angle::GetCurrentThreadId(); 74*8975f5c5SAndroid Build Coastguard Worker if (ANGLE_UNLIKELY(!mMutex.try_lock())) 75*8975f5c5SAndroid Build Coastguard Worker { 76*8975f5c5SAndroid Build Coastguard Worker if (ANGLE_UNLIKELY(getOwnerThreadId() == threadId)) 77*8975f5c5SAndroid Build Coastguard Worker { 78*8975f5c5SAndroid Build Coastguard Worker ASSERT(mLockLevel > 0); 79*8975f5c5SAndroid Build Coastguard Worker ++mLockLevel; 80*8975f5c5SAndroid Build Coastguard Worker return; 81*8975f5c5SAndroid Build Coastguard Worker } 82*8975f5c5SAndroid Build Coastguard Worker mMutex.lock(); 83*8975f5c5SAndroid Build Coastguard Worker } 84*8975f5c5SAndroid Build Coastguard Worker ASSERT(getOwnerThreadId() == angle::InvalidThreadId()); 85*8975f5c5SAndroid Build Coastguard Worker ASSERT(mLockLevel == 0); 86*8975f5c5SAndroid Build Coastguard Worker mOwnerThreadId.store(threadId, std::memory_order_relaxed); 87*8975f5c5SAndroid Build Coastguard Worker mLockLevel = 1; 88*8975f5c5SAndroid Build Coastguard Worker } 89*8975f5c5SAndroid Build Coastguard Worker unlock()90*8975f5c5SAndroid Build Coastguard Worker ANGLE_INLINE void unlock() 91*8975f5c5SAndroid Build Coastguard Worker { 92*8975f5c5SAndroid Build Coastguard Worker ASSERT(getOwnerThreadId() == angle::GetCurrentThreadId()); 93*8975f5c5SAndroid Build Coastguard Worker ASSERT(mLockLevel > 0); 94*8975f5c5SAndroid Build Coastguard Worker if (ANGLE_LIKELY(--mLockLevel == 0)) 95*8975f5c5SAndroid Build Coastguard Worker { 96*8975f5c5SAndroid Build Coastguard Worker mOwnerThreadId.store(angle::InvalidThreadId(), std::memory_order_relaxed); 97*8975f5c5SAndroid Build Coastguard Worker mMutex.unlock(); 98*8975f5c5SAndroid Build Coastguard Worker } 99*8975f5c5SAndroid Build Coastguard Worker } 100*8975f5c5SAndroid Build Coastguard Worker 101*8975f5c5SAndroid Build Coastguard Worker private: getOwnerThreadId() const102*8975f5c5SAndroid Build Coastguard Worker ANGLE_INLINE angle::ThreadId getOwnerThreadId() const 103*8975f5c5SAndroid Build Coastguard Worker { 104*8975f5c5SAndroid Build Coastguard Worker return mOwnerThreadId.load(std::memory_order_relaxed); 105*8975f5c5SAndroid Build Coastguard Worker } 106*8975f5c5SAndroid Build Coastguard Worker 107*8975f5c5SAndroid Build Coastguard Worker GlobalMutexType mMutex; 108*8975f5c5SAndroid Build Coastguard Worker std::atomic<angle::ThreadId> mOwnerThreadId{angle::InvalidThreadId()}; 109*8975f5c5SAndroid Build Coastguard Worker uint32_t mLockLevel = 0; 110*8975f5c5SAndroid Build Coastguard Worker }; 111*8975f5c5SAndroid Build Coastguard Worker #endif // defined(ANGLE_ENABLE_GLOBAL_MUTEX_RECURSION) 112*8975f5c5SAndroid Build Coastguard Worker namespace 113*8975f5c5SAndroid Build Coastguard Worker { 114*8975f5c5SAndroid Build Coastguard Worker #if defined(ANGLE_ENABLE_GLOBAL_MUTEX_LOAD_TIME_ALLOCATE) 115*8975f5c5SAndroid Build Coastguard Worker # if !ANGLE_HAS_ATTRIBUTE_CONSTRUCTOR || !ANGLE_HAS_ATTRIBUTE_DESTRUCTOR 116*8975f5c5SAndroid Build Coastguard Worker # error \ 117*8975f5c5SAndroid Build Coastguard Worker "'angle_enable_global_mutex_load_time_allocate' " \ 118*8975f5c5SAndroid Build Coastguard Worker "requires constructor/destructor compiler atributes." 119*8975f5c5SAndroid Build Coastguard Worker # endif 120*8975f5c5SAndroid Build Coastguard Worker GlobalMutex *g_MutexPtr = nullptr; 121*8975f5c5SAndroid Build Coastguard Worker GlobalMutex *g_EGLSyncMutexPtr = nullptr; 122*8975f5c5SAndroid Build Coastguard Worker AllocateGlobalMutex()123*8975f5c5SAndroid Build Coastguard Workervoid ANGLE_CONSTRUCTOR AllocateGlobalMutex() 124*8975f5c5SAndroid Build Coastguard Worker { 125*8975f5c5SAndroid Build Coastguard Worker ASSERT(g_MutexPtr == nullptr); 126*8975f5c5SAndroid Build Coastguard Worker g_MutexPtr = new GlobalMutex(); 127*8975f5c5SAndroid Build Coastguard Worker ASSERT(g_EGLSyncMutexPtr == nullptr); 128*8975f5c5SAndroid Build Coastguard Worker g_EGLSyncMutexPtr = new GlobalMutex(); 129*8975f5c5SAndroid Build Coastguard Worker } 130*8975f5c5SAndroid Build Coastguard Worker DeallocateGlobalMutex()131*8975f5c5SAndroid Build Coastguard Workervoid ANGLE_DESTRUCTOR DeallocateGlobalMutex() 132*8975f5c5SAndroid Build Coastguard Worker { 133*8975f5c5SAndroid Build Coastguard Worker SafeDelete(g_MutexPtr); 134*8975f5c5SAndroid Build Coastguard Worker SafeDelete(g_EGLSyncMutexPtr); 135*8975f5c5SAndroid Build Coastguard Worker } 136*8975f5c5SAndroid Build Coastguard Worker #else 137*8975f5c5SAndroid Build Coastguard Worker ANGLE_REQUIRE_CONSTANT_INIT std::atomic<GlobalMutex *> g_Mutex(nullptr); 138*8975f5c5SAndroid Build Coastguard Worker ANGLE_REQUIRE_CONSTANT_INIT std::atomic<GlobalMutex *> g_EGLSyncMutex(nullptr); 139*8975f5c5SAndroid Build Coastguard Worker static_assert(std::is_trivially_destructible<decltype(g_Mutex)>::value, 140*8975f5c5SAndroid Build Coastguard Worker "global mutex is not trivially destructible"); 141*8975f5c5SAndroid Build Coastguard Worker static_assert(std::is_trivially_destructible<decltype(g_EGLSyncMutex)>::value, 142*8975f5c5SAndroid Build Coastguard Worker "global EGL Sync mutex is not trivially destructible"); 143*8975f5c5SAndroid Build Coastguard Worker 144*8975f5c5SAndroid Build Coastguard Worker GlobalMutex *AllocateGlobalMutexImpl(std::atomic<GlobalMutex *> *globalMutex) 145*8975f5c5SAndroid Build Coastguard Worker { 146*8975f5c5SAndroid Build Coastguard Worker GlobalMutex *currentMutex = nullptr; 147*8975f5c5SAndroid Build Coastguard Worker std::unique_ptr<GlobalMutex> newMutex(new GlobalMutex()); 148*8975f5c5SAndroid Build Coastguard Worker do 149*8975f5c5SAndroid Build Coastguard Worker { 150*8975f5c5SAndroid Build Coastguard Worker if (globalMutex->compare_exchange_weak(currentMutex, newMutex.get())) 151*8975f5c5SAndroid Build Coastguard Worker { 152*8975f5c5SAndroid Build Coastguard Worker return newMutex.release(); 153*8975f5c5SAndroid Build Coastguard Worker } 154*8975f5c5SAndroid Build Coastguard Worker } while (currentMutex == nullptr); 155*8975f5c5SAndroid Build Coastguard Worker return currentMutex; 156*8975f5c5SAndroid Build Coastguard Worker } 157*8975f5c5SAndroid Build Coastguard Worker 158*8975f5c5SAndroid Build Coastguard Worker GlobalMutex *GetGlobalMutex() 159*8975f5c5SAndroid Build Coastguard Worker { 160*8975f5c5SAndroid Build Coastguard Worker GlobalMutex *mutex = g_Mutex.load(); 161*8975f5c5SAndroid Build Coastguard Worker return mutex != nullptr ? mutex : AllocateGlobalMutexImpl(&g_Mutex); 162*8975f5c5SAndroid Build Coastguard Worker } 163*8975f5c5SAndroid Build Coastguard Worker 164*8975f5c5SAndroid Build Coastguard Worker GlobalMutex *GetGlobalEGLSyncObjectMutex() 165*8975f5c5SAndroid Build Coastguard Worker { 166*8975f5c5SAndroid Build Coastguard Worker GlobalMutex *mutex = g_EGLSyncMutex.load(); 167*8975f5c5SAndroid Build Coastguard Worker return mutex != nullptr ? mutex : AllocateGlobalMutexImpl(&g_EGLSyncMutex); 168*8975f5c5SAndroid Build Coastguard Worker } 169*8975f5c5SAndroid Build Coastguard Worker #endif 170*8975f5c5SAndroid Build Coastguard Worker } // anonymous namespace 171*8975f5c5SAndroid Build Coastguard Worker 172*8975f5c5SAndroid Build Coastguard Worker // ScopedGlobalMutexLock implementation. 173*8975f5c5SAndroid Build Coastguard Worker #if defined(ANGLE_ENABLE_GLOBAL_MUTEX_LOAD_TIME_ALLOCATE) 174*8975f5c5SAndroid Build Coastguard Worker template <GlobalMutexChoice mutexChoice> ScopedGlobalMutexLock()175*8975f5c5SAndroid Build Coastguard WorkerScopedGlobalMutexLock<mutexChoice>::ScopedGlobalMutexLock() 176*8975f5c5SAndroid Build Coastguard Worker { 177*8975f5c5SAndroid Build Coastguard Worker switch (mutexChoice) 178*8975f5c5SAndroid Build Coastguard Worker { 179*8975f5c5SAndroid Build Coastguard Worker case GlobalMutexChoice::EGL: 180*8975f5c5SAndroid Build Coastguard Worker g_MutexPtr->lock(); 181*8975f5c5SAndroid Build Coastguard Worker break; 182*8975f5c5SAndroid Build Coastguard Worker case GlobalMutexChoice::Sync: 183*8975f5c5SAndroid Build Coastguard Worker g_EGLSyncMutexPtr->lock(); 184*8975f5c5SAndroid Build Coastguard Worker break; 185*8975f5c5SAndroid Build Coastguard Worker default: 186*8975f5c5SAndroid Build Coastguard Worker UNREACHABLE(); 187*8975f5c5SAndroid Build Coastguard Worker break; 188*8975f5c5SAndroid Build Coastguard Worker } 189*8975f5c5SAndroid Build Coastguard Worker } 190*8975f5c5SAndroid Build Coastguard Worker 191*8975f5c5SAndroid Build Coastguard Worker template <GlobalMutexChoice mutexChoice> ~ScopedGlobalMutexLock()192*8975f5c5SAndroid Build Coastguard WorkerScopedGlobalMutexLock<mutexChoice>::~ScopedGlobalMutexLock() 193*8975f5c5SAndroid Build Coastguard Worker { 194*8975f5c5SAndroid Build Coastguard Worker switch (mutexChoice) 195*8975f5c5SAndroid Build Coastguard Worker { 196*8975f5c5SAndroid Build Coastguard Worker case GlobalMutexChoice::EGL: 197*8975f5c5SAndroid Build Coastguard Worker g_MutexPtr->unlock(); 198*8975f5c5SAndroid Build Coastguard Worker break; 199*8975f5c5SAndroid Build Coastguard Worker case GlobalMutexChoice::Sync: 200*8975f5c5SAndroid Build Coastguard Worker g_EGLSyncMutexPtr->unlock(); 201*8975f5c5SAndroid Build Coastguard Worker break; 202*8975f5c5SAndroid Build Coastguard Worker default: 203*8975f5c5SAndroid Build Coastguard Worker UNREACHABLE(); 204*8975f5c5SAndroid Build Coastguard Worker break; 205*8975f5c5SAndroid Build Coastguard Worker } 206*8975f5c5SAndroid Build Coastguard Worker } 207*8975f5c5SAndroid Build Coastguard Worker #else 208*8975f5c5SAndroid Build Coastguard Worker template <GlobalMutexChoice mutexChoice> ScopedGlobalMutexLock()209*8975f5c5SAndroid Build Coastguard WorkerScopedGlobalMutexLock<mutexChoice>::ScopedGlobalMutexLock() 210*8975f5c5SAndroid Build Coastguard Worker { 211*8975f5c5SAndroid Build Coastguard Worker switch (mutexChoice) 212*8975f5c5SAndroid Build Coastguard Worker { 213*8975f5c5SAndroid Build Coastguard Worker case GlobalMutexChoice::EGL: 214*8975f5c5SAndroid Build Coastguard Worker mMutex = GetGlobalMutex(); 215*8975f5c5SAndroid Build Coastguard Worker break; 216*8975f5c5SAndroid Build Coastguard Worker case GlobalMutexChoice::Sync: 217*8975f5c5SAndroid Build Coastguard Worker mMutex = GetGlobalEGLSyncObjectMutex(); 218*8975f5c5SAndroid Build Coastguard Worker break; 219*8975f5c5SAndroid Build Coastguard Worker default: 220*8975f5c5SAndroid Build Coastguard Worker UNREACHABLE(); 221*8975f5c5SAndroid Build Coastguard Worker break; 222*8975f5c5SAndroid Build Coastguard Worker } 223*8975f5c5SAndroid Build Coastguard Worker 224*8975f5c5SAndroid Build Coastguard Worker mMutex->lock(); 225*8975f5c5SAndroid Build Coastguard Worker } 226*8975f5c5SAndroid Build Coastguard Worker 227*8975f5c5SAndroid Build Coastguard Worker template <GlobalMutexChoice mutexChoice> ~ScopedGlobalMutexLock()228*8975f5c5SAndroid Build Coastguard WorkerScopedGlobalMutexLock<mutexChoice>::~ScopedGlobalMutexLock() 229*8975f5c5SAndroid Build Coastguard Worker { 230*8975f5c5SAndroid Build Coastguard Worker mMutex->unlock(); 231*8975f5c5SAndroid Build Coastguard Worker } 232*8975f5c5SAndroid Build Coastguard Worker #endif 233*8975f5c5SAndroid Build Coastguard Worker 234*8975f5c5SAndroid Build Coastguard Worker template class ScopedGlobalMutexLock<GlobalMutexChoice::EGL>; 235*8975f5c5SAndroid Build Coastguard Worker template class ScopedGlobalMutexLock<GlobalMutexChoice::Sync>; 236*8975f5c5SAndroid Build Coastguard Worker } // namespace priv 237*8975f5c5SAndroid Build Coastguard Worker 238*8975f5c5SAndroid Build Coastguard Worker // ScopedOptionalGlobalMutexLock implementation. ScopedOptionalGlobalMutexLock(bool enabled)239*8975f5c5SAndroid Build Coastguard WorkerScopedOptionalGlobalMutexLock::ScopedOptionalGlobalMutexLock(bool enabled) 240*8975f5c5SAndroid Build Coastguard Worker { 241*8975f5c5SAndroid Build Coastguard Worker if (enabled) 242*8975f5c5SAndroid Build Coastguard Worker { 243*8975f5c5SAndroid Build Coastguard Worker #if defined(ANGLE_ENABLE_GLOBAL_MUTEX_LOAD_TIME_ALLOCATE) 244*8975f5c5SAndroid Build Coastguard Worker mMutex = priv::g_MutexPtr; 245*8975f5c5SAndroid Build Coastguard Worker #else 246*8975f5c5SAndroid Build Coastguard Worker mMutex = priv::GetGlobalMutex(); 247*8975f5c5SAndroid Build Coastguard Worker #endif 248*8975f5c5SAndroid Build Coastguard Worker mMutex->lock(); 249*8975f5c5SAndroid Build Coastguard Worker } 250*8975f5c5SAndroid Build Coastguard Worker else 251*8975f5c5SAndroid Build Coastguard Worker { 252*8975f5c5SAndroid Build Coastguard Worker mMutex = nullptr; 253*8975f5c5SAndroid Build Coastguard Worker } 254*8975f5c5SAndroid Build Coastguard Worker } 255*8975f5c5SAndroid Build Coastguard Worker ~ScopedOptionalGlobalMutexLock()256*8975f5c5SAndroid Build Coastguard WorkerScopedOptionalGlobalMutexLock::~ScopedOptionalGlobalMutexLock() 257*8975f5c5SAndroid Build Coastguard Worker { 258*8975f5c5SAndroid Build Coastguard Worker if (mMutex != nullptr) 259*8975f5c5SAndroid Build Coastguard Worker { 260*8975f5c5SAndroid Build Coastguard Worker mMutex->unlock(); 261*8975f5c5SAndroid Build Coastguard Worker } 262*8975f5c5SAndroid Build Coastguard Worker } 263*8975f5c5SAndroid Build Coastguard Worker 264*8975f5c5SAndroid Build Coastguard Worker // Global functions. 265*8975f5c5SAndroid Build Coastguard Worker #if defined(ANGLE_PLATFORM_WINDOWS) && !defined(ANGLE_STATIC) 266*8975f5c5SAndroid Build Coastguard Worker # if defined(ANGLE_ENABLE_GLOBAL_MUTEX_LOAD_TIME_ALLOCATE) 267*8975f5c5SAndroid Build Coastguard Worker # error "'angle_enable_global_mutex_load_time_allocate' is not supported in Windows DLL." 268*8975f5c5SAndroid Build Coastguard Worker # endif 269*8975f5c5SAndroid Build Coastguard Worker AllocateGlobalMutex()270*8975f5c5SAndroid Build Coastguard Workervoid AllocateGlobalMutex() 271*8975f5c5SAndroid Build Coastguard Worker { 272*8975f5c5SAndroid Build Coastguard Worker (void)priv::AllocateGlobalMutexImpl(&priv::g_Mutex); 273*8975f5c5SAndroid Build Coastguard Worker (void)priv::AllocateGlobalMutexImpl(&priv::g_EGLSyncMutex); 274*8975f5c5SAndroid Build Coastguard Worker } 275*8975f5c5SAndroid Build Coastguard Worker DeallocateGlobalMutexImpl(std::atomic<priv::GlobalMutex * > * globalMutex)276*8975f5c5SAndroid Build Coastguard Workervoid DeallocateGlobalMutexImpl(std::atomic<priv::GlobalMutex *> *globalMutex) 277*8975f5c5SAndroid Build Coastguard Worker { 278*8975f5c5SAndroid Build Coastguard Worker priv::GlobalMutex *mutex = globalMutex->exchange(nullptr); 279*8975f5c5SAndroid Build Coastguard Worker if (mutex != nullptr) 280*8975f5c5SAndroid Build Coastguard Worker { 281*8975f5c5SAndroid Build Coastguard Worker { 282*8975f5c5SAndroid Build Coastguard Worker // Wait for the mutex to become released by other threads before deleting. 283*8975f5c5SAndroid Build Coastguard Worker std::lock_guard<priv::GlobalMutex> lock(*mutex); 284*8975f5c5SAndroid Build Coastguard Worker } 285*8975f5c5SAndroid Build Coastguard Worker delete mutex; 286*8975f5c5SAndroid Build Coastguard Worker } 287*8975f5c5SAndroid Build Coastguard Worker } 288*8975f5c5SAndroid Build Coastguard Worker DeallocateGlobalMutex()289*8975f5c5SAndroid Build Coastguard Workervoid DeallocateGlobalMutex() 290*8975f5c5SAndroid Build Coastguard Worker { 291*8975f5c5SAndroid Build Coastguard Worker DeallocateGlobalMutexImpl(&priv::g_Mutex); 292*8975f5c5SAndroid Build Coastguard Worker DeallocateGlobalMutexImpl(&priv::g_EGLSyncMutex); 293*8975f5c5SAndroid Build Coastguard Worker } 294*8975f5c5SAndroid Build Coastguard Worker #endif 295*8975f5c5SAndroid Build Coastguard Worker 296*8975f5c5SAndroid Build Coastguard Worker } // namespace egl 297