00001 // -*- C++ -*- 00002 00003 //============================================================================= 00004 /** 00005 * @file Process_Mutex.h 00006 * 00007 * $Id: Process_Mutex.h 87179 2009-10-20 16:27:01Z shuston $ 00008 * 00009 * A wrapper for mutexes that can be used across processes on the 00010 * same host machine, as well as within a process, of course. 00011 * 00012 * @author Douglas C. Schmidt <schmidt@uci.edu> 00013 */ 00014 //============================================================================= 00015 00016 #ifndef ACE_PROCESS_MUTEX_H 00017 #define ACE_PROCESS_MUTEX_H 00018 00019 #include /**/ "ace/pre.h" 00020 00021 #include /**/ "ace/config-all.h" 00022 00023 #if !defined (ACE_LACKS_PRAGMA_ONCE) 00024 # pragma once 00025 #endif /* ACE_LACKS_PRAGMA_ONCE */ 00026 00027 // To make it easier to carry the setting though this file as well as 00028 // Process_Mutex.{cpp inl}, set a private macro here. 00029 #ifdef _ACE_USE_SV_SEM 00030 # undef _ACE_USE_SV_SEM 00031 #endif /* _ACE_USE_SV_SEM */ 00032 00033 #if defined (ACE_HAS_SYSV_IPC) && !defined (ACE_USES_MUTEX_FOR_PROCESS_MUTEX) 00034 # include "ace/SV_Semaphore_Complex.h" 00035 # define _ACE_USE_SV_SEM 00036 #else 00037 # include "ace/Mutex.h" 00038 #endif /* ACE_HAS_SYSV_IPC && !ACE_USES_MUTEX_FOR_PROCESS_MUTEX */ 00039 00040 ACE_BEGIN_VERSIONED_NAMESPACE_DECL 00041 00042 // Forward declarations 00043 class ACE_Time_Value; 00044 00045 /** 00046 * @class ACE_Process_Mutex 00047 * 00048 * @brief A wrapper for mutexes that can be used across processes on 00049 * the same host machine, as well as within a process, of course. 00050 * 00051 * @attention The mechanism upon which @c ACE_Process_Mutex is based 00052 * can be configured at build time to be either @c ACE_SV_Semaphore_Complex 00053 * (on platforms that support it) or @c ACE_Mutex. On platforms that offer 00054 * System V IPC (the @c ACE_HAS_SYSV_IPC config macro is defined) 00055 * @c ACE_SV_Semaphore_Complex is the default because it is more convenient 00056 * and easy to use. @c ACE_Mutex is the default on all other platforms. 00057 * On platforms where ACE_SV_Semaphore_Complex is used by default, the 00058 * mechanism can be changed to ACE_Mutex when ACE is built by adding 00059 * @code 00060 * #define ACE_USES_MUTEX_FOR_PROCESS_MUTEX 00061 * @endcode 00062 * to your @c config.h file. 00063 * @par 00064 * Consider these tradeoffs when evaluating whether or not to change 00065 * the default: 00066 * - Some platforms (e.g., Pthreads and UI Threads) require interprocess 00067 * mutexes to be allocated from shared memory. On these platforms, using 00068 * ACE_Mutex as the underlying mechanism requires that ACE_Process_Mutex 00069 * objects be allocated in shared memory. Using ACE_SV_Semaphore_Complex 00070 * avoids this restriction. 00071 * - System V IPC kernel parameters have a low default limit on some 00072 * platforms. This would restrict the number of ACE_Process_Mutex objects 00073 * that can be in use simultaneously when using ACE_SV_Semaphore_Complex. 00074 * - If you require the ability to do a timed @c acquire(), you must 00075 * use ACE_Mutex as the underlying mechanism because timed acquire does not 00076 * work with System V semaphores. 00077 * - When using ACE_Mutex on a Pthreads-based platform, an ACE_Process_Mutex 00078 * object is deleted when the process which created the object destroys 00079 * it, regardless of whether or not there are other processes still 00080 * accessing the ACE_Process_Mutex. Using ACE_SV_Semaphore_Complex avoids 00081 * this problem; the semaphore is destroyed when the last use of the 00082 * object ends. For portable applications it is better to always ensure 00083 * that the owner of the mutex destroys it after all other processes have 00084 * stopped using it. 00085 */ 00086 class ACE_Export ACE_Process_Mutex 00087 { 00088 public: 00089 /** 00090 * Create an ACE_Process_Mutex. 00091 * 00092 * @param name optional, null-terminated string containing the name of 00093 * the object. Multiple users of the same @c ACE_Process_Mutex must use 00094 * the same name to access the same object. If not specified, a name 00095 * is generated. 00096 * @param arg optional, attributes to be used to initialize the mutex. 00097 * If using @c ACE_SV_Semaphore_Complex as the underlying mechanism, 00098 * this argument is ignored. 00099 * @param mode optional, the protection mode for either the backing store 00100 * file (for ACE_Mutex use) or the ACE_SV_Semaphore_Complex that's created. 00101 */ 00102 ACE_Process_Mutex (const char *name = 0, 00103 void *arg = 0, 00104 mode_t mode = ACE_DEFAULT_FILE_PERMS); 00105 00106 #if defined (ACE_HAS_WCHAR) 00107 /** 00108 * Create an ACE_Process_Mutex (@c wchar_t version) 00109 * 00110 * @param name optional, null-terminated string containing the name of 00111 * the object. Multiple users of the same @c ACE_Process_Mutex must use 00112 * the same name to access the same object. If not specified, a name 00113 * is generated. 00114 * @param arg optional, attributes to be used to initialize the mutex. 00115 * If using @c ACE_SV_Semaphore_Complex as the underlying mechanism, 00116 * this argument is ignored. 00117 * @param mode optional, the protection mode for either the backing store 00118 * file (for ACE_Mutex use) or the ACE_SV_Semaphore_Complex that's created. 00119 */ 00120 ACE_Process_Mutex (const wchar_t *name, 00121 void *arg = 0, 00122 mode_t mode = ACE_DEFAULT_FILE_PERMS); 00123 #endif /* ACE_HAS_WCHAR */ 00124 00125 /** 00126 * Destructor. 00127 * 00128 * @note The destructor will not release an acquired mutex except 00129 * on Windows. 00130 */ 00131 ~ACE_Process_Mutex (void); 00132 00133 /** 00134 * Explicitly destroy the mutex. Note that only one thread should 00135 * call this method since it doesn't protect against race 00136 * conditions. 00137 * 00138 * @return 0 on success; -1 on failure. 00139 */ 00140 int remove (void); 00141 00142 /** 00143 * Acquire lock ownership (wait on queue if necessary). 00144 * 00145 * @return 0 on success; -1 on failure. 00146 */ 00147 int acquire (void); 00148 00149 /** 00150 * Acquire lock ownership, but timeout if lock if hasn't been 00151 * acquired by given time. 00152 * 00153 * @param tv the absolute time until which the caller is willing to 00154 * wait to acquire the lock. 00155 * 00156 * @return 0 on success; -1 on failure. 00157 */ 00158 int acquire (ACE_Time_Value &tv); 00159 00160 /** 00161 * Conditionally acquire lock (i.e., don't wait on queue). 00162 * 00163 * @return 0 on success; -1 on failure. If the lock could not be acquired 00164 * because someone else already had the lock, @c errno is set to @c EBUSY. 00165 */ 00166 int tryacquire (void); 00167 00168 /// Release lock and unblock a thread at head of queue. 00169 int release (void); 00170 00171 /// Acquire lock ownership (wait on queue if necessary). 00172 int acquire_read (void); 00173 00174 /// Acquire lock ownership (wait on queue if necessary). 00175 int acquire_write (void); 00176 00177 /** 00178 * Conditionally acquire a lock (i.e., won't block). Returns -1 on 00179 * failure. If we "failed" because someone else already had the 00180 * lock, @c errno is set to @c EBUSY. 00181 */ 00182 int tryacquire_read (void); 00183 00184 /** 00185 * Conditionally acquire a lock (i.e., won't block). Returns -1 on 00186 * failure. If we "failed" because someone else already had the 00187 * lock, @c errno is set to @c EBUSY. 00188 */ 00189 int tryacquire_write (void); 00190 00191 /** 00192 * This is only here for consistency with the other synchronization 00193 * APIs and usability with Lock adapters. Assumes the caller already has 00194 * acquired the mutex and returns 0 in all cases. 00195 */ 00196 int tryacquire_write_upgrade (void); 00197 00198 #if !defined (_ACE_USE_SV_SEM) 00199 /// Return the underlying mutex. 00200 const ACE_mutex_t &lock (void) const; 00201 #endif /* !_ACE_USE_SV_SEM */ 00202 00203 /// Dump the state of an object. 00204 void dump (void) const; 00205 00206 /// Declare the dynamic allocation hooks. 00207 ACE_ALLOC_HOOK_DECLARE; 00208 00209 private: 00210 /// If the user does not provide a name we generate a unique name in 00211 /// this buffer. 00212 ACE_TCHAR name_[ACE_UNIQUE_NAME_LEN]; 00213 00214 /// Create and return the unique name. 00215 const ACE_TCHAR *unique_name (void); 00216 00217 #if defined (_ACE_USE_SV_SEM) 00218 /// We need this to get the right semantics... 00219 ACE_SV_Semaphore_Complex lock_; 00220 #else 00221 ACE_Mutex lock_; 00222 #endif /* _ACE_USE_SV_SEM */ 00223 }; 00224 00225 ACE_END_VERSIONED_NAMESPACE_DECL 00226 00227 #if defined (__ACE_INLINE__) 00228 #include "ace/Process_Mutex.inl" 00229 #endif /* __ACE_INLINE__ */ 00230 00231 #include /**/ "ace/post.h" 00232 00233 #endif /* ACE_PROCESS_MUTEX_H */