mirror of
https://sourceware.org/git/glibc.git
synced 2024-11-10 07:10:06 +00:00
* sysdeps/sparc/fpu/fraiseexcpt.c (__feraiseexcept): Fix raising
FE_UNDERFLOW on Niagara CPUs. * sysdeps/sparc/fpu/feholdexcpt.c (feholdexcept): Clear all exceptions. * sysdeps/unix/sysv/linux/sparc/internaltypes.h (sparc_new_sem, sparc_old_sem): New structs. * sysdeps/unix/sysv/linux/sparc/sparc32/sem_wait.c (__sem_wait_cleanup): New function. (__new_sem_wait): Use sparc_new_sem structure. Bump and afterwards decrease nwaiters. Register __sem_wait_cleanup as cleanup handler. Pass isem->private ^ FUTEX_PRIVATE_FLAG as last argument to lll_futex_wait. (__old_sem_wait): New function. * sysdeps/unix/sysv/linux/sparc/sparc32/sparcv9/sem_wait.c: Include nptl/sysdeps/unix/sysv/linux/sparc version. * sysdeps/unix/sysv/linux/sparc/sparc32/sparcv9/sem_timedwait.c: Likewise. * sysdeps/unix/sysv/linux/sparc/sparc32/sparcv9/sem_post.c: Likewise. * sysdeps/unix/sysv/linux/sparc/sparc32/sem_trywait.c (__new_sem_trywait): Use sparc_old_sem structure. * sysdeps/unix/sysv/linux/sparc/sparc32/sem_timedwait.c (sem_timedwait): Use sparc_new_sem structure. Bump and afterwards decrease nwaiters. Register __sem_wait_cleanup as cleanup handler. Pass isem->private ^ FUTEX_PRIVATE_FLAG as last argument to lll_futex_timed_wait. * sysdeps/unix/sysv/linux/sparc/sparc32/sem_post.c (__new_sem_post): Use sparc_new_sem structure. Only wake if nwaiters > 0. Pass isem->private ^ FUTEX_PRIVATE_FLAG as last argument to lll_futex_wake. (__old_sem_post): New function. * sysdeps/unix/sysv/linux/sparc/sem_wait.c: New file. * sysdeps/unix/sysv/linux/sparc/sem_init.c: New file. * sysdeps/unix/sysv/linux/sparc/sem_timedwait.c: New file. * sysdeps/unix/sysv/linux/sparc/sem_post.c: New file. * sysdeps/unix/sysv/linux/sparc/sparc32/sparcv9/sem_init.c: Remove. * sysdeps/unix/sysv/linux/sparc/sparc32/sem_init.c: Remove. 2007-08-15 Jakub Jelinek <jakub@redhat.com> * sysdeps/sparc/fpu/fraiseexcpt.c (__feraiseexcept): Fix raising FE_UNDERFLOW on Niagara CPUs. * sysdeps/sparc/fpu/feholdexcpt.c (feholdexcept): Clear all exceptions.
This commit is contained in:
parent
d13f4a4386
commit
e4720b0e59
@ -1,3 +1,11 @@
|
||||
2007-08-15 Jakub Jelinek <jakub@redhat.com>
|
||||
|
||||
* sysdeps/sparc/fpu/fraiseexcpt.c (__feraiseexcept): Fix raising
|
||||
FE_UNDERFLOW on Niagara CPUs.
|
||||
|
||||
* sysdeps/sparc/fpu/feholdexcpt.c (feholdexcept): Clear all
|
||||
exceptions.
|
||||
|
||||
2007-08-14 Jakub Jelinek <jakub@redhat.com>
|
||||
|
||||
* sysdeps/sparc/sparc32/dl-machine.h (elf_machine_runtime_setup): No
|
||||
|
@ -1,3 +1,38 @@
|
||||
2007-08-15 Jakub Jelinek <jakub@redhat.com>
|
||||
|
||||
* sysdeps/unix/sysv/linux/sparc/internaltypes.h (sparc_new_sem,
|
||||
sparc_old_sem): New structs.
|
||||
* sysdeps/unix/sysv/linux/sparc/sparc32/sem_wait.c
|
||||
(__sem_wait_cleanup): New function.
|
||||
(__new_sem_wait): Use sparc_new_sem structure. Bump and afterwards
|
||||
decrease nwaiters. Register __sem_wait_cleanup as cleanup handler.
|
||||
Pass isem->private ^ FUTEX_PRIVATE_FLAG as last argument to
|
||||
lll_futex_wait.
|
||||
(__old_sem_wait): New function.
|
||||
* sysdeps/unix/sysv/linux/sparc/sparc32/sparcv9/sem_wait.c: Include
|
||||
nptl/sysdeps/unix/sysv/linux/sparc version.
|
||||
* sysdeps/unix/sysv/linux/sparc/sparc32/sparcv9/sem_timedwait.c:
|
||||
Likewise.
|
||||
* sysdeps/unix/sysv/linux/sparc/sparc32/sparcv9/sem_post.c: Likewise.
|
||||
* sysdeps/unix/sysv/linux/sparc/sparc32/sem_trywait.c
|
||||
(__new_sem_trywait): Use sparc_old_sem structure.
|
||||
* sysdeps/unix/sysv/linux/sparc/sparc32/sem_timedwait.c
|
||||
(sem_timedwait): Use sparc_new_sem structure. Bump and afterwards
|
||||
decrease nwaiters. Register __sem_wait_cleanup as cleanup handler.
|
||||
Pass isem->private ^ FUTEX_PRIVATE_FLAG as last argument to
|
||||
lll_futex_timed_wait.
|
||||
* sysdeps/unix/sysv/linux/sparc/sparc32/sem_post.c (__new_sem_post):
|
||||
Use sparc_new_sem structure. Only wake if nwaiters > 0. Pass
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG as last argument to
|
||||
lll_futex_wake.
|
||||
(__old_sem_post): New function.
|
||||
* sysdeps/unix/sysv/linux/sparc/sem_wait.c: New file.
|
||||
* sysdeps/unix/sysv/linux/sparc/sem_init.c: New file.
|
||||
* sysdeps/unix/sysv/linux/sparc/sem_timedwait.c: New file.
|
||||
* sysdeps/unix/sysv/linux/sparc/sem_post.c: New file.
|
||||
* sysdeps/unix/sysv/linux/sparc/sparc32/sparcv9/sem_init.c: Remove.
|
||||
* sysdeps/unix/sysv/linux/sparc/sparc32/sem_init.c: Remove.
|
||||
|
||||
2007-08-14 Kaz Kojima <kkojima@rr.iij4u.or.jp>
|
||||
|
||||
* sysdeps/unix/sysv/linux/sh/pthread_cond_broadcast.S
|
||||
|
@ -15,4 +15,20 @@ union sparc_pthread_barrier
|
||||
} s;
|
||||
};
|
||||
|
||||
struct sparc_new_sem
|
||||
{
|
||||
unsigned int value;
|
||||
unsigned char lock;
|
||||
unsigned char private;
|
||||
unsigned char pad[2];
|
||||
unsigned long int nwaiters;
|
||||
};
|
||||
|
||||
struct sparc_old_sem
|
||||
{
|
||||
unsigned int value;
|
||||
unsigned char lock;
|
||||
unsigned char private;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* Copyright (C) 2002, 2006 Free Software Foundation, Inc.
|
||||
/* Copyright (C) 2002, 2007 Free Software Foundation, Inc.
|
||||
This file is part of the GNU C Library.
|
||||
Contributed by Ulrich Drepper <drepper@redhat.com>, 2002.
|
||||
|
||||
@ -18,16 +18,12 @@
|
||||
02111-1307 USA. */
|
||||
|
||||
#include <errno.h>
|
||||
#include <string.h>
|
||||
#include <semaphore.h>
|
||||
#include <lowlevellock.h>
|
||||
#include <shlib-compat.h>
|
||||
#include "semaphoreP.h"
|
||||
|
||||
struct sparc_sem
|
||||
{
|
||||
struct sem s;
|
||||
unsigned char lock;
|
||||
};
|
||||
#include <kernel-features.h>
|
||||
|
||||
|
||||
int
|
||||
@ -44,20 +40,54 @@ __new_sem_init (sem, pshared, value)
|
||||
}
|
||||
|
||||
/* Map to the internal type. */
|
||||
struct sparc_sem *isem = (struct sparc_sem *) sem;
|
||||
struct sparc_new_sem *isem = (struct sparc_new_sem *) sem;
|
||||
|
||||
/* Use the value the user provided. */
|
||||
isem->s.count = value;
|
||||
|
||||
isem->lock = 0;
|
||||
|
||||
/* We can completely ignore the PSHARED parameter since inter-process
|
||||
use needs no special preparation. */
|
||||
/* Use the values the user provided. */
|
||||
memset (isem, '\0', sizeof (*isem));
|
||||
isem->value = value;
|
||||
#ifdef __ASSUME_PRIVATE_FUTEX
|
||||
isem->private = pshared ? 0 : FUTEX_PRIVATE_FLAG;
|
||||
#else
|
||||
isem->private = pshared ? 0 : THREAD_GETMEM (THREAD_SELF,
|
||||
header.private_futex);
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
versioned_symbol (libpthread, __new_sem_init, sem_init, GLIBC_2_1);
|
||||
|
||||
|
||||
|
||||
#if SHLIB_COMPAT(libpthread, GLIBC_2_0, GLIBC_2_1)
|
||||
strong_alias (__new_sem_init, __old_sem_init)
|
||||
int
|
||||
attribute_compat_text_section
|
||||
__old_sem_init (sem, pshared, value)
|
||||
sem_t *sem;
|
||||
int pshared;
|
||||
unsigned int value;
|
||||
{
|
||||
/* Parameter sanity check. */
|
||||
if (__builtin_expect (value > SEM_VALUE_MAX, 0))
|
||||
{
|
||||
__set_errno (EINVAL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Map to the internal type. */
|
||||
struct sparc_old_sem *isem = (struct sparc_old_sem *) sem;
|
||||
|
||||
/* Use the value the user provided. */
|
||||
memset (isem, '\0', sizeof (*isem));
|
||||
isem->value = value;
|
||||
|
||||
#ifdef __ASSUME_PRIVATE_FUTEX
|
||||
isem->private = pshared ? 0 : FUTEX_PRIVATE_FLAG;
|
||||
#else
|
||||
isem->private = pshared ? 0 : THREAD_GETMEM (THREAD_SELF,
|
||||
header.private_futex);
|
||||
#endif
|
||||
|
||||
return 0;
|
||||
}
|
||||
compat_symbol (libpthread, __old_sem_init, sem_init, GLIBC_2_0);
|
||||
#endif
|
69
nptl/sysdeps/unix/sysv/linux/sparc/sem_post.c
Normal file
69
nptl/sysdeps/unix/sysv/linux/sparc/sem_post.c
Normal file
@ -0,0 +1,69 @@
|
||||
/* sem_post -- post to a POSIX semaphore. SPARC version.
|
||||
Copyright (C) 2003, 2004, 2007 Free Software Foundation, Inc.
|
||||
This file is part of the GNU C Library.
|
||||
Contributed by Jakub Jelinek <jakub@redhat.com>, 2003.
|
||||
|
||||
The GNU C Library is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU Lesser General Public
|
||||
License as published by the Free Software Foundation; either
|
||||
version 2.1 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
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with the GNU C Library; if not, write to the Free
|
||||
Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
|
||||
02111-1307 USA. */
|
||||
|
||||
#include <errno.h>
|
||||
#include <sysdep.h>
|
||||
#include <lowlevellock.h>
|
||||
#include <internaltypes.h>
|
||||
#include <semaphore.h>
|
||||
|
||||
#include <shlib-compat.h>
|
||||
|
||||
int
|
||||
__new_sem_post (sem_t *sem)
|
||||
{
|
||||
struct sparc_new_sem *isem = (struct sparc_new_sem *) sem;
|
||||
|
||||
int nr = atomic_increment_val (&isem->value);
|
||||
atomic_full_barrier ();
|
||||
if (isem->nwaiters > 0)
|
||||
{
|
||||
int err = lll_futex_wake (&isem->value, 1,
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG);
|
||||
if (__builtin_expect (err, 0) < 0)
|
||||
{
|
||||
__set_errno (-err);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
versioned_symbol (libpthread, __new_sem_post, sem_post, GLIBC_2_1);
|
||||
|
||||
|
||||
#if SHLIB_COMPAT (libpthread, GLIBC_2_0, GLIBC_2_1)
|
||||
int
|
||||
attribute_compat_text_section
|
||||
__old_sem_post (sem_t *sem)
|
||||
{
|
||||
struct sparc_old_sem *isem = (struct sparc_old_sem *) sem;
|
||||
|
||||
int nr = atomic_increment_val (&isem->value);
|
||||
int err = lll_futex_wake (&isem->value, 1,
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG);
|
||||
if (__builtin_expect (err, 0) < 0)
|
||||
{
|
||||
__set_errno (-err);
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
compat_symbol (libpthread, __old_sem_post, sem_post, GLIBC_2_0);
|
||||
#endif
|
112
nptl/sysdeps/unix/sysv/linux/sparc/sem_timedwait.c
Normal file
112
nptl/sysdeps/unix/sysv/linux/sparc/sem_timedwait.c
Normal file
@ -0,0 +1,112 @@
|
||||
/* sem_timedwait -- wait on a semaphore. Generic futex-using version.
|
||||
Copyright (C) 2003, 2007 Free Software Foundation, Inc.
|
||||
This file is part of the GNU C Library.
|
||||
Contributed by Paul Mackerras <paulus@au.ibm.com>, 2003.
|
||||
|
||||
The GNU C Library is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU Lesser General Public
|
||||
License as published by the Free Software Foundation; either
|
||||
version 2.1 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
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with the GNU C Library; if not, write to the Free
|
||||
Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
|
||||
02111-1307 USA. */
|
||||
|
||||
#include <errno.h>
|
||||
#include <sysdep.h>
|
||||
#include <lowlevellock.h>
|
||||
#include <internaltypes.h>
|
||||
#include <semaphore.h>
|
||||
|
||||
#include <pthreadP.h>
|
||||
#include <shlib-compat.h>
|
||||
|
||||
|
||||
extern void __sem_wait_cleanup (void *arg) attribute_hidden;
|
||||
|
||||
|
||||
int
|
||||
sem_timedwait (sem_t *sem, const struct timespec *abstime)
|
||||
{
|
||||
struct sparc_new_sem *isem = (struct sparc_new_sem *) sem;
|
||||
int err;
|
||||
|
||||
if (atomic_decrement_if_positive (&isem->value) > 0)
|
||||
return 0;
|
||||
|
||||
if (abstime->tv_nsec < 0 || abstime->tv_nsec >= 1000000000)
|
||||
{
|
||||
__set_errno (EINVAL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
atomic_increment (&isem->nwaiters);
|
||||
|
||||
pthread_cleanup_push (__sem_wait_cleanup, isem);
|
||||
|
||||
while (1)
|
||||
{
|
||||
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? */
|
||||
err = -ETIMEDOUT;
|
||||
if (sec < 0)
|
||||
{
|
||||
__set_errno (ETIMEDOUT);
|
||||
err = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Do wait. */
|
||||
rt.tv_sec = sec;
|
||||
rt.tv_nsec = nsec;
|
||||
|
||||
/* Enable asynchronous cancellation. Required by the standard. */
|
||||
int oldtype = __pthread_enable_asynccancel ();
|
||||
|
||||
err = lll_futex_timed_wait (&isem->value, 0, &rt,
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG);
|
||||
|
||||
/* Disable asynchronous cancellation. */
|
||||
__pthread_disable_asynccancel (oldtype);
|
||||
|
||||
if (err != 0 && err != -EWOULDBLOCK)
|
||||
{
|
||||
__set_errno (-err);
|
||||
err = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
if (atomic_decrement_if_positive (&isem->value) > 0)
|
||||
{
|
||||
err = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
pthread_cleanup_pop (0);
|
||||
|
||||
atomic_decrement (&isem->nwaiters);
|
||||
|
||||
return err;
|
||||
}
|
117
nptl/sysdeps/unix/sysv/linux/sparc/sem_wait.c
Normal file
117
nptl/sysdeps/unix/sysv/linux/sparc/sem_wait.c
Normal file
@ -0,0 +1,117 @@
|
||||
/* sem_wait -- wait on a semaphore. Generic futex-using version.
|
||||
Copyright (C) 2003, 2007 Free Software Foundation, Inc.
|
||||
This file is part of the GNU C Library.
|
||||
Contributed by Paul Mackerras <paulus@au.ibm.com>, 2003.
|
||||
|
||||
The GNU C Library is free software; you can redistribute it and/or
|
||||
modify it under the terms of the GNU Lesser General Public
|
||||
License as published by the Free Software Foundation; either
|
||||
version 2.1 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
|
||||
Lesser General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU Lesser General Public
|
||||
License along with the GNU C Library; if not, write to the Free
|
||||
Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
|
||||
02111-1307 USA. */
|
||||
|
||||
#include <errno.h>
|
||||
#include <sysdep.h>
|
||||
#include <lowlevellock.h>
|
||||
#include <internaltypes.h>
|
||||
#include <semaphore.h>
|
||||
|
||||
#include <pthreadP.h>
|
||||
#include <shlib-compat.h>
|
||||
|
||||
|
||||
void
|
||||
attribute_hidden
|
||||
__sem_wait_cleanup (void *arg)
|
||||
{
|
||||
struct sparc_new_sem *isem = (struct sparc_new_sem *) arg;
|
||||
|
||||
atomic_decrement (&isem->nwaiters);
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
__new_sem_wait (sem_t *sem)
|
||||
{
|
||||
struct sparc_new_sem *isem = (struct sparc_new_sem *) sem;
|
||||
int err;
|
||||
|
||||
if (atomic_decrement_if_positive (&isem->value) > 0)
|
||||
return 0;
|
||||
|
||||
atomic_increment (&isem->nwaiters);
|
||||
|
||||
pthread_cleanup_push (__sem_wait_cleanup, isem);
|
||||
|
||||
while (1)
|
||||
{
|
||||
/* Enable asynchronous cancellation. Required by the standard. */
|
||||
int oldtype = __pthread_enable_asynccancel ();
|
||||
|
||||
err = lll_futex_wait (&isem->value, 0,
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG);
|
||||
|
||||
/* Disable asynchronous cancellation. */
|
||||
__pthread_disable_asynccancel (oldtype);
|
||||
|
||||
if (err != 0 && err != -EWOULDBLOCK)
|
||||
{
|
||||
__set_errno (-err);
|
||||
err = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
if (atomic_decrement_if_positive (&isem->value) > 0)
|
||||
{
|
||||
err = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
pthread_cleanup_pop (0);
|
||||
|
||||
atomic_decrement (&isem->nwaiters);
|
||||
|
||||
return err;
|
||||
}
|
||||
versioned_symbol (libpthread, __new_sem_wait, sem_wait, GLIBC_2_1);
|
||||
|
||||
|
||||
#if SHLIB_COMPAT (libpthread, GLIBC_2_0, GLIBC_2_1)
|
||||
int
|
||||
attribute_compat_text_section
|
||||
__old_sem_wait (sem_t *sem)
|
||||
{
|
||||
struct sparc_old_sem *isem = (struct sparc_old_sem *) sem;
|
||||
int err;
|
||||
|
||||
do
|
||||
{
|
||||
if (atomic_decrement_if_positive (&isem->value) > 0)
|
||||
return 0;
|
||||
|
||||
/* Enable asynchronous cancellation. Required by the standard. */
|
||||
int oldtype = __pthread_enable_asynccancel ();
|
||||
|
||||
err = lll_futex_wait (&isem->value, 0,
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG);
|
||||
|
||||
/* Disable asynchronous cancellation. */
|
||||
__pthread_disable_asynccancel (oldtype);
|
||||
}
|
||||
while (err == 0 || err == -EWOULDBLOCK);
|
||||
|
||||
__set_errno (-err);
|
||||
return -1;
|
||||
}
|
||||
|
||||
compat_symbol (libpthread, __old_sem_wait, sem_wait, GLIBC_2_0);
|
||||
#endif
|
@ -29,19 +29,51 @@
|
||||
int
|
||||
__new_sem_post (sem_t *sem)
|
||||
{
|
||||
int *futex = (int *) sem, nr;
|
||||
struct sparc_new_sem *isem = (struct sparc_new_sem *) sem;
|
||||
int nr;
|
||||
|
||||
if (__atomic_is_v9)
|
||||
nr = atomic_increment_val (futex);
|
||||
nr = atomic_increment_val (&isem->value);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (futex + 1);
|
||||
nr = ++*futex;
|
||||
__sparc32_atomic_do_unlock24 (futex + 1);
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
nr = ++(isem->value);
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
int err = lll_futex_wake (futex, nr,
|
||||
// XYZ check mutex flag
|
||||
LLL_SHARED);
|
||||
atomic_full_barrier ();
|
||||
if (isem->nwaiters > 0)
|
||||
{
|
||||
int err = lll_futex_wake (&isem->value, 1,
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG);
|
||||
if (__builtin_expect (err, 0) < 0)
|
||||
{
|
||||
__set_errno (-err);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
versioned_symbol (libpthread, __new_sem_post, sem_post, GLIBC_2_1);
|
||||
|
||||
|
||||
#if SHLIB_COMPAT (libpthread, GLIBC_2_0, GLIBC_2_1)
|
||||
int
|
||||
attribute_compat_text_section
|
||||
__old_sem_post (sem_t *sem)
|
||||
{
|
||||
struct sparc_old_sem *isem = (struct sparc_old_sem *) sem;
|
||||
int nr;
|
||||
|
||||
if (__atomic_is_v9)
|
||||
nr = atomic_increment_val (&isem->value);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
nr = ++(isem->value);
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
int err = lll_futex_wake (&isem->value, 1,
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG);
|
||||
if (__builtin_expect (err, 0) < 0)
|
||||
{
|
||||
__set_errno (-err);
|
||||
@ -49,8 +81,5 @@ __new_sem_post (sem_t *sem)
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
versioned_symbol (libpthread, __new_sem_post, sem_post, GLIBC_2_1);
|
||||
#if SHLIB_COMPAT (libpthread, GLIBC_2_0, GLIBC_2_1)
|
||||
strong_alias (__new_sem_post, __old_sem_post)
|
||||
compat_symbol (libpthread, __old_sem_post, sem_post, GLIBC_2_0);
|
||||
#endif
|
||||
|
@ -1,5 +1,5 @@
|
||||
/* sem_timedwait -- wait on a semaphore. SPARC version.
|
||||
Copyright (C) 2003, 2006 Free Software Foundation, Inc.
|
||||
Copyright (C) 2003, 2006, 2007 Free Software Foundation, Inc.
|
||||
This file is part of the GNU C Library.
|
||||
Contributed by Paul Mackerras <paulus@au.ibm.com>, 2003.
|
||||
|
||||
@ -28,37 +28,48 @@
|
||||
#include <shlib-compat.h>
|
||||
|
||||
|
||||
extern void __sem_wait_cleanup (void *arg) attribute_hidden;
|
||||
|
||||
|
||||
int
|
||||
sem_timedwait (sem_t *sem, const struct timespec *abstime)
|
||||
{
|
||||
/* First check for cancellation. */
|
||||
CANCELLATION_P (THREAD_SELF);
|
||||
|
||||
int *futex = (int *) sem;
|
||||
int val;
|
||||
struct sparc_new_sem *isem = (struct sparc_new_sem *) sem;
|
||||
int err;
|
||||
int val;
|
||||
|
||||
if (*futex > 0)
|
||||
if (__atomic_is_v9)
|
||||
val = atomic_decrement_if_positive (&isem->value);
|
||||
else
|
||||
{
|
||||
if (__atomic_is_v9)
|
||||
val = atomic_decrement_if_positive (futex);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (futex + 1);
|
||||
val = *futex;
|
||||
if (val > 0)
|
||||
*futex = val - 1;
|
||||
__sparc32_atomic_do_unlock24 (futex + 1);
|
||||
}
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
val = isem->value;
|
||||
if (val > 0)
|
||||
return 0;
|
||||
isem->value = val - 1;
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
|
||||
err = -EINVAL;
|
||||
if (abstime->tv_nsec < 0 || abstime->tv_nsec >= 1000000000)
|
||||
goto error_return;
|
||||
if (val > 0)
|
||||
return 0;
|
||||
|
||||
do
|
||||
if (abstime->tv_nsec < 0 || abstime->tv_nsec >= 1000000000)
|
||||
{
|
||||
__set_errno (EINVAL);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (__atomic_is_v9)
|
||||
atomic_increment (&isem->nwaiters);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
isem->nwaiters++;
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
|
||||
pthread_cleanup_push (__sem_wait_cleanup, isem);
|
||||
|
||||
while (1)
|
||||
{
|
||||
struct timeval tv;
|
||||
struct timespec rt;
|
||||
@ -79,7 +90,11 @@ sem_timedwait (sem_t *sem, const struct timespec *abstime)
|
||||
/* Already timed out? */
|
||||
err = -ETIMEDOUT;
|
||||
if (sec < 0)
|
||||
goto error_return;
|
||||
{
|
||||
__set_errno (ETIMEDOUT);
|
||||
err = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Do wait. */
|
||||
rt.tv_sec = sec;
|
||||
@ -88,30 +103,47 @@ sem_timedwait (sem_t *sem, const struct timespec *abstime)
|
||||
/* Enable asynchronous cancellation. Required by the standard. */
|
||||
int oldtype = __pthread_enable_asynccancel ();
|
||||
|
||||
err = lll_futex_timed_wait (futex, 0, &rt);
|
||||
err = lll_futex_timed_wait (&isem->value, 0, &rt,
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG);
|
||||
|
||||
/* Disable asynchronous cancellation. */
|
||||
__pthread_disable_asynccancel (oldtype);
|
||||
|
||||
if (err != 0 && err != -EWOULDBLOCK)
|
||||
goto error_return;
|
||||
{
|
||||
__set_errno (-err);
|
||||
err = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
if (__atomic_is_v9)
|
||||
val = atomic_decrement_if_positive (futex);
|
||||
val = atomic_decrement_if_positive (&isem->value);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (futex + 1);
|
||||
val = *futex;
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
val = isem->value;
|
||||
if (val > 0)
|
||||
*futex = val - 1;
|
||||
__sparc32_atomic_do_unlock24 (futex + 1);
|
||||
isem->value = val - 1;
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
|
||||
if (val > 0)
|
||||
{
|
||||
err = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
while (val <= 0);
|
||||
|
||||
return 0;
|
||||
pthread_cleanup_pop (0);
|
||||
|
||||
error_return:
|
||||
__set_errno (-err);
|
||||
return -1;
|
||||
if (__atomic_is_v9)
|
||||
atomic_decrement (&isem->nwaiters);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
isem->nwaiters--;
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
|
||||
return err;
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
/* sem_trywait -- wait on a semaphore. SPARC version.
|
||||
Copyright (C) 2003, 2006 Free Software Foundation, Inc.
|
||||
Copyright (C) 2003, 2006, 2007 Free Software Foundation, Inc.
|
||||
This file is part of the GNU C Library.
|
||||
Contributed by Paul Mackerras <paulus@au.ibm.com>, 2003.
|
||||
|
||||
@ -30,20 +30,20 @@
|
||||
int
|
||||
__new_sem_trywait (sem_t *sem)
|
||||
{
|
||||
int *futex = (int *) sem;
|
||||
struct sparc_old_sem *isem = (struct sparc_old_sem *) sem;
|
||||
int val;
|
||||
|
||||
if (*futex > 0)
|
||||
if (isem->value > 0)
|
||||
{
|
||||
if (__atomic_is_v9)
|
||||
val = atomic_decrement_if_positive (futex);
|
||||
val = atomic_decrement_if_positive (&isem->value);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (futex + 1);
|
||||
val = *futex;
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
val = isem->value;
|
||||
if (val > 0)
|
||||
*futex = val - 1;
|
||||
__sparc32_atomic_do_unlock24 (futex + 1);
|
||||
isem->value = val - 1;
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
if (val > 0)
|
||||
return 0;
|
||||
|
@ -1,5 +1,5 @@
|
||||
/* sem_wait -- wait on a semaphore. SPARC version.
|
||||
Copyright (C) 2003, 2006 Free Software Foundation, Inc.
|
||||
/* sem_wait -- wait on a semaphore. Generic futex-using version.
|
||||
Copyright (C) 2003, 2007 Free Software Foundation, Inc.
|
||||
This file is part of the GNU C Library.
|
||||
Contributed by Paul Mackerras <paulus@au.ibm.com>, 2003.
|
||||
|
||||
@ -28,35 +28,135 @@
|
||||
#include <shlib-compat.h>
|
||||
|
||||
|
||||
void
|
||||
attribute_hidden
|
||||
__sem_wait_cleanup (void *arg)
|
||||
{
|
||||
struct sparc_new_sem *isem = (struct sparc_new_sem *) arg;
|
||||
|
||||
if (__atomic_is_v9)
|
||||
atomic_decrement (&isem->nwaiters);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
isem->nwaiters--;
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
__new_sem_wait (sem_t *sem)
|
||||
{
|
||||
/* First check for cancellation. */
|
||||
CANCELLATION_P (THREAD_SELF);
|
||||
|
||||
int *futex = (int *) sem;
|
||||
struct sparc_new_sem *isem = (struct sparc_new_sem *) sem;
|
||||
int err;
|
||||
int val;
|
||||
|
||||
if (__atomic_is_v9)
|
||||
val = atomic_decrement_if_positive (&isem->value);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
val = isem->value;
|
||||
if (val > 0)
|
||||
isem->value = val - 1;
|
||||
else
|
||||
isem->nwaiters++;
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
|
||||
if (val > 0)
|
||||
return 0;
|
||||
|
||||
if (__atomic_is_v9)
|
||||
atomic_increment (&isem->nwaiters);
|
||||
else
|
||||
/* Already done above while still holding isem->lock. */;
|
||||
|
||||
pthread_cleanup_push (__sem_wait_cleanup, isem);
|
||||
|
||||
while (1)
|
||||
{
|
||||
/* Enable asynchronous cancellation. Required by the standard. */
|
||||
int oldtype = __pthread_enable_asynccancel ();
|
||||
|
||||
err = lll_futex_wait (&isem->value, 0,
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG);
|
||||
|
||||
/* Disable asynchronous cancellation. */
|
||||
__pthread_disable_asynccancel (oldtype);
|
||||
|
||||
if (err != 0 && err != -EWOULDBLOCK)
|
||||
{
|
||||
__set_errno (-err);
|
||||
err = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
if (__atomic_is_v9)
|
||||
val = atomic_decrement_if_positive (&isem->value);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
val = isem->value;
|
||||
if (val > 0)
|
||||
isem->value = val - 1;
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
|
||||
if (val > 0)
|
||||
{
|
||||
err = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
pthread_cleanup_pop (0);
|
||||
|
||||
if (__atomic_is_v9)
|
||||
atomic_decrement (&isem->nwaiters);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
isem->nwaiters--;
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
|
||||
return err;
|
||||
}
|
||||
versioned_symbol (libpthread, __new_sem_wait, sem_wait, GLIBC_2_1);
|
||||
|
||||
|
||||
#if SHLIB_COMPAT (libpthread, GLIBC_2_0, GLIBC_2_1)
|
||||
int
|
||||
attribute_compat_text_section
|
||||
__old_sem_wait (sem_t *sem)
|
||||
{
|
||||
struct sparc_old_sem *isem = (struct sparc_old_sem *) sem;
|
||||
int err;
|
||||
int val;
|
||||
|
||||
do
|
||||
{
|
||||
int val;
|
||||
if (__atomic_is_v9)
|
||||
val = atomic_decrement_if_positive (futex);
|
||||
val = atomic_decrement_if_positive (&isem->value);
|
||||
else
|
||||
{
|
||||
__sparc32_atomic_do_lock24 (futex + 1);
|
||||
val = *futex;
|
||||
__sparc32_atomic_do_lock24 (&isem->lock);
|
||||
val = isem->value;
|
||||
if (val > 0)
|
||||
*futex = val - 1;
|
||||
__sparc32_atomic_do_unlock24 (futex + 1);
|
||||
isem->value = val - 1;
|
||||
__sparc32_atomic_do_unlock24 (&isem->lock);
|
||||
}
|
||||
|
||||
if (val > 0)
|
||||
return 0;
|
||||
|
||||
/* Enable asynchronous cancellation. Required by the standard. */
|
||||
int oldtype = __pthread_enable_asynccancel ();
|
||||
|
||||
err = lll_futex_wait (futex, 0);
|
||||
err = lll_futex_wait (futex, 0,
|
||||
isem->private ^ FUTEX_PRIVATE_FLAG);
|
||||
|
||||
/* Disable asynchronous cancellation. */
|
||||
__pthread_disable_asynccancel (oldtype);
|
||||
@ -67,8 +167,5 @@ __new_sem_wait (sem_t *sem)
|
||||
return -1;
|
||||
}
|
||||
|
||||
versioned_symbol (libpthread, __new_sem_wait, sem_wait, GLIBC_2_1);
|
||||
#if SHLIB_COMPAT (libpthread, GLIBC_2_0, GLIBC_2_1)
|
||||
strong_alias (__new_sem_wait, __old_sem_wait)
|
||||
compat_symbol (libpthread, __old_sem_wait, sem_wait, GLIBC_2_0);
|
||||
#endif
|
||||
|
@ -1 +0,0 @@
|
||||
#include "../../../../../../../sem_init.c"
|
@ -1 +1 @@
|
||||
#include "../../../sem_post.c"
|
||||
#include "../../sem_post.c"
|
||||
|
@ -1 +1 @@
|
||||
#include "../../../sem_timedwait.c"
|
||||
#include "../../sem_timedwait.c"
|
||||
|
@ -1 +1 @@
|
||||
#include "../../../sem_wait.c"
|
||||
#include "../../sem_wait.c"
|
||||
|
@ -1,5 +1,5 @@
|
||||
/* Store current floating-point environment and clear exceptions.
|
||||
Copyright (C) 1997, 1998, 2005 Free Software Foundation, Inc.
|
||||
Copyright (C) 1997, 1998, 2005, 2007 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
|
||||
@ -26,8 +26,8 @@ feholdexcept (fenv_t *envp)
|
||||
|
||||
__fenv_stfsr (*envp);
|
||||
|
||||
/* Set all exceptions to non-stop. */
|
||||
tmp = *envp & ~(0x1f << 23);
|
||||
/* Set all exceptions to non-stop and clear all exceptions. */
|
||||
tmp = *envp & ~((0x1f << 23) | FE_ALL_EXCEPT);
|
||||
|
||||
__fenv_ldfsr (tmp);
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
/* Raise given exceptions.
|
||||
Copyright (C) 1997, 1999, 2000, 2002 Free Software Foundation, Inc.
|
||||
Copyright (C) 1997, 1999, 2000, 2002, 2007 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
|
||||
@ -26,9 +26,9 @@ int
|
||||
__feraiseexcept (int excepts)
|
||||
{
|
||||
static const struct {
|
||||
double zero, one, max, min, sixteen, pi;
|
||||
double zero, one, max, min, pi;
|
||||
} c = {
|
||||
0.0, 1.0, DBL_MAX, DBL_MIN, 16.0, M_PI
|
||||
0.0, 1.0, DBL_MAX, DBL_MIN, M_PI
|
||||
};
|
||||
double d;
|
||||
|
||||
@ -66,7 +66,7 @@ __feraiseexcept (int excepts)
|
||||
if ((FE_UNDERFLOW & excepts) != 0)
|
||||
{
|
||||
__asm ("" : "=e" (d) : "0" (c.min));
|
||||
d /= c.sixteen;
|
||||
d *= d;
|
||||
__asm __volatile ("" : : "e" (d));
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user