00001
00002
00003
00004
00005
00006
00007
00008 #include "config.h"
00009
00010 #ifdef HAVE_MUTEX_TAS
00011
00012 #ifndef lint
00013 static const char revid[] = "$Id: mut__tas_8c-source.html,v 1.1 2008/06/08 10:20:55 sebdiaz Exp $";
00014 #endif
00015
00016 #ifndef NO_SYSTEM_INCLUDES
00017 #include <sys/types.h>
00018
00019 #include <errno.h>
00020 #include <stdlib.h>
00021 #include <string.h>
00022 #include <unistd.h>
00023 #endif
00024
00025 #include "db_int.h"
00026
00027 #ifdef HAVE_MUTEX_68K_GCC_ASSEMBLY
00028 #include "68K.gcc"
00029 #endif
00030 #ifdef HAVE_MUTEX_ALPHA_GCC_ASSEMBLY
00031 #include "alpha.gcc"
00032 #endif
00033 #ifdef HAVE_MUTEX_HPPA_GCC_ASSEMBLY
00034 #include "parisc.gcc"
00035 #endif
00036 #ifdef HAVE_MUTEX_IA64_GCC_ASSEMBLY
00037 #include "ia64.gcc"
00038 #endif
00039 #ifdef HAVE_MUTEX_SCO_X86_CC_ASSEMBLY
00040 #include "sco.cc"
00041 #endif
00042 #ifdef HAVE_MUTEX_SPARC_GCC_ASSEMBLY
00043 #include "sparc.gcc"
00044 #endif
00045 #ifdef HAVE_MUTEX_X86_GCC_ASSEMBLY
00046 #include "x86.gcc"
00047 #endif
00048
00049 #ifdef DIAGNOSTIC
00050 #undef MSG1
00051 #define MSG1 "mutex_lock: ERROR: lock currently in use: pid: %lu.\n"
00052 #undef MSG2
00053 #define MSG2 "mutex_unlock: ERROR: lock already unlocked\n"
00054 #ifndef STDERR_FILENO
00055 #define STDERR_FILENO 2
00056 #endif
00057 #endif
00058
00059
00060
00061
00062
00063
00064
00065 int
00066 CDB___db_tas_mutex_init(dbenv, mutexp, flags)
00067 DB_ENV *dbenv;
00068 MUTEX *mutexp;
00069 u_int32_t flags;
00070 {
00071
00072 DB_ASSERT(((db_alignp_t)mutexp & (MUTEX_ALIGN - 1)) == 0);
00073
00074 memset(mutexp, 0, sizeof(*mutexp));
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084 if (LF_ISSET(MUTEX_THREAD) || F_ISSET(dbenv, DB_ENV_PRIVATE)) {
00085 if (!F_ISSET(dbenv, DB_ENV_THREAD)) {
00086 F_SET(mutexp, MUTEX_IGNORE);
00087 return (0);
00088 }
00089 F_SET(mutexp, MUTEX_THREAD);
00090 }
00091
00092
00093 if (MUTEX_INIT(&mutexp->tas))
00094 return (CDB___os_get_errno());
00095
00096 mutexp->spins = CDB___os_spin();
00097
00098 return (0);
00099 }
00100
00101
00102
00103
00104
00105
00106
00107 int
00108 CDB___db_tas_mutex_lock(mutexp)
00109 MUTEX *mutexp;
00110 {
00111 u_long ms;
00112 int nspins;
00113
00114 if (!DB_GLOBAL(db_mutexlocks) || F_ISSET(mutexp, MUTEX_IGNORE))
00115 return (0);
00116
00117 ms = 1;
00118
00119 loop:
00120 for (nspins = mutexp->spins; nspins > 0; --nspins) {
00121 #ifdef HAVE_MUTEX_HPPA_MSEM_INIT
00122 relock:
00123 #endif
00124 if (!MUTEX_SET(&mutexp->tas))
00125 continue;
00126 #ifdef HAVE_MUTEX_HPPA_MSEM_INIT
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137 if (mutexp->locked != 0) {
00138 mutexp->locked = (u_int32_t)getpid();
00139 goto relock;
00140 }
00141
00142
00143
00144
00145
00146 #endif
00147 #ifdef DIAGNOSTIC
00148 if (mutexp->locked != 0) {
00149 char msgbuf[128];
00150 (void)snprintf(msgbuf,
00151 sizeof(msgbuf), MSG1, (u_long)mutexp->locked);
00152 (void)write(STDERR_FILENO, msgbuf, strlen(msgbuf));
00153 }
00154 #endif
00155 #if defined(DIAGNOSTIC) || defined(HAVE_MUTEX_HPPA_MSEM_INIT)
00156 mutexp->locked = (u_int32_t)getpid();
00157 #endif
00158 if (ms == 1)
00159 ++mutexp->mutex_set_nowait;
00160 else
00161 ++mutexp->mutex_set_wait;
00162 return (0);
00163 }
00164
00165
00166 CDB___os_yield(NULL, ms * USEC_PER_MS);
00167 if ((ms <<= 1) > MS_PER_SEC)
00168 ms = MS_PER_SEC;
00169
00170 goto loop;
00171 }
00172
00173
00174
00175
00176
00177
00178
00179 int
00180 CDB___db_tas_mutex_unlock(mutexp)
00181 MUTEX *mutexp;
00182 {
00183 if (!DB_GLOBAL(db_mutexlocks) || F_ISSET(mutexp, MUTEX_IGNORE))
00184 return (0);
00185
00186 #ifdef DIAGNOSTIC
00187 if (!mutexp->locked)
00188 (void)write(STDERR_FILENO, MSG2, sizeof(MSG2) - 1);
00189 #endif
00190 #if defined(DIAGNOSTIC) || defined(HAVE_MUTEX_HPPA_MSEM_INIT)
00191 mutexp->locked = 0;
00192 #endif
00193
00194 MUTEX_UNSET(&mutexp->tas);
00195
00196 return (0);
00197 }
00198 #endif