|
@@ -1,247 +1,3 @@
|
|
-/* Atomic operations. PowerPC Common version.
|
|
|
|
- Copyright (C) 2003, 2004 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, see
|
|
|
|
- <http://www.gnu.org/licenses/>. */
|
|
|
|
-
|
|
|
|
-#include <bits/wordsize.h>
|
|
|
|
-
|
|
|
|
-#if __WORDSIZE == 64
|
|
|
|
-/* Atomic operations. PowerPC64 version.
|
|
|
|
- Copyright (C) 2003, 2004 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, see
|
|
|
|
- <http://www.gnu.org/licenses/>. */
|
|
|
|
-
|
|
|
|
-/* The 32-bit exchange_bool is different on powerpc64 because the subf
|
|
|
|
- does signed 64-bit arthmatic while the lwarx is 32-bit unsigned
|
|
|
|
- (a load word and zero (high 32) form) load.
|
|
|
|
- In powerpc64 register values are 64-bit by default, including oldval.
|
|
|
|
- The value in old val unknown sign extension, lwarx loads the 32-bit
|
|
|
|
- value as unsigned. So we explicitly clear the high 32 bits in oldval. */
|
|
|
|
-# define __arch_compare_and_exchange_bool_32_acq(mem, newval, oldval) \
|
|
|
|
-({ \
|
|
|
|
- unsigned int __tmp, __tmp2; \
|
|
|
|
- __asm__ __volatile__ (" clrldi %1,%1,32\n" \
|
|
|
|
- "1: lwarx %0,0,%2\n" \
|
|
|
|
- " subf. %0,%1,%0\n" \
|
|
|
|
- " bne 2f\n" \
|
|
|
|
- " stwcx. %4,0,%2\n" \
|
|
|
|
- " bne- 1b\n" \
|
|
|
|
- "2: " __ARCH_ACQ_INSTR \
|
|
|
|
- : "=&r" (__tmp), "=r" (__tmp2) \
|
|
|
|
- : "b" (mem), "1" (oldval), "r" (newval) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __tmp != 0; \
|
|
|
|
-})
|
|
|
|
-
|
|
|
|
-# define __arch_compare_and_exchange_bool_32_rel(mem, newval, oldval) \
|
|
|
|
-({ \
|
|
|
|
- unsigned int __tmp, __tmp2; \
|
|
|
|
- __asm__ __volatile__ (__ARCH_REL_INSTR "\n" \
|
|
|
|
- " clrldi %1,%1,32\n" \
|
|
|
|
- "1: lwarx %0,0,%2\n" \
|
|
|
|
- " subf. %0,%1,%0\n" \
|
|
|
|
- " bne 2f\n" \
|
|
|
|
- " stwcx. %4,0,%2\n" \
|
|
|
|
- " bne- 1b\n" \
|
|
|
|
- "2: " \
|
|
|
|
- : "=&r" (__tmp), "=r" (__tmp2) \
|
|
|
|
- : "b" (mem), "1" (oldval), "r" (newval) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __tmp != 0; \
|
|
|
|
-})
|
|
|
|
-
|
|
|
|
-/*
|
|
|
|
- * Only powerpc64 processors support Load doubleword and reserve index (ldarx)
|
|
|
|
- * and Store doubleword conditional indexed (stdcx) instructions. So here
|
|
|
|
- * we define the 64-bit forms.
|
|
|
|
- */
|
|
|
|
-# define __arch_compare_and_exchange_bool_64_acq(mem, newval, oldval) \
|
|
|
|
-({ \
|
|
|
|
- unsigned long __tmp; \
|
|
|
|
- __asm__ __volatile__ ( \
|
|
|
|
- "1: ldarx %0,0,%1\n" \
|
|
|
|
- " subf. %0,%2,%0\n" \
|
|
|
|
- " bne 2f\n" \
|
|
|
|
- " stdcx. %3,0,%1\n" \
|
|
|
|
- " bne- 1b\n" \
|
|
|
|
- "2: " __ARCH_ACQ_INSTR \
|
|
|
|
- : "=&r" (__tmp) \
|
|
|
|
- : "b" (mem), "r" (oldval), "r" (newval) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __tmp != 0; \
|
|
|
|
-})
|
|
|
|
-
|
|
|
|
-# define __arch_compare_and_exchange_bool_64_rel(mem, newval, oldval) \
|
|
|
|
-({ \
|
|
|
|
- unsigned long __tmp; \
|
|
|
|
- __asm__ __volatile__ (__ARCH_REL_INSTR "\n" \
|
|
|
|
- "1: ldarx %0,0,%1\n" \
|
|
|
|
- " subf. %0,%2,%0\n" \
|
|
|
|
- " bne 2f\n" \
|
|
|
|
- " stdcx. %3,0,%1\n" \
|
|
|
|
- " bne- 1b\n" \
|
|
|
|
- "2: " \
|
|
|
|
- : "=&r" (__tmp) \
|
|
|
|
- : "b" (mem), "r" (oldval), "r" (newval) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __tmp != 0; \
|
|
|
|
-})
|
|
|
|
-
|
|
|
|
-#define __arch_compare_and_exchange_val_64_acq(mem, newval, oldval) \
|
|
|
|
- ({ \
|
|
|
|
- __typeof (*(mem)) __tmp; \
|
|
|
|
- __typeof (mem) __memp = (mem); \
|
|
|
|
- __asm__ __volatile__ ( \
|
|
|
|
- "1: ldarx %0,0,%1\n" \
|
|
|
|
- " cmpd %0,%2\n" \
|
|
|
|
- " bne 2f\n" \
|
|
|
|
- " stdcx. %3,0,%1\n" \
|
|
|
|
- " bne- 1b\n" \
|
|
|
|
- "2: " __ARCH_ACQ_INSTR \
|
|
|
|
- : "=&r" (__tmp) \
|
|
|
|
- : "b" (__memp), "r" (oldval), "r" (newval) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __tmp; \
|
|
|
|
- })
|
|
|
|
-
|
|
|
|
-#define __arch_compare_and_exchange_val_64_rel(mem, newval, oldval) \
|
|
|
|
- ({ \
|
|
|
|
- __typeof (*(mem)) __tmp; \
|
|
|
|
- __typeof (mem) __memp = (mem); \
|
|
|
|
- __asm__ __volatile__ (__ARCH_REL_INSTR "\n" \
|
|
|
|
- "1: ldarx %0,0,%1\n" \
|
|
|
|
- " cmpd %0,%2\n" \
|
|
|
|
- " bne 2f\n" \
|
|
|
|
- " stdcx. %3,0,%1\n" \
|
|
|
|
- " bne- 1b\n" \
|
|
|
|
- "2: " \
|
|
|
|
- : "=&r" (__tmp) \
|
|
|
|
- : "b" (__memp), "r" (oldval), "r" (newval) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __tmp; \
|
|
|
|
- })
|
|
|
|
-
|
|
|
|
-# define __arch_atomic_exchange_64_acq(mem, value) \
|
|
|
|
- ({ \
|
|
|
|
- __typeof (*mem) __val; \
|
|
|
|
- __asm__ __volatile__ (__ARCH_REL_INSTR "\n" \
|
|
|
|
- "1: ldarx %0,0,%2\n" \
|
|
|
|
- " stdcx. %3,0,%2\n" \
|
|
|
|
- " bne- 1b\n" \
|
|
|
|
- " " __ARCH_ACQ_INSTR \
|
|
|
|
- : "=&r" (__val), "=m" (*mem) \
|
|
|
|
- : "b" (mem), "r" (value), "m" (*mem) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __val; \
|
|
|
|
- })
|
|
|
|
-
|
|
|
|
-# define __arch_atomic_exchange_64_rel(mem, value) \
|
|
|
|
- ({ \
|
|
|
|
- __typeof (*mem) __val; \
|
|
|
|
- __asm__ __volatile__ (__ARCH_REL_INSTR "\n" \
|
|
|
|
- "1: ldarx %0,0,%2\n" \
|
|
|
|
- " stdcx. %3,0,%2\n" \
|
|
|
|
- " bne- 1b" \
|
|
|
|
- : "=&r" (__val), "=m" (*mem) \
|
|
|
|
- : "b" (mem), "r" (value), "m" (*mem) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __val; \
|
|
|
|
- })
|
|
|
|
-
|
|
|
|
-# define __arch_atomic_exchange_and_add_64(mem, value) \
|
|
|
|
- ({ \
|
|
|
|
- __typeof (*mem) __val, __tmp; \
|
|
|
|
- __asm__ __volatile__ ("1: ldarx %0,0,%3\n" \
|
|
|
|
- " add %1,%0,%4\n" \
|
|
|
|
- " stdcx. %1,0,%3\n" \
|
|
|
|
- " bne- 1b" \
|
|
|
|
- : "=&b" (__val), "=&r" (__tmp), "=m" (*mem) \
|
|
|
|
- : "b" (mem), "r" (value), "m" (*mem) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __val; \
|
|
|
|
- })
|
|
|
|
-
|
|
|
|
-# define __arch_atomic_increment_val_64(mem) \
|
|
|
|
- ({ \
|
|
|
|
- __typeof (*(mem)) __val; \
|
|
|
|
- __asm__ __volatile__ ("1: ldarx %0,0,%2\n" \
|
|
|
|
- " addi %0,%0,1\n" \
|
|
|
|
- " stdcx. %0,0,%2\n" \
|
|
|
|
- " bne- 1b" \
|
|
|
|
- : "=&b" (__val), "=m" (*mem) \
|
|
|
|
- : "b" (mem), "m" (*mem) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __val; \
|
|
|
|
- })
|
|
|
|
-
|
|
|
|
-# define __arch_atomic_decrement_val_64(mem) \
|
|
|
|
- ({ \
|
|
|
|
- __typeof (*(mem)) __val; \
|
|
|
|
- __asm__ __volatile__ ("1: ldarx %0,0,%2\n" \
|
|
|
|
- " subi %0,%0,1\n" \
|
|
|
|
- " stdcx. %0,0,%2\n" \
|
|
|
|
- " bne- 1b" \
|
|
|
|
- : "=&b" (__val), "=m" (*mem) \
|
|
|
|
- : "b" (mem), "m" (*mem) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __val; \
|
|
|
|
- })
|
|
|
|
-
|
|
|
|
-# define __arch_atomic_decrement_if_positive_64(mem) \
|
|
|
|
- ({ int __val, __tmp; \
|
|
|
|
- __asm__ __volatile__ ("1: ldarx %0,0,%3\n" \
|
|
|
|
- " cmpdi 0,%0,0\n" \
|
|
|
|
- " addi %1,%0,-1\n" \
|
|
|
|
- " ble 2f\n" \
|
|
|
|
- " stdcx. %1,0,%3\n" \
|
|
|
|
- " bne- 1b\n" \
|
|
|
|
- "2: " __ARCH_ACQ_INSTR \
|
|
|
|
- : "=&b" (__val), "=&r" (__tmp), "=m" (*mem) \
|
|
|
|
- : "b" (mem), "m" (*mem) \
|
|
|
|
- : "cr0", "memory"); \
|
|
|
|
- __val; \
|
|
|
|
- })
|
|
|
|
-
|
|
|
|
-/*
|
|
|
|
- * All powerpc64 processors support the new "light weight" sync (lwsync).
|
|
|
|
- */
|
|
|
|
-# define atomic_read_barrier() __asm__ ("lwsync" ::: "memory")
|
|
|
|
-/*
|
|
|
|
- * "light weight" sync can also be used for the release barrier.
|
|
|
|
- */
|
|
|
|
-# ifndef UP
|
|
|
|
-# define __ARCH_REL_INSTR "lwsync"
|
|
|
|
-# endif
|
|
|
|
-
|
|
|
|
-#else
|
|
|
|
/* Atomic operations. PowerPC32 version.
|
|
/* Atomic operations. PowerPC32 version.
|
|
Copyright (C) 2003, 2004 Free Software Foundation, Inc.
|
|
Copyright (C) 2003, 2004 Free Software Foundation, Inc.
|
|
This file is part of the GNU C Library.
|
|
This file is part of the GNU C Library.
|
|
@@ -261,12 +17,6 @@
|
|
License along with the GNU C Library; if not, see
|
|
License along with the GNU C Library; if not, see
|
|
<http://www.gnu.org/licenses/>. */
|
|
<http://www.gnu.org/licenses/>. */
|
|
|
|
|
|
-/*
|
|
|
|
- * The 32-bit exchange_bool is different on powerpc64 because the subf
|
|
|
|
- * does signed 64-bit arthmatic while the lwarx is 32-bit unsigned
|
|
|
|
- * (a load word and zero (high 32) form). So powerpc64 has a slightly
|
|
|
|
- * different version in sysdeps/powerpc/powerpc64/bits/atomic.h.
|
|
|
|
- */
|
|
|
|
# define __arch_compare_and_exchange_bool_32_acq(mem, newval, oldval) \
|
|
# define __arch_compare_and_exchange_bool_32_acq(mem, newval, oldval) \
|
|
({ \
|
|
({ \
|
|
unsigned int __tmp; \
|
|
unsigned int __tmp; \
|
|
@@ -355,8 +105,6 @@
|
|
# define atomic_read_barrier() __asm__ ("sync" ::: "memory")
|
|
# define atomic_read_barrier() __asm__ ("sync" ::: "memory")
|
|
#endif
|
|
#endif
|
|
|
|
|
|
-#endif
|
|
|
|
-
|
|
|
|
#include <stdint.h>
|
|
#include <stdint.h>
|
|
|
|
|
|
typedef int32_t atomic32_t;
|
|
typedef int32_t atomic32_t;
|