diff options
Diffstat (limited to 'linuxthreads')
-rw-r--r-- | linuxthreads/ChangeLog | 31 | ||||
-rw-r--r-- | linuxthreads/oldsemaphore.c | 2 | ||||
-rw-r--r-- | linuxthreads/shlib-versions | 1 | ||||
-rw-r--r-- | linuxthreads/spinlock.c | 8 | ||||
-rw-r--r-- | linuxthreads/spinlock.h | 15 | ||||
-rw-r--r-- | linuxthreads/sysdeps/hppa/pspinlock.c | 81 | ||||
-rw-r--r-- | linuxthreads/sysdeps/hppa/pt-machine.h | 54 | ||||
-rw-r--r-- | linuxthreads/sysdeps/pthread/bits/initspin.h | 28 | ||||
-rw-r--r-- | linuxthreads/sysdeps/pthread/bits/libc-lock.h | 23 | ||||
-rw-r--r-- | linuxthreads/sysdeps/pthread/pthread.h | 15 | ||||
-rw-r--r-- | linuxthreads/sysdeps/unix/sysv/linux/hppa/bits/initspin.h | 27 |
11 files changed, 256 insertions, 29 deletions
diff --git a/linuxthreads/ChangeLog b/linuxthreads/ChangeLog index dc0a248..f863f66 100644 --- a/linuxthreads/ChangeLog +++ b/linuxthreads/ChangeLog @@ -1,3 +1,34 @@ +2000-10-12 Alan Modra <alan@linuxcare.com.au> + + * sysdeps/pthread/bits/initspin.h: New file. + * spinlock.h: Move LOCK_INITIALIZER definition to <bits/initspin.h>. + (__pthread_init_lock): Initialize lock with LT_SPINLOCK_INIT. + (__pthread_alt_init_lock): Likewise. + (__pthread_alt_trylock): Release lock with LT_SPINLOCK_INIT. + +2000-10-12 David Huggins-Daines <dhd@linuxcare.com> + + * oldsemaphore.c (__old_sem_init): Release lock with + LT_SPINLOCK_INIT, not zero. + * spinlock.c (__pthread_unlock): Likewise. + (__pthread_alt_lock): Likewise. + (__pthread_alt_timedlock): Likewise. + (__pthread_alt_unlock): Likewise. + * sysdeps/pthread/bits/libc-lock.h: Initialize locks with + LT_SPINLOCK_INIT if it is non-zero. Likewise for init-once flags. + * sysdeps/pthread/pthread.h: Include bits/initspin.h. Use + LT_SPINLOCK_INIT do initialize spinlocks not 0. + +2000-10-12 David Huggins-Daines <dhd@linuxcare.com> + + * shlib-versions: Add version definitions for hppa-linux. + +2000-10-12 Alan Modra <alan@linuxcare.com.au> + + * sysdeps/hppa/pspinlock.c: New file. + * sysdeps/hppa/pt-machine.h: New file. + * sysdeps/unix/sysv/linux/hppa/bits/initspin.h: New file. + 2000-10-05 Jakub Jelinek <jakub@redhat.com> * mutex.c (__pthread_mutex_destroy): Correct test of diff --git a/linuxthreads/oldsemaphore.c b/linuxthreads/oldsemaphore.c index 52957d9..b9eb20f 100644 --- a/linuxthreads/oldsemaphore.c +++ b/linuxthreads/oldsemaphore.c @@ -65,7 +65,7 @@ int __old_sem_init(old_sem_t *sem, int pshared, unsigned int value) errno = ENOSYS; return -1; } - sem->sem_spinlock = 0; + sem->sem_spinlock = LT_SPINLOCK_INIT; sem->sem_status = ((long)value << 1) + 1; return 0; } diff --git a/linuxthreads/shlib-versions b/linuxthreads/shlib-versions index 763639a..5344c6b 100644 --- a/linuxthreads/shlib-versions +++ b/linuxthreads/shlib-versions @@ -3,4 +3,5 @@ mips.*-.*-linux.* libpthread=0 GLIBC_2.0 GLIBC_2.2 sparc64-.*-linux.* libpthread=0 GLIBC_2.2 sh.*-.*-linux.* libpthread=0 GLIBC_2.2 ia64.*-.*-linux.* libpthread=0 GLIBC_2.2 +hppa.*-.*-linux.* libpthread=0 GLIBC_2.2 .*-.*-linux.* libpthread=0 diff --git a/linuxthreads/spinlock.c b/linuxthreads/spinlock.c index 102b1be..5846c45 100644 --- a/linuxthreads/spinlock.c +++ b/linuxthreads/spinlock.c @@ -155,7 +155,7 @@ int __pthread_unlock(struct _pthread_fastlock * lock) #if !defined HAS_COMPARE_AND_SWAP || defined TEST_FOR_COMPARE_AND_SWAP { WRITE_MEMORY_BARRIER(); - lock->__spinlock = 0; + lock->__spinlock = LT_SPINLOCK_INIT; return 0; } #endif @@ -394,7 +394,7 @@ void __pthread_alt_lock(struct _pthread_fastlock * lock, } WRITE_MEMORY_BARRIER(); - lock->__spinlock = 0; + lock->__spinlock = LT_SPINLOCK_INIT; if (suspend_needed) suspend (self); @@ -468,7 +468,7 @@ int __pthread_alt_timedlock(struct _pthread_fastlock * lock, } WRITE_MEMORY_BARRIER(); - lock->__spinlock = 0; + lock->__spinlock = LT_SPINLOCK_INIT; goto suspend; } #endif @@ -649,7 +649,7 @@ void __pthread_alt_unlock(struct _pthread_fastlock *lock) #if !defined HAS_COMPARE_AND_SWAP || defined TEST_FOR_COMPARE_AND_SWAP { WRITE_MEMORY_BARRIER(); - lock->__spinlock = 0; + lock->__spinlock = LT_SPINLOCK_INIT; } #endif } diff --git a/linuxthreads/spinlock.h b/linuxthreads/spinlock.h index 2d3e9bf..9fbeff1 100644 --- a/linuxthreads/spinlock.h +++ b/linuxthreads/spinlock.h @@ -12,6 +12,8 @@ /* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */ /* GNU Library General Public License for more details. */ +#include <bits/initspin.h> + /* There are 2 compare and swap synchronization primitives with different semantics: @@ -97,7 +99,7 @@ extern int __pthread_unlock(struct _pthread_fastlock *lock); static inline void __pthread_init_lock(struct _pthread_fastlock * lock) { lock->__status = 0; - lock->__spinlock = 0; + lock->__spinlock = LT_SPINLOCK_INIT; } static inline int __pthread_trylock (struct _pthread_fastlock * lock) @@ -139,7 +141,7 @@ extern void __pthread_alt_unlock(struct _pthread_fastlock *lock); static inline void __pthread_alt_init_lock(struct _pthread_fastlock * lock) { lock->__status = 0; - lock->__spinlock = 0; + lock->__spinlock = LT_SPINLOCK_INIT; } static inline int __pthread_alt_trylock (struct _pthread_fastlock * lock) @@ -163,7 +165,7 @@ static inline int __pthread_alt_trylock (struct _pthread_fastlock * lock) WRITE_MEMORY_BARRIER(); res = 0; } - lock->__spinlock = 0; + lock->__spinlock = LT_SPINLOCK_INIT; } return res; } @@ -178,11 +180,6 @@ static inline int __pthread_alt_trylock (struct _pthread_fastlock * lock) #endif } -/* Initializers for both lock variants */ - -#define LOCK_INITIALIZER {0, 0} -#define ALT_LOCK_INITIALIZER {0, 0} - /* Operations on pthread_atomic, which is defined in internals.h */ static inline long atomic_increment(struct pthread_atomic *pa) @@ -208,8 +205,6 @@ static inline long atomic_decrement(struct pthread_atomic *pa) return oldval; } -#define ATOMIC_INITIALIZER { 0, 0 } - static inline void __pthread_set_own_extricate_if (pthread_descr self, pthread_extricate_if *peif) diff --git a/linuxthreads/sysdeps/hppa/pspinlock.c b/linuxthreads/sysdeps/hppa/pspinlock.c new file mode 100644 index 0000000..1b1511f --- /dev/null +++ b/linuxthreads/sysdeps/hppa/pspinlock.c @@ -0,0 +1,81 @@ +/* POSIX spinlock implementation. hppa version. + Copyright (C) 2000 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public License as + published by the Free Software Foundation; either version 2 of the + License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public + License along with the GNU C Library; see the file COPYING.LIB. If not, + write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. */ + +#include <errno.h> +#include <pthread.h> + + +int +__pthread_spin_lock (pthread_spinlock_t *lock) +{ + unsigned int val; + + do + asm volatile ("ldcw %1,%0" + : "=r" (val), "=m" (*lock) + : "m" (*lock)); + while (!val); + + return 0; +} +weak_alias (__pthread_spin_lock, pthread_spin_lock) + + +int +__pthread_spin_trylock (pthread_spinlock_t *lock) +{ + unsigned int val; + + asm volatile ("ldcw %1,%0" + : "=r" (val), "=m" (*lock) + : "m" (*lock)); + + return val ? 0 : EBUSY; +} +weak_alias (__pthread_spin_trylock, pthread_spin_trylock) + + +int +__pthread_spin_unlock (pthread_spinlock_t *lock) +{ + *lock = 1; + return 0; +} +weak_alias (__pthread_spin_unlock, pthread_spin_unlock) + + +int +__pthread_spin_init (pthread_spinlock_t *lock, int pshared) +{ + /* We can ignore the `pshared' parameter. Since we are busy-waiting + all processes which can access the memory location `lock' points + to can use the spinlock. */ + *lock = 1; + return 0; +} +weak_alias (__pthread_spin_init, pthread_spin_init) + + +int +__pthread_spin_destroy (pthread_spinlock_t *lock) +{ + /* Nothing to do. */ + return 0; +} +weak_alias (__pthread_spin_destroy, pthread_spin_destroy) diff --git a/linuxthreads/sysdeps/hppa/pt-machine.h b/linuxthreads/sysdeps/hppa/pt-machine.h new file mode 100644 index 0000000..bc0d2d6 --- /dev/null +++ b/linuxthreads/sysdeps/hppa/pt-machine.h @@ -0,0 +1,54 @@ +/* Machine-dependent pthreads configuration and inline functions. + hppa version. + Copyright (C) 2000 Free Software Foundation, Inc. + This file is part of the GNU C Library. + Contributed by Richard Henderson <rth@tamu.edu>. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public License as + published by the Free Software Foundation; either version 2 of the + License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public + License along with the GNU C Library; see the file COPYING.LIB. If not, + write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. */ + +#include <bits/initspin.h> + +#ifndef PT_EI +# define PT_EI extern inline +#endif + +/* Get some notion of the current stack. Need not be exactly the top + of the stack, just something somewhere in the current frame. */ +#define CURRENT_STACK_FRAME stack_pointer +register char * stack_pointer __asm__ ("%r30"); + + +/* The hppa only has one atomic read and modify memory operation, + load and clear, so hppa spinlocks must use zero to signify that + someone is holding the lock. */ + +#define xstr(s) str(s) +#define str(s) #s +/* Spinlock implementation; required. */ +PT_EI int +testandset (int *spinlock) +{ + int ret; + + __asm__ __volatile__( + "ldcw 0(%2),%0" + : "=r"(ret), "=m"(*spinlock) + : "r"(spinlock)); + + return ret == 0; +} +#undef str +#undef xstr diff --git a/linuxthreads/sysdeps/pthread/bits/initspin.h b/linuxthreads/sysdeps/pthread/bits/initspin.h new file mode 100644 index 0000000..050983c --- /dev/null +++ b/linuxthreads/sysdeps/pthread/bits/initspin.h @@ -0,0 +1,28 @@ +/* Generic definitions for spinlock initializers. + Copyright (C) 2000 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public License as + published by the Free Software Foundation; either version 2 of the + License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public + License along with the GNU C Library; see the file COPYING.LIB. If not, + write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. */ + +/* Initial value of a spinlock. Most platforms should use zero, + unless they only implement a "test and clear" operation instead of + the usual "test and set". */ +#define LT_SPINLOCK_INIT 0 + +/* Macros for lock initializers, using the above definition. */ +#define LOCK_INITIALIZER { 0, LT_SPINLOCK_INIT } +#define ALT_LOCK_INITIALIZER { 0, LT_SPINLOCK_INIT } +#define ATOMIC_INITIALIZER { 0, LT_SPINLOCK_INIT } diff --git a/linuxthreads/sysdeps/pthread/bits/libc-lock.h b/linuxthreads/sysdeps/pthread/bits/libc-lock.h index d0e9a8d..41bca4d 100644 --- a/linuxthreads/sysdeps/pthread/bits/libc-lock.h +++ b/linuxthreads/sysdeps/pthread/bits/libc-lock.h @@ -48,12 +48,21 @@ typedef pthread_key_t __libc_key_t; /* Define an initialized lock variable NAME with storage class CLASS. - For the C library we take a deeper look at the initializer. For this - implementation all fields are initialized to zero. Therefore we - don't initialize the variable which allows putting it into the BSS - section. */ -#define __libc_lock_define_initialized(CLASS,NAME) \ + For the C library we take a deeper look at the initializer. For + this implementation all fields are initialized to zero. Therefore + we don't initialize the variable which allows putting it into the + BSS section. (Except on PA-RISC and other odd architectures, where + initialized locks must be set to one due to the lack of normal + atomic operations.) */ + +#if LT_SPINLOCK_INIT == 0 +# define __libc_lock_define_initialized(CLASS,NAME) \ CLASS __libc_lock_t NAME; +#else +# define __libc_lock_define_initialized(CLASS,NAME) \ + CLASS __libc_lock_t NAME = PTHREAD_MUTEX_INITIALIZER; +#endif + #define __libc_rwlock_define_initialized(CLASS,NAME) \ CLASS __libc_rwlock_t NAME = PTHREAD_RWLOCK_INITIALIZER; @@ -143,9 +152,9 @@ typedef pthread_key_t __libc_key_t; do { \ if (__pthread_once != NULL) \ __pthread_once (&(ONCE_CONTROL), (INIT_FUNCTION)); \ - else if ((ONCE_CONTROL) == 0) { \ + else if ((ONCE_CONTROL) == PTHREAD_ONCE_INIT) { \ INIT_FUNCTION (); \ - (ONCE_CONTROL) = 1; \ + (ONCE_CONTROL) = !PTHREAD_ONCE_INIT; \ } \ } while (0) diff --git a/linuxthreads/sysdeps/pthread/pthread.h b/linuxthreads/sysdeps/pthread/pthread.h index f2a742e..45be6cf 100644 --- a/linuxthreads/sysdeps/pthread/pthread.h +++ b/linuxthreads/sysdeps/pthread/pthread.h @@ -23,6 +23,7 @@ #define __need_sigset_t #include <signal.h> #include <bits/pthreadtypes.h> +#include <bits/initspin.h> __BEGIN_DECLS @@ -30,26 +31,26 @@ __BEGIN_DECLS /* Initializers. */ #define PTHREAD_MUTEX_INITIALIZER \ - {0, 0, 0, PTHREAD_MUTEX_TIMED_NP, {0, 0}} + {0, 0, 0, PTHREAD_MUTEX_TIMED_NP, LOCK_INITIALIZER} #ifdef __USE_GNU # define PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP \ - {0, 0, 0, PTHREAD_MUTEX_RECURSIVE_NP, {0, 0}} + {0, 0, 0, PTHREAD_MUTEX_RECURSIVE_NP, LOCK_INITIALIZER} # define PTHREAD_ERRORCHECK_MUTEX_INITIALIZER_NP \ - {0, 0, 0, PTHREAD_MUTEX_ERRORCHECK_NP, {0, 0}} + {0, 0, 0, PTHREAD_MUTEX_ERRORCHECK_NP, LOCK_INITIALIZER} # define PTHREAD_ADAPTIVE_MUTEX_INITIALIZER_NP \ - {0, 0, 0, PTHREAD_MUTEX_ADAPTIVE_NP, {0, 0}} + {0, 0, 0, PTHREAD_MUTEX_ADAPTIVE_NP, LOCK_INITIALIZER} #endif -#define PTHREAD_COND_INITIALIZER {{0, 0}, 0} +#define PTHREAD_COND_INITIALIZER {LOCK_INITIALIZER, 0} #ifdef __USE_UNIX98 # define PTHREAD_RWLOCK_INITIALIZER \ - { {0, 0}, 0, NULL, NULL, NULL, \ + { LOCK_INITIALIZER, 0, NULL, NULL, NULL, \ PTHREAD_RWLOCK_DEFAULT_NP, PTHREAD_PROCESS_PRIVATE } #endif #ifdef __USE_GNU # define PTHREAD_RWLOCK_WRITER_NONRECURSIVE_INITIALIZER_NP \ - { {0, 0}, 0, NULL, NULL, NULL, \ + { LOCK_INITIALIZER, 0, NULL, NULL, NULL, \ PTHREAD_RWLOCK_PREFER_WRITER_NONRECURSIVE_NP, PTHREAD_PROCESS_PRIVATE } #endif diff --git a/linuxthreads/sysdeps/unix/sysv/linux/hppa/bits/initspin.h b/linuxthreads/sysdeps/unix/sysv/linux/hppa/bits/initspin.h new file mode 100644 index 0000000..bb8d326 --- /dev/null +++ b/linuxthreads/sysdeps/unix/sysv/linux/hppa/bits/initspin.h @@ -0,0 +1,27 @@ +/* PA-RISC specific definitions for spinlock initializers. + Copyright (C) 2000 Free Software Foundation, Inc. + This file is part of the GNU C Library. + + The GNU C Library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public License as + published by the Free Software Foundation; either version 2 of the + License, or (at your option) any later version. + + The GNU C Library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public + License along with the GNU C Library; see the file COPYING.LIB. If not, + write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. */ + +/* Initial value of a spinlock. PA-RISC only implements atomic load + and clear so this must be non-zero. */ +#define LT_SPINLOCK_INIT 1 + +/* Macros for lock initializers, using the above definition. */ +#define LOCK_INITIALIZER { 0, LT_SPINLOCK_INIT } +#define ALT_LOCK_INITIALIZER { 0, LT_SPINLOCK_INIT } +#define ATOMIC_INITIALIZER { 0, LT_SPINLOCK_INIT } |