diff options
author | vtkachenko@melody.mysql.com <> | 2005-12-20 14:56:45 +0100 |
---|---|---|
committer | vtkachenko@melody.mysql.com <> | 2005-12-20 14:56:45 +0100 |
commit | 22c930c924fcd6df57b84674cf629f27f750bde3 (patch) | |
tree | 0a2564d58c25ae11d3dbbc835c67a3e46438d523 | |
parent | b898368a93792215f45fb3706c2ea0710cadad97 (diff) | |
download | mariadb-git-22c930c924fcd6df57b84674cf629f27f750bde3.tar.gz |
Fast mutexes implementation
(spin-loop inside pthread_mutex_lock).
thr_mutex.c:
Added spinloop in mutex_lock
my_pthread.h:
Added definition of my_pthread_fastmutex_t
configure.in:
Added --with-fast-mutexes switch
-rw-r--r-- | configure.in | 14 | ||||
-rw-r--r-- | include/my_pthread.h | 31 | ||||
-rw-r--r-- | mysys/thr_mutex.c | 77 |
3 files changed, 122 insertions, 0 deletions
diff --git a/configure.in b/configure.in index b5d9b3267c6..3c9961e5c18 100644 --- a/configure.in +++ b/configure.in @@ -1574,6 +1574,20 @@ else CXXFLAGS="$OPTIMIZE_CXXFLAGS -DDBUG_OFF $CXXFLAGS" fi +if test "$with_debug" = "no" +then + AC_ARG_WITH([fast-mutexes], + AC_HELP_STRING([--with-fast-mutexes], + [compile with fast mutexes (default is enabled)]), + [with_fast_mutexes=$withval], [with_fast_mutexes=yes]) +fi + +if test "$with_fast_mutexes" = "yes" +then + AC_DEFINE([MY_PTHREAD_FASTMUTEX], [1], + [Define to 1 if you want to use fast mutexes]) +fi + # Force static compilation to avoid linking problems/get more speed AC_ARG_WITH(mysqld-ldflags, [ --with-mysqld-ldflags Extra linking arguments for mysqld], diff --git a/include/my_pthread.h b/include/my_pthread.h index 202e047dc4e..81100fe2b88 100644 --- a/include/my_pthread.h +++ b/include/my_pthread.h @@ -547,6 +547,37 @@ void safe_mutex_end(FILE *file); #define safe_mutex_assert_not_owner(mp) #endif /* SAFE_MUTEX */ +#if defined(MY_PTHREAD_FASTMUTEX) && !defined(SAFE_MUTEX) +typedef struct st_my_pthread_fastmutex_t +{ + pthread_mutex_t mutex; + uint spins; +} my_pthread_fastmutex_t; + +int my_pthread_fastmutex_init(my_pthread_fastmutex_t *mp, + const pthread_mutexattr_t *attr); +int my_pthread_fastmutex_lock(my_pthread_fastmutex_t *mp); + +#undef pthread_mutex_init +#undef pthread_mutex_lock +#undef pthread_mutex_unlock +#undef pthread_mutex_destroy +#undef pthread_mutex_wait +#undef pthread_mutex_timedwait +#undef pthread_mutex_t +#undef pthread_cond_wait +#undef pthread_cond_timedwait +#undef pthread_mutex_trylock +#define pthread_mutex_init(A,B) my_pthread_fastmutex_init((A),(B)) +#define pthread_mutex_lock(A) my_pthread_fastmutex_lock(A) +#define pthread_mutex_unlock(A) pthread_mutex_unlock(&(A)->mutex) +#define pthread_mutex_destroy(A) pthread_mutex_destroy(&(A)->mutex) +#define pthread_cond_wait(A,B) pthread_cond_wait((A),&(B)->mutex) +#define pthread_cond_timedwait(A,B,C) pthread_cond_timedwait((A),&(B)->mutex,(C)) +#define pthread_mutex_trylock(A) pthread_mutex_trylock(&(A)->mutex) +#define pthread_mutex_t my_pthread_fastmutex_t +#endif /* defined(MY_PTHREAD_FASTMUTEX) && !defined(SAFE_MUTEX) */ + /* READ-WRITE thread locking */ #ifdef HAVE_BROKEN_RWLOCK /* For OpenUnix */ diff --git a/mysys/thr_mutex.c b/mysys/thr_mutex.c index 3326068d164..3dde1fd5bfa 100644 --- a/mysys/thr_mutex.c +++ b/mysys/thr_mutex.c @@ -356,3 +356,80 @@ void safe_mutex_end(FILE *file __attribute__((unused))) } #endif /* THREAD && SAFE_MUTEX */ + +#if defined(THREAD) && defined(MY_PTHREAD_FASTMUTEX) && !defined(SAFE_MUTEX) + +#include "mysys_priv.h" +#include "my_static.h" +#include <m_string.h> + +#include <m_ctype.h> +#include <hash.h> +#include <myisampack.h> +#include <mysys_err.h> +#include <my_sys.h> + +#undef pthread_mutex_t +#undef pthread_mutex_init +#undef pthread_mutex_lock +#undef pthread_mutex_trylock +#undef pthread_mutex_unlock +#undef pthread_mutex_destroy +#undef pthread_cond_wait +#undef pthread_cond_timedwait + +ulong mutex_delay(ulong delayloops) +{ + ulong i; + volatile ulong j; + + j = 0; + + for (i = 0; i < delayloops * 50; i++) + j += i; + + return(j); +} + +#define MY_PTHREAD_FASTMUTEX_SPINS 8 +#define MY_PTHREAD_FASTMUTEX_DELAY 4 + +int my_pthread_fastmutex_init(my_pthread_fastmutex_t *mp, + const pthread_mutexattr_t *attr) +{ + static int cpu_count= 0; +#ifdef _SC_NPROCESSORS_CONF + if (!cpu_count && (attr == MY_MUTEX_INIT_FAST)) + cpu_count= sysconf(_SC_NPROCESSORS_CONF); +#endif + + if ((cpu_count > 1) && (attr == MY_MUTEX_INIT_FAST)) + mp->spins= MY_PTHREAD_FASTMUTEX_SPINS; + else + mp->spins= 0; + return pthread_mutex_init(&mp->mutex, attr); +} + +int my_pthread_fastmutex_lock(my_pthread_fastmutex_t *mp) +{ + int res; + uint i; + uint maxdelay= MY_PTHREAD_FASTMUTEX_DELAY; + + for (i= 0; i < mp->spins; i++) + { + res= pthread_mutex_trylock(&mp->mutex); + + if (res == 0) + return 0; + + if (res != EBUSY) + return res; + + mutex_delay(maxdelay); + maxdelay += ((double) random() / (double) RAND_MAX) * + MY_PTHREAD_FASTMUTEX_DELAY + 1; + } + return pthread_mutex_lock(&mp->mutex); +} +#endif /* defined(THREAD) && defined(MY_PTHREAD_FASTMUTEX) && !defined(SAFE_MUTEX) */ |