Login
Log in using an SSO provider:
Fedora Account System
Red Hat Associate
Red Hat Customer
Login using a Red Hat Bugzilla account
Forgot Password
Create an Account
Red Hat Bugzilla – Attachment 755948 Details for
Bug 969817
gc lacks atomic ops for aarch64
Home
New
Search
Simple Search
Advanced Search
My Links
Browse
Requests
Reports
Current State
Search
Tabular reports
Graphical reports
Duplicates
Other Reports
User Changes
Plotly Reports
Bug Status
Bug Severity
Non-Defaults
Product Dashboard
Help
Page Help!
Bug Writing Guidelines
What's new
Browser Support Policy
5.0.4.rh90 Release notes
FAQ
Guides index
User guide
Web Services
Contact
Legal
[?]
This site requires JavaScript to be enabled to function correctly, please enable it.
[patch]
aarch64 support for libatomic_ops
gc-aarch64.patch (text/plain), 13.72 KB, created by
Mark Salter
on 2013-06-02 14:47:47 UTC
(
hide
)
Description:
aarch64 support for libatomic_ops
Filename:
MIME Type:
Creator:
Mark Salter
Created:
2013-06-02 14:47:47 UTC
Size:
13.72 KB
patch
obsolete
>diff --git a/include/private/gcconfig.h b/include/private/gcconfig.h >index 767859c..ec92882 100644 >--- a/include/private/gcconfig.h >+++ b/include/private/gcconfig.h >@@ -70,6 +70,13 @@ > # define I386 > # define mach_type_known > # endif >+# if defined(__aarch64__) >+# define AARCH64 >+# if !defined(LINUX) >+# define NOSYS >+# define mach_type_known >+# endif >+# endif > # if defined(__arm) || defined(__arm__) || defined(__thumb__) > # define ARM32 > # if !defined(LINUX) && !defined(NETBSD) && !defined(OPENBSD) \ >@@ -250,6 +257,10 @@ > # define IA64 > # define mach_type_known > # endif >+# if defined(LINUX) && defined(__aarch64__) >+# define AARCH64 >+# define mach_type_known >+# endif > # if defined(LINUX) && (defined(__arm) || defined(__arm__)) > # define ARM32 > # define mach_type_known >@@ -537,6 +548,7 @@ > /* running Amdahl UTS4 */ > /* S390 ==> 390-like machine */ > /* running LINUX */ >+ /* AARCH64 ==> ARM AArch64 */ > /* ARM32 ==> Intel StrongARM */ > /* IA64 ==> Intel IPF */ > /* (e.g. Itanium) */ >@@ -1899,6 +1911,31 @@ > # endif > # endif > >+# ifdef AARCH64 >+# define CPP_WORDSZ 64 >+# define MACH_TYPE "AARCH64" >+# define ALIGNMENT 8 >+# ifndef HBLKSIZE >+# define HBLKSIZE 4096 >+# endif >+# ifdef LINUX >+# define OS_TYPE "LINUX" >+# define LINUX_STACKBOTTOM >+# define DYNAMIC_LOADING >+ extern int __data_start[]; >+# define DATASTART ((ptr_t)__data_start) >+ extern char _end[]; >+# define DATAEND ((ptr_t)(&_end)) >+# endif >+# ifdef NOSYS >+ /* __data_start is usually defined in the target linker script. */ >+ extern int __data_start[]; >+# define DATASTART ((ptr_t)__data_start) >+ extern void *__stack_base__; >+# define STACKBOTTOM ((ptr_t)__stack_base__) >+# endif >+# endif >+ > # ifdef ARM32 > # define CPP_WORDSZ 32 > # define MACH_TYPE "ARM32" >diff --git a/libatomic_ops/src/atomic_ops.h b/libatomic_ops/src/atomic_ops.h >index db177d5..d91da53 100644 >--- a/libatomic_ops/src/atomic_ops.h >+++ b/libatomic_ops/src/atomic_ops.h >@@ -244,6 +244,10 @@ > || defined(__powerpc64__) || defined(__ppc64__) > # include "atomic_ops/sysdeps/gcc/powerpc.h" > # endif /* __powerpc__ */ >+# if defined(__aarch64__) >+# include "atomic_ops/sysdeps/gcc/aarch64.h" >+# define AO_CAN_EMUL_CAS >+# endif /* __aarch64__ */ > # if defined(__arm__) && !defined(AO_USE_PTHREAD_DEFS) > # include "atomic_ops/sysdeps/gcc/arm.h" > # define AO_CAN_EMUL_CAS >diff --git a/libatomic_ops/src/atomic_ops/sysdeps/Makefile.am b/libatomic_ops/src/atomic_ops/sysdeps/Makefile.am >index d8b24dc..b73a20c 100644 >--- a/libatomic_ops/src/atomic_ops/sysdeps/Makefile.am >+++ b/libatomic_ops/src/atomic_ops/sysdeps/Makefile.am >@@ -30,6 +30,7 @@ nobase_sysdep_HEADERS= generic_pthread.h \ > gcc/hexagon.h gcc/hppa.h gcc/ia64.h gcc/m68k.h \ > gcc/mips.h gcc/powerpc.h gcc/s390.h \ > gcc/sh.h gcc/sparc.h gcc/x86.h gcc/x86_64.h \ >+ gcc/aarch64.h \ > \ > hpc/hppa.h hpc/ia64.h \ > \ >diff --git a/libatomic_ops/src/atomic_ops/sysdeps/gcc/aarch64.h b/libatomic_ops/src/atomic_ops/sysdeps/gcc/aarch64.h >new file mode 100644 >index 0000000..94f1f14 >--- /dev/null >+++ b/libatomic_ops/src/atomic_ops/sysdeps/gcc/aarch64.h >@@ -0,0 +1,353 @@ >+/* >+ * Copyright (c) 1991-1994 by Xerox Corporation. All rights reserved. >+ * Copyright (c) 1996-1999 by Silicon Graphics. All rights reserved. >+ * Copyright (c) 1999-2003 by Hewlett-Packard Company. All rights reserved. >+ * >+ * >+ * THIS MATERIAL IS PROVIDED AS IS, WITH ABSOLUTELY NO WARRANTY EXPRESSED >+ * OR IMPLIED. ANY USE IS AT YOUR OWN RISK. >+ * >+ * Permission is hereby granted to use or copy this program >+ * for any purpose, provided the above notices are retained on all copies. >+ * Permission to modify the code and to distribute modified code is granted, >+ * provided the above notices are retained, and a notice that the code was >+ * modified is included with the above copyright notice. >+ * >+ */ >+ >+#include "../read_ordered.h" >+ >+#include "../test_and_set_t_is_ao_t.h" >+ >+#include "../standard_ao_double_t.h" >+ >+#ifndef AO_UNIPROCESSOR >+ AO_INLINE void >+ AO_nop_write(void) >+ { >+ __asm__ __volatile__("dmb st" : : : "memory"); >+ } >+# define AO_HAVE_nop_write >+#endif >+ >+#ifndef AO_EXPECT_FALSE >+#if __GNUC__ >= 3 && !defined(LINT2) >+# define AO_EXPECT_FALSE(expr) __builtin_expect(expr, 0) >+ /* Equivalent to (expr) but predict that usually (expr) == 0. */ >+#else >+# define AO_EXPECT_FALSE(expr) (expr) >+#endif /* !__GNUC__ */ >+#endif >+ >+/* TODO: Adjust version check on fixing double-wide AO support in GCC. */ >+#if __GNUC__ == 4 >+ >+ AO_INLINE AO_double_t >+ AO_double_load(const volatile AO_double_t *addr) >+ { >+ AO_double_t result; >+ int status; >+ >+ /* Note that STXP cannot be discarded because LD[A]XP is not */ >+ /* single-copy atomic (unlike LDREXD for 32-bit ARM). */ >+ do { >+ __asm__ __volatile__("//AO_double_load\n" >+ " ldxp %0, %1, %3\n" >+ " stxp %w2, %0, %1, %3" >+ : "=&r" (result.AO_val1), "=&r" (result.AO_val2), "=&r" (status) >+ : "Q" (*addr)); >+ } while (AO_EXPECT_FALSE(status)); >+ return result; >+ } >+# define AO_HAVE_double_load >+ >+ AO_INLINE AO_double_t >+ AO_double_load_acquire(const volatile AO_double_t *addr) >+ { >+ AO_double_t result; >+ int status; >+ >+ do { >+ __asm__ __volatile__("//AO_double_load_acquire\n" >+ " ldaxp %0, %1, %3\n" >+ " stxp %w2, %0, %1, %3" >+ : "=&r" (result.AO_val1), "=&r" (result.AO_val2), "=&r" (status) >+ : "Q" (*addr)); >+ } while (AO_EXPECT_FALSE(status)); >+ return result; >+ } >+# define AO_HAVE_double_load_acquire >+ >+ AO_INLINE void >+ AO_double_store(volatile AO_double_t *addr, AO_double_t value) >+ { >+ AO_double_t old_val; >+ int status; >+ >+ do { >+ __asm__ __volatile__("//AO_double_store\n" >+ " ldxp %0, %1, %3\n" >+ " stxp %w2, %4, %5, %3" >+ : "=&r" (old_val.AO_val1), "=&r" (old_val.AO_val2), "=&r" (status), >+ "=Q" (*addr) >+ : "r" (value.AO_val1), "r" (value.AO_val2)); >+ /* Compared to the arm.h implementation, the 'cc' (flags) are not */ >+ /* clobbered because A64 has no concept of conditional execution. */ >+ } while (AO_EXPECT_FALSE(status)); >+ } >+# define AO_HAVE_double_store >+ >+ AO_INLINE void >+ AO_double_store_release(volatile AO_double_t *addr, AO_double_t value) >+ { >+ AO_double_t old_val; >+ int status; >+ >+ do { >+ __asm__ __volatile__("//AO_double_store_release\n" >+ " ldxp %0, %1, %3\n" >+ " stlxp %w2, %4, %5, %3" >+ : "=&r" (old_val.AO_val1), "=&r" (old_val.AO_val2), "=&r" (status), >+ "=Q" (*addr) >+ : "r" (value.AO_val1), "r" (value.AO_val2)); >+ } while (AO_EXPECT_FALSE(status)); >+ } >+# define AO_HAVE_double_store_release >+ >+ AO_INLINE int >+ AO_double_compare_and_swap(volatile AO_double_t *addr, >+ AO_double_t old_val, AO_double_t new_val) >+ { >+ AO_double_t tmp; >+ int result = 1; >+ >+ do { >+ __asm__ __volatile__("//AO_double_compare_and_swap\n" >+ " ldxp %0, %1, %2\n" >+ : "=&r" (tmp.AO_val1), "=&r" (tmp.AO_val2) >+ : "Q" (*addr)); >+ if (tmp.AO_val1 != old_val.AO_val1 || tmp.AO_val2 != old_val.AO_val2) >+ break; >+ __asm__ __volatile__( >+ " stxp %w0, %2, %3, %1\n" >+ : "=&r" (result), "=Q" (*addr) >+ : "r" (new_val.AO_val1), "r" (new_val.AO_val2)); >+ } while (AO_EXPECT_FALSE(result)); >+ return !result; >+ } >+# define AO_HAVE_double_compare_and_swap >+ >+ AO_INLINE int >+ AO_double_compare_and_swap_acquire(volatile AO_double_t *addr, >+ AO_double_t old_val, AO_double_t new_val) >+ { >+ AO_double_t tmp; >+ int result = 1; >+ >+ do { >+ __asm__ __volatile__("//AO_double_compare_and_swap_acquire\n" >+ " ldaxp %0, %1, %2\n" >+ : "=&r" (tmp.AO_val1), "=&r" (tmp.AO_val2) >+ : "Q" (*addr)); >+ if (tmp.AO_val1 != old_val.AO_val1 || tmp.AO_val2 != old_val.AO_val2) >+ break; >+ __asm__ __volatile__( >+ " stxp %w0, %2, %3, %1\n" >+ : "=&r" (result), "=Q" (*addr) >+ : "r" (new_val.AO_val1), "r" (new_val.AO_val2)); >+ } while (AO_EXPECT_FALSE(result)); >+ return !result; >+ } >+# define AO_HAVE_double_compare_and_swap_acquire >+ >+ AO_INLINE int >+ AO_double_compare_and_swap_release(volatile AO_double_t *addr, >+ AO_double_t old_val, AO_double_t new_val) >+ { >+ AO_double_t tmp; >+ int result = 1; >+ >+ do { >+ __asm__ __volatile__("//AO_double_compare_and_swap_release\n" >+ " ldxp %0, %1, %2\n" >+ : "=&r" (tmp.AO_val1), "=&r" (tmp.AO_val2) >+ : "Q" (*addr)); >+ if (tmp.AO_val1 != old_val.AO_val1 || tmp.AO_val2 != old_val.AO_val2) >+ break; >+ __asm__ __volatile__( >+ " stlxp %w0, %2, %3, %1\n" >+ : "=&r" (result), "=Q" (*addr) >+ : "r" (new_val.AO_val1), "r" (new_val.AO_val2)); >+ } while (AO_EXPECT_FALSE(result)); >+ return !result; >+ } >+# define AO_HAVE_double_compare_and_swap_release >+#endif >+ >+AO_INLINE void >+AO_nop_full(void) >+{ >+# ifndef AO_UNIPROCESSOR >+__sync_synchronize (); >+# endif >+} >+#define AO_HAVE_nop_full >+ >+AO_INLINE AO_t >+AO_load(const volatile AO_t *addr) >+{ >+ return (AO_t)__atomic_load_n (addr, __ATOMIC_RELAXED); >+} >+#define AO_HAVE_load >+ >+AO_INLINE AO_t >+AO_load_acquire(const volatile AO_t *addr) >+{ >+ return (AO_t)__atomic_load_n (addr, __ATOMIC_ACQUIRE); >+} >+#define AO_HAVE_load_acquire >+ >+AO_INLINE void >+ AO_store(volatile AO_t *addr, AO_t value) >+{ >+ __atomic_store_n(addr, value, __ATOMIC_RELAXED); >+} >+#define AO_HAVE_store >+ >+AO_INLINE void >+ AO_store_release(volatile AO_t *addr, AO_t value) >+{ >+ __atomic_store_n(addr, value, __ATOMIC_RELEASE); >+} >+#define AO_HAVE_store_release >+ >+AO_INLINE AO_TS_VAL_t >+AO_test_and_set(volatile AO_TS_t *addr) >+{ >+ return (AO_TS_VAL_t)__atomic_test_and_set(addr, __ATOMIC_RELAXED); >+} >+# define AO_HAVE_test_and_set >+ >+AO_INLINE AO_TS_VAL_t >+AO_test_and_set_acquire(volatile AO_TS_t *addr) >+{ >+ return (AO_TS_VAL_t)__atomic_test_and_set(addr, __ATOMIC_ACQUIRE); >+} >+# define AO_HAVE_test_and_set_acquire >+ >+AO_INLINE AO_TS_VAL_t >+AO_test_and_set_release(volatile AO_TS_t *addr) >+{ >+ return (AO_TS_VAL_t)__atomic_test_and_set(addr, __ATOMIC_RELEASE); >+} >+# define AO_HAVE_test_and_set_release >+ >+AO_INLINE AO_TS_VAL_t >+AO_test_and_set_full(volatile AO_TS_t *addr) >+{ >+ return (AO_TS_VAL_t)__atomic_test_and_set(addr, __ATOMIC_SEQ_CST); >+} >+# define AO_HAVE_test_and_set_full >+ >+AO_INLINE AO_t >+AO_fetch_and_add(volatile AO_t *p, AO_t incr) >+{ >+ return (AO_t)__atomic_fetch_add(p, incr, __ATOMIC_RELAXED); >+} >+#define AO_HAVE_fetch_and_add >+ >+AO_INLINE AO_t >+AO_fetch_and_add_acquire(volatile AO_t *p, AO_t incr) >+{ >+ return (AO_t)__atomic_fetch_add(p, incr, __ATOMIC_ACQUIRE); >+} >+#define AO_HAVE_fetch_and_add_acquire >+ >+AO_INLINE AO_t >+AO_fetch_and_add_release(volatile AO_t *p, AO_t incr) >+{ >+ return (AO_t)__atomic_fetch_add(p, incr, __ATOMIC_RELEASE); >+} >+#define AO_HAVE_fetch_and_add_release >+ >+AO_INLINE AO_t >+AO_fetch_and_add_full(volatile AO_t *p, AO_t incr) >+{ >+ return (AO_t)__atomic_fetch_add(p, incr, __ATOMIC_SEQ_CST); >+} >+#define AO_HAVE_fetch_and_add_full >+ >+AO_INLINE AO_t >+AO_fetch_and_add1(volatile AO_t *p) >+{ >+ return (AO_t)__atomic_fetch_add(p, 1, __ATOMIC_RELAXED); >+} >+#define AO_HAVE_fetch_and_add1 >+ >+AO_INLINE AO_t >+AO_fetch_and_add1_acquire(volatile AO_t *p) >+{ >+ return (AO_t)__atomic_fetch_add(p, 1, __ATOMIC_ACQUIRE); >+} >+#define AO_HAVE_fetch_and_add1_acquire >+ >+AO_INLINE AO_t >+AO_fetch_and_add1_release(volatile AO_t *p) >+{ >+ return (AO_t)__atomic_fetch_add(p, 1, __ATOMIC_RELEASE); >+} >+#define AO_HAVE_fetch_and_add1_release >+ >+AO_INLINE AO_t >+AO_fetch_and_add1_full(volatile AO_t *p) >+{ >+ return (AO_t)__atomic_fetch_add(p, 1, __ATOMIC_SEQ_CST); >+} >+#define AO_HAVE_fetch_and_add1_full >+ >+AO_INLINE AO_t >+AO_fetch_and_sub1(volatile AO_t *p) >+{ >+ return (AO_t)__atomic_fetch_sub(p, 1, __ATOMIC_RELAXED); >+} >+#define AO_HAVE_fetch_and_sub1 >+ >+AO_INLINE AO_t >+AO_fetch_and_sub1_acquire(volatile AO_t *p) >+{ >+ return (AO_t)__atomic_fetch_sub(p, 1, __ATOMIC_ACQUIRE); >+} >+#define AO_HAVE_fetch_and_sub1_acquire >+ >+AO_INLINE AO_t >+AO_fetch_and_sub1_release(volatile AO_t *p) >+{ >+ return (AO_t)__atomic_fetch_sub(p, 1, __ATOMIC_RELEASE); >+} >+#define AO_HAVE_fetch_and_sub1_release >+ >+AO_INLINE AO_t >+AO_fetch_and_sub1_full(volatile AO_t *p) >+{ >+ return (AO_t)__atomic_fetch_sub(p, 1, __ATOMIC_SEQ_CST); >+} >+#define AO_HAVE_fetch_and_sub1_full >+ >+/* Returns nonzero if the comparison succeeded. */ >+AO_INLINE int >+AO_compare_and_swap(volatile AO_t *addr, AO_t old_val, AO_t new_val) >+{ >+ return (int)__sync_bool_compare_and_swap(addr, old_val, new_val); >+} >+# define AO_HAVE_compare_and_swap >+ >+AO_INLINE AO_t >+AO_fetch_compare_and_swap(volatile AO_t *addr, AO_t old_val, AO_t new_val) >+{ >+ return (AO_t)__sync_val_compare_and_swap(addr, old_val, new_val); >+} >+# define AO_HAVE_fetch_compare_and_swap >+ >+ >+ >+#include "../../generalize.h" >diff --git a/libatomic_ops/src/atomic_ops/sysdeps/standard_ao_double_t.h b/libatomic_ops/src/atomic_ops/sysdeps/standard_ao_double_t.h >index 7089f05..de726fc 100644 >--- a/libatomic_ops/src/atomic_ops/sysdeps/standard_ao_double_t.h >+++ b/libatomic_ops/src/atomic_ops/sysdeps/standard_ao_double_t.h >@@ -11,6 +11,8 @@ > typedef __m128 double_ptr_storage; > #elif defined(_WIN32) && !defined(__GNUC__) > typedef unsigned __int64 double_ptr_storage; >+#elif defined(__aarch64__) >+ typedef unsigned __int128 double_ptr_storage; > #else > typedef unsigned long long double_ptr_storage; > #endif
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 969817
: 755948