diff options
Diffstat (limited to 'sysdeps/sparc')
-rw-r--r-- | sysdeps/sparc/nptl/pthread_barrier_init.c | 7 | ||||
-rw-r--r-- | sysdeps/sparc/nptl/pthread_barrier_wait.c | 6 | ||||
-rw-r--r-- | sysdeps/sparc/sparc32/pthread_barrier_wait.c | 6 | ||||
-rw-r--r-- | sysdeps/sparc/sparc32/sem_init.c | 29 | ||||
-rw-r--r-- | sysdeps/sparc/sparc32/sem_open.c | 2 | ||||
-rw-r--r-- | sysdeps/sparc/sparc32/sem_post.c | 26 | ||||
-rw-r--r-- | sysdeps/sparc/sparc32/sem_wait.c | 1 | ||||
-rw-r--r-- | sysdeps/sparc/sparc32/sem_waitcommon.c | 107 |
8 files changed, 29 insertions, 155 deletions
diff --git a/sysdeps/sparc/nptl/pthread_barrier_init.c b/sysdeps/sparc/nptl/pthread_barrier_init.c index aa21a63f2d..86ec7d0348 100644 --- a/sysdeps/sparc/nptl/pthread_barrier_init.c +++ b/sysdeps/sparc/nptl/pthread_barrier_init.c @@ -35,10 +35,9 @@ __pthread_barrier_init (barrier, attr, count) struct pthread_barrierattr *iattr = (struct pthread_barrierattr *) attr; if (iattr != NULL) { - if (iattr->pshared != PTHREAD_PROCESS_PRIVATE - && __builtin_expect (iattr->pshared != PTHREAD_PROCESS_SHARED, 0)) - /* Invalid attribute. */ - return EINVAL; + int err = futex_supports_pshared (iattr->pshared); + if (err != 0) + return err; } ibarrier = (union sparc_pthread_barrier *) barrier; diff --git a/sysdeps/sparc/nptl/pthread_barrier_wait.c b/sysdeps/sparc/nptl/pthread_barrier_wait.c index dd4c336dc2..9e9806a31a 100644 --- a/sysdeps/sparc/nptl/pthread_barrier_wait.c +++ b/sysdeps/sparc/nptl/pthread_barrier_wait.c @@ -21,6 +21,7 @@ #include <lowlevellock.h> #include <pthreadP.h> #include <sparc-nptl.h> +#include <futex-internal.h> /* Wait on barrier. */ int @@ -31,6 +32,7 @@ __pthread_barrier_wait (barrier) = (union sparc_pthread_barrier *) barrier; int result = 0; int private = ibarrier->s.pshared ? LLL_SHARED : LLL_PRIVATE; + int futex_private = ibarrier->s.pshared ? FUTEX_SHARED : FUTEX_PRIVATE; /* Make sure we are alone. */ lll_lock (ibarrier->b.lock, private); @@ -46,7 +48,7 @@ __pthread_barrier_wait (barrier) ++ibarrier->b.curr_event; /* Wake up everybody. */ - lll_futex_wake (&ibarrier->b.curr_event, INT_MAX, private); + futex_wake (&ibarrier->b.curr_event, INT_MAX, futex_private); /* This is the thread which finished the serialization. */ result = PTHREAD_BARRIER_SERIAL_THREAD; @@ -62,7 +64,7 @@ __pthread_barrier_wait (barrier) /* Wait for the event counter of the barrier to change. */ do - lll_futex_wait (&ibarrier->b.curr_event, event, private); + futex_wait_simple (&ibarrier->b.curr_event, event, futex_private); while (event == ibarrier->b.curr_event); } diff --git a/sysdeps/sparc/sparc32/pthread_barrier_wait.c b/sysdeps/sparc/sparc32/pthread_barrier_wait.c index 81d22b0653..5e1aa1159c 100644 --- a/sysdeps/sparc/sparc32/pthread_barrier_wait.c +++ b/sysdeps/sparc/sparc32/pthread_barrier_wait.c @@ -21,6 +21,7 @@ #include <lowlevellock.h> #include <pthreadP.h> #include <sparc-nptl.h> +#include <futex-internal.h> /* Wait on barrier. */ int @@ -31,6 +32,7 @@ __pthread_barrier_wait (barrier) = (union sparc_pthread_barrier *) barrier; int result = 0; int private = ibarrier->s.pshared ? LLL_SHARED : LLL_PRIVATE; + int futex_private = ibarrier->s.pshared ? FUTEX_SHARED : FUTEX_PRIVATE; /* Make sure we are alone. */ lll_lock (ibarrier->b.lock, private); @@ -46,7 +48,7 @@ __pthread_barrier_wait (barrier) ++ibarrier->b.curr_event; /* Wake up everybody. */ - lll_futex_wake (&ibarrier->b.curr_event, INT_MAX, private); + futex_wake (&ibarrier->b.curr_event, INT_MAX, futex_private); /* This is the thread which finished the serialization. */ result = PTHREAD_BARRIER_SERIAL_THREAD; @@ -62,7 +64,7 @@ __pthread_barrier_wait (barrier) /* Wait for the event counter of the barrier to change. */ do - lll_futex_wait (&ibarrier->b.curr_event, event, private); + futex_wait_simple (&ibarrier->b.curr_event, event, futex_private); while (event == ibarrier->b.curr_event); } diff --git a/sysdeps/sparc/sparc32/sem_init.c b/sysdeps/sparc/sparc32/sem_init.c index 7c46cee900..1c7c455617 100644 --- a/sysdeps/sparc/sparc32/sem_init.c +++ b/sysdeps/sparc/sparc32/sem_init.c @@ -20,23 +20,7 @@ #include <semaphore.h> #include <shlib-compat.h> #include "semaphoreP.h" -#include <kernel-features.h> - -/* Returns FUTEX_PRIVATE if pshared is zero and private futexes are supported; - returns FUTEX_SHARED otherwise. - TODO Remove when cleaning up the futex API throughout glibc. */ -static __always_inline int -futex_private_if_supported (int pshared) -{ - if (pshared != 0) - return LLL_SHARED; -#ifdef __ASSUME_PRIVATE_FUTEX - return LLL_PRIVATE; -#else - return THREAD_GETMEM (THREAD_SELF, header.private_futex) - ^ FUTEX_PRIVATE_FLAG; -#endif -} +#include <futex-internal.h> int @@ -49,6 +33,14 @@ __new_sem_init (sem_t *sem, int pshared, unsigned int value) return -1; } + pshared = pshared != 0 ? PTHREAD_PROCESS_SHARED : PTHREAD_PROCESS_PRIVATE; + int err = futex_supports_pshared (pshared); + if (err != 0) + { + __set_errno (err); + return -1; + } + /* Map to the internal type. */ struct new_sem *isem = (struct new_sem *) sem; @@ -57,7 +49,8 @@ __new_sem_init (sem_t *sem, int pshared, unsigned int value) isem->pad = 0; isem->nwaiters = 0; - isem->private = futex_private_if_supported (pshared); + isem->private = (pshared == PTHREAD_PROCESS_PRIVATE + ? FUTEX_PRIVATE : FUTEX_SHARED); return 0; } diff --git a/sysdeps/sparc/sparc32/sem_open.c b/sysdeps/sparc/sparc32/sem_open.c index 2698d195ba..16cb9ad591 100644 --- a/sysdeps/sparc/sparc32/sem_open.c +++ b/sysdeps/sparc/sparc32/sem_open.c @@ -199,7 +199,7 @@ sem_open (const char *name, int oflag, ...) sem.newsem.nwaiters = 0; /* This always is a shared semaphore. */ - sem.newsem.private = LLL_SHARED; + sem.newsem.private = FUTEX_SHARED; /* Initialize the remaining bytes as well. */ memset ((char *) &sem.initsem + sizeof (struct new_sem), '\0', diff --git a/sysdeps/sparc/sparc32/sem_post.c b/sysdeps/sparc/sparc32/sem_post.c index c9f85a06f5..fd1a2fe910 100644 --- a/sysdeps/sparc/sparc32/sem_post.c +++ b/sysdeps/sparc/sparc32/sem_post.c @@ -23,34 +23,10 @@ #include <lowlevellock.h> #include <internaltypes.h> #include <semaphore.h> +#include <futex-internal.h> #include <shlib-compat.h> -/* Wrapper for lll_futex_wake, with error checking. - TODO Remove when cleaning up the futex API throughout glibc. */ -static __always_inline void -futex_wake (unsigned int* futex, int processes_to_wake, int private) -{ - int res = lll_futex_wake (futex, processes_to_wake, private); - /* No error. Ignore the number of woken processes. */ - if (res >= 0) - return; - switch (res) - { - case -EFAULT: /* Could have happened due to memory reuse. */ - case -EINVAL: /* Could be either due to incorrect alignment (a bug in - glibc or in the application) or due to memory being - reused for a PI futex. We cannot distinguish between the - two causes, and one of them is correct use, so we do not - act in this case. */ - return; - case -ENOSYS: /* Must have been caused by a glibc bug. */ - /* No other errors are documented at this time. */ - default: - abort (); - } -} - /* See sem_wait for an explanation of the algorithm. */ int diff --git a/sysdeps/sparc/sparc32/sem_wait.c b/sysdeps/sparc/sparc32/sem_wait.c index c1fd10c9d0..fce7ed43ee 100644 --- a/sysdeps/sparc/sparc32/sem_wait.c +++ b/sysdeps/sparc/sparc32/sem_wait.c @@ -17,6 +17,7 @@ License along with the GNU C Library; if not, see <http://www.gnu.org/licenses/>. */ +#include <lowlevellock.h> /* lll_futex* used by the old code. */ #include "sem_waitcommon.c" int diff --git a/sysdeps/sparc/sparc32/sem_waitcommon.c b/sysdeps/sparc/sparc32/sem_waitcommon.c index 9c1c6a5af7..9e43d45431 100644 --- a/sysdeps/sparc/sparc32/sem_waitcommon.c +++ b/sysdeps/sparc/sparc32/sem_waitcommon.c @@ -19,7 +19,7 @@ #include <errno.h> #include <sysdep.h> -#include <lowlevellock.h> +#include <futex-internal.h> #include <internaltypes.h> #include <semaphore.h> #include <sys/time.h> @@ -28,104 +28,6 @@ #include <shlib-compat.h> #include <atomic.h> -/* Wrapper for lll_futex_wait with absolute timeout and error checking. - TODO Remove when cleaning up the futex API throughout glibc. */ -static __always_inline int -futex_abstimed_wait (unsigned int* futex, unsigned int expected, - const struct timespec* abstime, int private, bool cancel) -{ - int err, oldtype; - if (abstime == NULL) - { - if (cancel) - oldtype = __pthread_enable_asynccancel (); - err = lll_futex_wait (futex, expected, private); - if (cancel) - __pthread_disable_asynccancel (oldtype); - } - else - { - struct timeval tv; - struct timespec rt; - int sec, nsec; - - /* Get the current time. */ - __gettimeofday (&tv, NULL); - - /* Compute relative timeout. */ - sec = abstime->tv_sec - tv.tv_sec; - nsec = abstime->tv_nsec - tv.tv_usec * 1000; - if (nsec < 0) - { - nsec += 1000000000; - --sec; - } - - /* Already timed out? */ - if (sec < 0) - return ETIMEDOUT; - - /* Do wait. */ - rt.tv_sec = sec; - rt.tv_nsec = nsec; - if (cancel) - oldtype = __pthread_enable_asynccancel (); - err = lll_futex_timed_wait (futex, expected, &rt, private); - if (cancel) - __pthread_disable_asynccancel (oldtype); - } - switch (err) - { - case 0: - case -EAGAIN: - case -EINTR: - case -ETIMEDOUT: - return -err; - - case -EFAULT: /* Must have been caused by a glibc or application bug. */ - case -EINVAL: /* Either due to wrong alignment or due to the timeout not - being normalized. Must have been caused by a glibc or - application bug. */ - case -ENOSYS: /* Must have been caused by a glibc bug. */ - /* No other errors are documented at this time. */ - default: - abort (); - } -} - -/* Wrapper for lll_futex_wake, with error checking. - TODO Remove when cleaning up the futex API throughout glibc. */ -static __always_inline void -futex_wake (unsigned int* futex, int processes_to_wake, int private) -{ - int res = lll_futex_wake (futex, processes_to_wake, private); - /* No error. Ignore the number of woken processes. */ - if (res >= 0) - return; - switch (res) - { - case -EFAULT: /* Could have happened due to memory reuse. */ - case -EINVAL: /* Could be either due to incorrect alignment (a bug in - glibc or in the application) or due to memory being - reused for a PI futex. We cannot distinguish between the - two causes, and one of them is correct use, so we do not - act in this case. */ - return; - case -ENOSYS: /* Must have been caused by a glibc bug. */ - /* No other errors are documented at this time. */ - default: - abort (); - } -} - - -/* Set this to true if you assume that, in contrast to current Linux futex - documentation, lll_futex_wake can return -EINTR only if interrupted by a - signal, not spuriously due to some other reason. - TODO Discuss EINTR conditions with the Linux kernel community. For - now, we set this to true to not change behavior of semaphores compared - to previous glibc builds. */ -static const int sem_assume_only_signals_cause_futex_EINTR = 1; static void __sem_wait_32_finish (struct new_sem *sem); @@ -149,8 +51,8 @@ do_futex_wait (struct new_sem *sem, const struct timespec *abstime) { int err; - err = futex_abstimed_wait (&sem->value, SEM_NWAITERS_MASK, abstime, - sem->private, true); + err = futex_abstimed_wait_cancelable (&sem->value, SEM_NWAITERS_MASK, + abstime, sem->private); return err; } @@ -202,8 +104,7 @@ __new_sem_wait_slow (struct new_sem *sem, const struct timespec *abstime) __sparc32_atomic_do_unlock24(&sem->pad); err = do_futex_wait(sem, abstime); - if (err == ETIMEDOUT || - (err == EINTR && sem_assume_only_signals_cause_futex_EINTR)) + if (err == ETIMEDOUT || err == EINTR) { __set_errno (err); err = -1; |