diff options
author | Jakub Jelinek <jakub@redhat.com> | 2007-07-31 17:46:17 +0000 |
---|---|---|
committer | Jakub Jelinek <jakub@redhat.com> | 2007-07-31 17:46:17 +0000 |
commit | 8833066b122427710a9e14a888ce6cfa862332d3 (patch) | |
tree | 29591019d695919417b3698618d6a342e97381d6 /nptl/sysdeps/unix/sysv/linux/s390/lowlevellock.h | |
parent | fedca46896bdb702cb988837a0c2c5447e72ba2b (diff) |
Updated to fedora-glibc-20070731T1624cvs/fedora-glibc-2_6_90-1
Diffstat (limited to 'nptl/sysdeps/unix/sysv/linux/s390/lowlevellock.h')
-rw-r--r-- | nptl/sysdeps/unix/sysv/linux/s390/lowlevellock.h | 74 |
1 files changed, 46 insertions, 28 deletions
diff --git a/nptl/sysdeps/unix/sysv/linux/s390/lowlevellock.h b/nptl/sysdeps/unix/sysv/linux/s390/lowlevellock.h index 38d9f2ac41..4758b63bd0 100644 --- a/nptl/sysdeps/unix/sysv/linux/s390/lowlevellock.h +++ b/nptl/sysdeps/unix/sysv/linux/s390/lowlevellock.h @@ -1,4 +1,4 @@ -/* Copyright (C) 2003, 2004, 2006 Free Software Foundation, Inc. +/* Copyright (C) 2003, 2004, 2006, 2007 Free Software Foundation, Inc. This file is part of the GNU C Library. Contributed by Martin Schwidefsky <schwidefsky@de.ibm.com>, 2003. @@ -35,31 +35,50 @@ #define FUTEX_LOCK_PI 6 #define FUTEX_UNLOCK_PI 7 #define FUTEX_TRYLOCK_PI 8 +#define FUTEX_PRIVATE_FLAG 128 + +/* Values for 'private' parameter of locking macros. Yes, the + definition seems to be backwards. But it is not. The bit will be + reversed before passing to the system call. */ +#define LLL_PRIVATE 0 +#define LLL_SHARED FUTEX_PRIVATE_FLAG + + +#if !defined NOT_IN_libc || defined IS_IN_rtld +/* In libc.so or ld.so all futexes are private. */ +# ifdef __ASSUME_PRIVATE_FUTEX +# define __lll_private_flag(fl, private) \ + ((fl) | FUTEX_PRIVATE_FLAG) +# else +# define __lll_private_flag(fl, private) \ + ((fl) | THREAD_GETMEM (THREAD_SELF, header.private_futex)) +# endif +#else +# ifdef __ASSUME_PRIVATE_FUTEX +# define __lll_private_flag(fl, private) \ + (((fl) | FUTEX_PRIVATE_FLAG) ^ (private)) +# else +# define __lll_private_flag(fl, private) \ + (__builtin_constant_p (private) \ + ? ((private) == 0 \ + ? ((fl) | THREAD_GETMEM (THREAD_SELF, header.private_futex)) \ + : (fl)) \ + : ((fl) | (((private) ^ FUTEX_PRIVATE_FLAG) \ + & THREAD_GETMEM (THREAD_SELF, header.private_futex)))) +# endif +#endif /* Initializer for compatibility lock. */ #define LLL_MUTEX_LOCK_INITIALIZER (0) -#define lll_futex_wait(futex, val) \ - ({ \ - register unsigned long int __r2 asm ("2") = (unsigned long int) (futex); \ - register unsigned long int __r3 asm ("3") = FUTEX_WAIT; \ - register unsigned long int __r4 asm ("4") = (unsigned long int) (val); \ - register unsigned long int __r5 asm ("5") = 0ul; \ - register unsigned long __result asm ("2"); \ - \ - __asm __volatile ("svc %b1" \ - : "=d" (__result) \ - : "i" (SYS_futex), "0" (__r2), "d" (__r3), \ - "d" (__r4), "d" (__r5) \ - : "cc", "memory" ); \ - __result; \ - }) +#define lll_futex_wait(futex, val, private) \ + lll_futex_timed_wait (futex, val, NULL, private) - -#define lll_futex_timed_wait(futex, val, timespec) \ +#define lll_futex_timed_wait(futex, val, timespec, private) \ ({ \ register unsigned long int __r2 asm ("2") = (unsigned long int) (futex); \ - register unsigned long int __r3 asm ("3") = FUTEX_WAIT; \ + register unsigned long int __r3 asm ("3") \ + = __lll_private_flag (FUTEX_WAIT, private); \ register unsigned long int __r4 asm ("4") = (unsigned long int) (val); \ register unsigned long int __r5 asm ("5") = (unsigned long int)(timespec);\ register unsigned long int __result asm ("2"); \ @@ -73,10 +92,11 @@ }) -#define lll_futex_wake(futex, nr) \ +#define lll_futex_wake(futex, nr, private) \ ({ \ register unsigned long int __r2 asm ("2") = (unsigned long int) (futex); \ - register unsigned long int __r3 asm ("3") = FUTEX_WAKE; \ + register unsigned long int __r3 asm ("3") \ + __lll_private_flag (FUTEX_WAKE, private); \ register unsigned long int __r4 asm ("4") = (unsigned long int) (nr); \ register unsigned long int __result asm ("2"); \ \ @@ -94,7 +114,7 @@ int *__futexp = &(futexv); \ \ atomic_or (__futexp, FUTEX_OWNER_DIED); \ - lll_futex_wake (__futexp, 1); \ + lll_futex_wake (__futexp, 1, LLL_SHARED); \ } \ while (0) @@ -271,7 +291,7 @@ __lll_mutex_unlock (int *futex) lll_compare_and_swap (futex, oldval, newval, "slr %2,%2"); if (oldval > 1) - lll_futex_wake (futex, 1); + lll_futex_wake (futex, 1, LLL_SHARED); } #define lll_mutex_unlock(futex) \ __lll_mutex_unlock(&(futex)) @@ -286,7 +306,7 @@ __lll_robust_mutex_unlock (int *futex, int mask) lll_compare_and_swap (futex, oldval, newval, "slr %2,%2"); if (oldval & mask) - lll_futex_wake (futex, 1); + lll_futex_wake (futex, 1, LLL_SHARED); } #define lll_robust_mutex_unlock(futex) \ __lll_robust_mutex_unlock(&(futex), FUTEX_WAITERS) @@ -297,7 +317,7 @@ __attribute__ ((always_inline)) __lll_mutex_unlock_force (int *futex) { *futex = 0; - lll_futex_wake (futex, 1); + lll_futex_wake (futex, 1, LLL_SHARED); } #define lll_mutex_unlock_force(futex) \ __lll_mutex_unlock_force(&(futex)) @@ -321,8 +341,6 @@ typedef int lll_lock_t; #define lll_unlock(futex) lll_mutex_unlock (futex) #define lll_islocked(futex) lll_mutex_islocked (futex) -extern int lll_unlock_wake_cb (int *__futex) attribute_hidden; - /* The states of a lock are: 1 - untaken 0 - taken by one user @@ -340,7 +358,7 @@ __lll_wait_tid (int *ptid) int tid; while ((tid = *ptid) != 0) - lll_futex_wait (ptid, tid); + lll_futex_wait (ptid, tid, LLL_SHARED); } #define lll_wait_tid(tid) __lll_wait_tid(&(tid)) |