154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius/* 254dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius****************************************************************************** 354dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* 459d709d503bab6e2b61931737e662dd293b40578ccornelius* Copyright (C) 1997-2013, International Business Machines 554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* Corporation and others. All Rights Reserved. 654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* 754dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius****************************************************************************** 854dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* 954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* File umutex.cpp 1054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* 1154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* Modification History: 1254dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* 1354dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* Date Name Description 1454dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* 04/02/97 aliu Creation. 1554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* 04/07/99 srl updated 1654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* 05/13/99 stephen Changed to umutex (from cmutex). 1754dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius* 11/22/99 aliu Make non-global mutex autoinitialize [j151] 1854dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius****************************************************************************** 1954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius*/ 2054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 2159d709d503bab6e2b61931737e662dd293b40578ccornelius#include "umutex.h" 2259d709d503bab6e2b61931737e662dd293b40578ccornelius 2354dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius#include "unicode/utypes.h" 2454dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius#include "uassert.h" 2559d709d503bab6e2b61931737e662dd293b40578ccornelius#include "cmemory.h" 2654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius#include "ucln_cmn.h" 2754dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 2859d709d503bab6e2b61931737e662dd293b40578ccornelius 2959d709d503bab6e2b61931737e662dd293b40578ccornelius// The ICU global mutex. Used when ICU implementation code passes NULL for the mutex pointer. 3059d709d503bab6e2b61931737e662dd293b40578ccorneliusstatic UMutex globalMutex = U_MUTEX_INITIALIZER; 3159d709d503bab6e2b61931737e662dd293b40578ccornelius 3254dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius/* 3354dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius * ICU Mutex wrappers. Wrap operating system mutexes, giving the rest of ICU a 3454dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius * platform independent set of mutex operations. For internal ICU use only. 3554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius */ 3654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 3759d709d503bab6e2b61931737e662dd293b40578ccornelius#if defined(U_USER_MUTEX_CPP) 3859d709d503bab6e2b61931737e662dd293b40578ccornelius// Build time user mutex hook: #include "U_USER_MUTEX_CPP" 3959d709d503bab6e2b61931737e662dd293b40578ccornelius#include U_MUTEX_XSTR(U_USER_MUTEX_CPP) 4054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 4159d709d503bab6e2b61931737e662dd293b40578ccornelius#elif U_PLATFORM_HAS_WIN32_API 4254dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 4359d709d503bab6e2b61931737e662dd293b40578ccornelius//------------------------------------------------------------------------------------------- 4459d709d503bab6e2b61931737e662dd293b40578ccornelius// 4559d709d503bab6e2b61931737e662dd293b40578ccornelius// Windows Specific Definitions 4659d709d503bab6e2b61931737e662dd293b40578ccornelius// 4759d709d503bab6e2b61931737e662dd293b40578ccornelius// Note: Cygwin (and possibly others) have both WIN32 and POSIX. 4859d709d503bab6e2b61931737e662dd293b40578ccornelius// Prefer Win32 in these cases. (Win32 comes ahead in the #if chain) 4959d709d503bab6e2b61931737e662dd293b40578ccornelius// 5059d709d503bab6e2b61931737e662dd293b40578ccornelius//------------------------------------------------------------------------------------------- 5154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 5259d709d503bab6e2b61931737e662dd293b40578ccornelius#if defined U_NO_PLATFORM_ATOMICS 5359d709d503bab6e2b61931737e662dd293b40578ccornelius#error ICU on Win32 requires support for low level atomic operations. 5459d709d503bab6e2b61931737e662dd293b40578ccornelius// Visual Studio, gcc, clang are OK. Shouldn't get here. 5554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius#endif 5654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 5754dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 5859d709d503bab6e2b61931737e662dd293b40578ccornelius// This function is called when a test of a UInitOnce::fState reveals that 5959d709d503bab6e2b61931737e662dd293b40578ccornelius// initialization has not completed, that we either need to call the 6059d709d503bab6e2b61931737e662dd293b40578ccornelius// function on this thread, or wait for some other thread to complete. 6154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius// 6259d709d503bab6e2b61931737e662dd293b40578ccornelius// The actual call to the init function is made inline by template code 6359d709d503bab6e2b61931737e662dd293b40578ccornelius// that knows the C++ types involved. This function returns TRUE if 6459d709d503bab6e2b61931737e662dd293b40578ccornelius// the caller needs to call the Init function. 6554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius// 6654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 6759d709d503bab6e2b61931737e662dd293b40578ccorneliusU_NAMESPACE_BEGIN 6854dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 6959d709d503bab6e2b61931737e662dd293b40578ccorneliusU_COMMON_API UBool U_EXPORT2 umtx_initImplPreInit(UInitOnce &uio) { 7059d709d503bab6e2b61931737e662dd293b40578ccornelius for (;;) { 7159d709d503bab6e2b61931737e662dd293b40578ccornelius int32_t previousState = InterlockedCompareExchange( 7259d709d503bab6e2b61931737e662dd293b40578ccornelius#if (U_PLATFORM == U_PF_MINGW) || (U_PLATFORM == U_PF_CYGWIN) 7359d709d503bab6e2b61931737e662dd293b40578ccornelius (LONG volatile *) // this is the type given in the API doc for this function. 7459d709d503bab6e2b61931737e662dd293b40578ccornelius#endif 7559d709d503bab6e2b61931737e662dd293b40578ccornelius &uio.fState, // Destination 7659d709d503bab6e2b61931737e662dd293b40578ccornelius 1, // Exchange Value 7759d709d503bab6e2b61931737e662dd293b40578ccornelius 0); // Compare value 7859d709d503bab6e2b61931737e662dd293b40578ccornelius 7959d709d503bab6e2b61931737e662dd293b40578ccornelius if (previousState == 0) { 8059d709d503bab6e2b61931737e662dd293b40578ccornelius return true; // Caller will next call the init function. 8159d709d503bab6e2b61931737e662dd293b40578ccornelius // Current state == 1. 8259d709d503bab6e2b61931737e662dd293b40578ccornelius } else if (previousState == 2) { 8359d709d503bab6e2b61931737e662dd293b40578ccornelius // Another thread already completed the initialization. 8459d709d503bab6e2b61931737e662dd293b40578ccornelius // We can simply return FALSE, indicating no 8559d709d503bab6e2b61931737e662dd293b40578ccornelius // further action is needed by the caller. 8659d709d503bab6e2b61931737e662dd293b40578ccornelius return FALSE; 8759d709d503bab6e2b61931737e662dd293b40578ccornelius } else { 8859d709d503bab6e2b61931737e662dd293b40578ccornelius // Another thread is currently running the initialization. 8959d709d503bab6e2b61931737e662dd293b40578ccornelius // Wait until it completes. 9059d709d503bab6e2b61931737e662dd293b40578ccornelius do { 9159d709d503bab6e2b61931737e662dd293b40578ccornelius Sleep(1); 9259d709d503bab6e2b61931737e662dd293b40578ccornelius previousState = umtx_loadAcquire(uio.fState); 9359d709d503bab6e2b61931737e662dd293b40578ccornelius } while (previousState == 1); 9454dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius } 9554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius } 9654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 9754dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 9859d709d503bab6e2b61931737e662dd293b40578ccornelius// This function is called by the thread that ran an initialization function, 9959d709d503bab6e2b61931737e662dd293b40578ccornelius// just after completing the function. 10059d709d503bab6e2b61931737e662dd293b40578ccornelius// 10159d709d503bab6e2b61931737e662dd293b40578ccornelius// success: True: the inialization succeeded. No further calls to the init 10259d709d503bab6e2b61931737e662dd293b40578ccornelius// function will be made. 10359d709d503bab6e2b61931737e662dd293b40578ccornelius// False: the initializtion failed. The next call to umtx_initOnce() 10459d709d503bab6e2b61931737e662dd293b40578ccornelius// will retry the initialization. 10554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 10659d709d503bab6e2b61931737e662dd293b40578ccorneliusU_COMMON_API void U_EXPORT2 umtx_initImplPostInit(UInitOnce &uio) { 10759d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_storeRelease(uio.fState, 2); 10854dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 10954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 11059d709d503bab6e2b61931737e662dd293b40578ccorneliusU_NAMESPACE_END 11154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 11259d709d503bab6e2b61931737e662dd293b40578ccorneliusstatic void winMutexInit(CRITICAL_SECTION *cs) { 11359d709d503bab6e2b61931737e662dd293b40578ccornelius InitializeCriticalSection(cs); 11459d709d503bab6e2b61931737e662dd293b40578ccornelius return; 11559d709d503bab6e2b61931737e662dd293b40578ccornelius} 11654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 11754dcd9b6a06071f647dac967e9e267abb9410720Craig CorneliusU_CAPI void U_EXPORT2 11854dcd9b6a06071f647dac967e9e267abb9410720Craig Corneliusumtx_lock(UMutex *mutex) { 11954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius if (mutex == NULL) { 12054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius mutex = &globalMutex; 12154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius } 12259d709d503bab6e2b61931737e662dd293b40578ccornelius CRITICAL_SECTION *cs = &mutex->fCS; 12359d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_initOnce(mutex->fInitOnce, winMutexInit, cs); 12459d709d503bab6e2b61931737e662dd293b40578ccornelius EnterCriticalSection(cs); 12554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 12654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 12754dcd9b6a06071f647dac967e9e267abb9410720Craig CorneliusU_CAPI void U_EXPORT2 12854dcd9b6a06071f647dac967e9e267abb9410720Craig Corneliusumtx_unlock(UMutex* mutex) 12954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius{ 13054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius if (mutex == NULL) { 13154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius mutex = &globalMutex; 13254dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius } 13359d709d503bab6e2b61931737e662dd293b40578ccornelius LeaveCriticalSection(&mutex->fCS); 13454dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 13554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 13659d709d503bab6e2b61931737e662dd293b40578ccornelius#elif U_PLATFORM_IMPLEMENTS_POSIX 13759d709d503bab6e2b61931737e662dd293b40578ccornelius 13859d709d503bab6e2b61931737e662dd293b40578ccornelius//------------------------------------------------------------------------------------------- 13954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius// 14059d709d503bab6e2b61931737e662dd293b40578ccornelius// POSIX specific definitions 14154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius// 14259d709d503bab6e2b61931737e662dd293b40578ccornelius//------------------------------------------------------------------------------------------- 14359d709d503bab6e2b61931737e662dd293b40578ccornelius 14459d709d503bab6e2b61931737e662dd293b40578ccornelius# include <pthread.h> 14559d709d503bab6e2b61931737e662dd293b40578ccornelius 14659d709d503bab6e2b61931737e662dd293b40578ccornelius// Each UMutex consists of a pthread_mutex_t. 14759d709d503bab6e2b61931737e662dd293b40578ccornelius// All are statically initialized and ready for use. 14859d709d503bab6e2b61931737e662dd293b40578ccornelius// There is no runtime mutex initialization code needed. 14954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 15054dcd9b6a06071f647dac967e9e267abb9410720Craig CorneliusU_CAPI void U_EXPORT2 15154dcd9b6a06071f647dac967e9e267abb9410720Craig Corneliusumtx_lock(UMutex *mutex) { 15254dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius if (mutex == NULL) { 15354dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius mutex = &globalMutex; 15454dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius } 15559d709d503bab6e2b61931737e662dd293b40578ccornelius int sysErr = pthread_mutex_lock(&mutex->fMutex); 15659d709d503bab6e2b61931737e662dd293b40578ccornelius (void)sysErr; // Suppress unused variable warnings. 15759d709d503bab6e2b61931737e662dd293b40578ccornelius U_ASSERT(sysErr == 0); 15854dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 15954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 16059d709d503bab6e2b61931737e662dd293b40578ccornelius 16154dcd9b6a06071f647dac967e9e267abb9410720Craig CorneliusU_CAPI void U_EXPORT2 16254dcd9b6a06071f647dac967e9e267abb9410720Craig Corneliusumtx_unlock(UMutex* mutex) 16354dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius{ 16454dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius if (mutex == NULL) { 16554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius mutex = &globalMutex; 16654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius } 16759d709d503bab6e2b61931737e662dd293b40578ccornelius int sysErr = pthread_mutex_unlock(&mutex->fMutex); 16859d709d503bab6e2b61931737e662dd293b40578ccornelius (void)sysErr; // Suppress unused variable warnings. 16959d709d503bab6e2b61931737e662dd293b40578ccornelius U_ASSERT(sysErr == 0); 17054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 17154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 17259d709d503bab6e2b61931737e662dd293b40578ccorneliusU_NAMESPACE_BEGIN 17354dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 17459d709d503bab6e2b61931737e662dd293b40578ccorneliusstatic pthread_mutex_t initMutex = PTHREAD_MUTEX_INITIALIZER; 17559d709d503bab6e2b61931737e662dd293b40578ccorneliusstatic pthread_cond_t initCondition = PTHREAD_COND_INITIALIZER; 17654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 17754dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 17859d709d503bab6e2b61931737e662dd293b40578ccornelius// This function is called when a test of a UInitOnce::fState reveals that 17959d709d503bab6e2b61931737e662dd293b40578ccornelius// initialization has not completed, that we either need to call the 18059d709d503bab6e2b61931737e662dd293b40578ccornelius// function on this thread, or wait for some other thread to complete. 18159d709d503bab6e2b61931737e662dd293b40578ccornelius// 18259d709d503bab6e2b61931737e662dd293b40578ccornelius// The actual call to the init function is made inline by template code 18359d709d503bab6e2b61931737e662dd293b40578ccornelius// that knows the C++ types involved. This function returns TRUE if 18459d709d503bab6e2b61931737e662dd293b40578ccornelius// the caller needs to call the Init function. 18559d709d503bab6e2b61931737e662dd293b40578ccornelius// 18659d709d503bab6e2b61931737e662dd293b40578ccorneliusU_COMMON_API UBool U_EXPORT2 18759d709d503bab6e2b61931737e662dd293b40578ccorneliusumtx_initImplPreInit(UInitOnce &uio) { 18859d709d503bab6e2b61931737e662dd293b40578ccornelius pthread_mutex_lock(&initMutex); 18959d709d503bab6e2b61931737e662dd293b40578ccornelius int32_t state = uio.fState; 19059d709d503bab6e2b61931737e662dd293b40578ccornelius if (state == 0) { 19159d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_storeRelease(uio.fState, 1); 19259d709d503bab6e2b61931737e662dd293b40578ccornelius pthread_mutex_unlock(&initMutex); 19359d709d503bab6e2b61931737e662dd293b40578ccornelius return TRUE; // Caller will next call the init function. 19459d709d503bab6e2b61931737e662dd293b40578ccornelius } else { 19559d709d503bab6e2b61931737e662dd293b40578ccornelius while (uio.fState == 1) { 19659d709d503bab6e2b61931737e662dd293b40578ccornelius // Another thread is currently running the initialization. 19759d709d503bab6e2b61931737e662dd293b40578ccornelius // Wait until it completes. 19859d709d503bab6e2b61931737e662dd293b40578ccornelius pthread_cond_wait(&initCondition, &initMutex); 19959d709d503bab6e2b61931737e662dd293b40578ccornelius } 20059d709d503bab6e2b61931737e662dd293b40578ccornelius pthread_mutex_unlock(&initMutex); 20159d709d503bab6e2b61931737e662dd293b40578ccornelius U_ASSERT(uio.fState == 2); 20259d709d503bab6e2b61931737e662dd293b40578ccornelius return FALSE; 20354dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius } 20459d709d503bab6e2b61931737e662dd293b40578ccornelius} 20554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 20654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 20759d709d503bab6e2b61931737e662dd293b40578ccornelius 20859d709d503bab6e2b61931737e662dd293b40578ccornelius// This function is called by the thread that ran an initialization function, 20959d709d503bab6e2b61931737e662dd293b40578ccornelius// just after completing the function. 21059d709d503bab6e2b61931737e662dd293b40578ccornelius// Some threads may be waiting on the condition, requiring the broadcast wakeup. 21159d709d503bab6e2b61931737e662dd293b40578ccornelius// Some threads may be racing to test the fState variable outside of the mutex, 21259d709d503bab6e2b61931737e662dd293b40578ccornelius// requiring the use of store/release when changing its value. 21359d709d503bab6e2b61931737e662dd293b40578ccornelius 21459d709d503bab6e2b61931737e662dd293b40578ccorneliusU_COMMON_API void U_EXPORT2 21559d709d503bab6e2b61931737e662dd293b40578ccorneliusumtx_initImplPostInit(UInitOnce &uio) { 21659d709d503bab6e2b61931737e662dd293b40578ccornelius pthread_mutex_lock(&initMutex); 21759d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_storeRelease(uio.fState, 2); 21859d709d503bab6e2b61931737e662dd293b40578ccornelius pthread_cond_broadcast(&initCondition); 21959d709d503bab6e2b61931737e662dd293b40578ccornelius pthread_mutex_unlock(&initMutex); 22054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 22154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 22259d709d503bab6e2b61931737e662dd293b40578ccorneliusU_NAMESPACE_END 22354dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 22459d709d503bab6e2b61931737e662dd293b40578ccornelius// End of POSIX specific umutex implementation. 22554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 22659d709d503bab6e2b61931737e662dd293b40578ccornelius#else // Platform #define chain. 22754dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 22859d709d503bab6e2b61931737e662dd293b40578ccornelius#error Unknown Platform 22954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 23059d709d503bab6e2b61931737e662dd293b40578ccornelius#endif // Platform #define chain. 23154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 23254dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 23359d709d503bab6e2b61931737e662dd293b40578ccornelius//------------------------------------------------------------------------------- 23459d709d503bab6e2b61931737e662dd293b40578ccornelius// 23559d709d503bab6e2b61931737e662dd293b40578ccornelius// Atomic Operations, out-of-line versions. 23659d709d503bab6e2b61931737e662dd293b40578ccornelius// These are conditional, only defined if better versions 23759d709d503bab6e2b61931737e662dd293b40578ccornelius// were not available for the platform. 23859d709d503bab6e2b61931737e662dd293b40578ccornelius// 23959d709d503bab6e2b61931737e662dd293b40578ccornelius// These versions are platform neutral. 24059d709d503bab6e2b61931737e662dd293b40578ccornelius// 24159d709d503bab6e2b61931737e662dd293b40578ccornelius//-------------------------------------------------------------------------------- 24254dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 24359d709d503bab6e2b61931737e662dd293b40578ccornelius#if defined U_NO_PLATFORM_ATOMICS 24454dcd9b6a06071f647dac967e9e267abb9410720Craig Corneliusstatic UMutex gIncDecMutex = U_MUTEX_INITIALIZER; 24554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 24659d709d503bab6e2b61931737e662dd293b40578ccorneliusU_NAMESPACE_BEGIN 24759d709d503bab6e2b61931737e662dd293b40578ccornelius 24859d709d503bab6e2b61931737e662dd293b40578ccorneliusU_COMMON_API int32_t U_EXPORT2 24959d709d503bab6e2b61931737e662dd293b40578ccorneliusumtx_atomic_inc(u_atomic_int32_t *p) { 25054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius int32_t retVal; 25159d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_lock(&gIncDecMutex); 25259d709d503bab6e2b61931737e662dd293b40578ccornelius retVal = ++(*p); 25359d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_unlock(&gIncDecMutex); 25454dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius return retVal; 25554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 25654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 25759d709d503bab6e2b61931737e662dd293b40578ccornelius 25859d709d503bab6e2b61931737e662dd293b40578ccorneliusU_COMMON_API int32_t U_EXPORT2 25959d709d503bab6e2b61931737e662dd293b40578ccorneliusumtx_atomic_dec(u_atomic_int32_t *p) { 26054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius int32_t retVal; 26159d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_lock(&gIncDecMutex); 26259d709d503bab6e2b61931737e662dd293b40578ccornelius retVal = --(*p); 26359d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_unlock(&gIncDecMutex); 26454dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius return retVal; 26554dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 26654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 26759d709d503bab6e2b61931737e662dd293b40578ccorneliusU_COMMON_API int32_t U_EXPORT2 26859d709d503bab6e2b61931737e662dd293b40578ccorneliusumtx_loadAcquire(u_atomic_int32_t &var) { 26959d709d503bab6e2b61931737e662dd293b40578ccornelius int32_t val = var; 27059d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_lock(&gIncDecMutex); 27159d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_unlock(&gIncDecMutex); 27259d709d503bab6e2b61931737e662dd293b40578ccornelius return val; 27359d709d503bab6e2b61931737e662dd293b40578ccornelius} 27459d709d503bab6e2b61931737e662dd293b40578ccornelius 27559d709d503bab6e2b61931737e662dd293b40578ccorneliusU_COMMON_API void U_EXPORT2 27659d709d503bab6e2b61931737e662dd293b40578ccorneliusumtx_storeRelease(u_atomic_int32_t &var, int32_t val) { 27759d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_lock(&gIncDecMutex); 27859d709d503bab6e2b61931737e662dd293b40578ccornelius umtx_unlock(&gIncDecMutex); 27959d709d503bab6e2b61931737e662dd293b40578ccornelius var = val; 28059d709d503bab6e2b61931737e662dd293b40578ccornelius} 28154dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 28259d709d503bab6e2b61931737e662dd293b40578ccorneliusU_NAMESPACE_END 28359d709d503bab6e2b61931737e662dd293b40578ccornelius#endif 28454dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 28559d709d503bab6e2b61931737e662dd293b40578ccornelius//-------------------------------------------------------------------------- 28659d709d503bab6e2b61931737e662dd293b40578ccornelius// 28759d709d503bab6e2b61931737e662dd293b40578ccornelius// Deprecated functions for setting user mutexes. 28859d709d503bab6e2b61931737e662dd293b40578ccornelius// 28959d709d503bab6e2b61931737e662dd293b40578ccornelius//-------------------------------------------------------------------------- 29054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 29159d709d503bab6e2b61931737e662dd293b40578ccorneliusU_DEPRECATED void U_EXPORT2 29259d709d503bab6e2b61931737e662dd293b40578ccorneliusu_setMutexFunctions(const void * /*context */, UMtxInitFn *, UMtxFn *, 29359d709d503bab6e2b61931737e662dd293b40578ccornelius UMtxFn *, UMtxFn *, UErrorCode *status) { 29459d709d503bab6e2b61931737e662dd293b40578ccornelius if (U_SUCCESS(*status)) { 29559d709d503bab6e2b61931737e662dd293b40578ccornelius *status = U_UNSUPPORTED_ERROR; 29654dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius } 29759d709d503bab6e2b61931737e662dd293b40578ccornelius return; 29854dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 29954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 30054dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius 30159d709d503bab6e2b61931737e662dd293b40578ccornelius 30259d709d503bab6e2b61931737e662dd293b40578ccorneliusU_DEPRECATED void U_EXPORT2 30359d709d503bab6e2b61931737e662dd293b40578ccorneliusu_setAtomicIncDecFunctions(const void * /*context */, UMtxAtomicFn *, UMtxAtomicFn *, 30459d709d503bab6e2b61931737e662dd293b40578ccornelius UErrorCode *status) { 30559d709d503bab6e2b61931737e662dd293b40578ccornelius if (U_SUCCESS(*status)) { 30659d709d503bab6e2b61931737e662dd293b40578ccornelius *status = U_UNSUPPORTED_ERROR; 30759d709d503bab6e2b61931737e662dd293b40578ccornelius } 30859d709d503bab6e2b61931737e662dd293b40578ccornelius return; 30954dcd9b6a06071f647dac967e9e267abb9410720Craig Cornelius} 310