aboutsummaryrefslogtreecommitdiff
path: root/libgo
diff options
context:
space:
mode:
authorIan Lance Taylor <ian@gcc.gnu.org>2012-02-12 06:23:08 +0000
committerIan Lance Taylor <ian@gcc.gnu.org>2012-02-12 06:23:08 +0000
commit12e3c3961436e0bc19f7fcbf7dd5ba6d556b0803 (patch)
treed088dbdf76ccf89230dc607d000488ace3bb43e9 /libgo
parent22d87829789be10d2b3a88c2ee6253d88ff88d6b (diff)
downloadgcc-12e3c3961436e0bc19f7fcbf7dd5ba6d556b0803.zip
gcc-12e3c3961436e0bc19f7fcbf7dd5ba6d556b0803.tar.gz
gcc-12e3c3961436e0bc19f7fcbf7dd5ba6d556b0803.tar.bz2
re PR go/52084 (go tests fail to link on powerpc-linux-gnu (undefined reference to __sync_add_and_fetch_8))
PR go/52084 libgo: Provide more __sync functions if required. From-SVN: r184138
Diffstat (limited to 'libgo')
-rw-r--r--libgo/config.h.in8
-rwxr-xr-xlibgo/configure58
-rw-r--r--libgo/configure.ac28
-rw-r--r--libgo/runtime/thread.c59
4 files changed, 152 insertions, 1 deletions
diff --git a/libgo/config.h.in b/libgo/config.h.in
index afbb9ee..ae81ff4 100644
--- a/libgo/config.h.in
+++ b/libgo/config.h.in
@@ -105,10 +105,18 @@
/* Define to 1 if <math.h> defines struct exception */
#undef HAVE_STRUCT_EXCEPTION
+/* Define to 1 if the compiler provides the __sync_add_and_fetch function for
+ uint64 */
+#undef HAVE_SYNC_ADD_AND_FETCH_8
+
/* Define to 1 if the compiler provides the __sync_bool_compare_and_swap
function for uint32 */
#undef HAVE_SYNC_BOOL_COMPARE_AND_SWAP_4
+/* Define to 1 if the compiler provides the __sync_bool_compare_and_swap
+ function for uint64 */
+#undef HAVE_SYNC_BOOL_COMPARE_AND_SWAP_8
+
/* Define to 1 if the compiler provides the __sync_fetch_and_add function for
uint32 */
#undef HAVE_SYNC_FETCH_AND_ADD_4
diff --git a/libgo/configure b/libgo/configure
index 6bb35a6..1ce89d2 100755
--- a/libgo/configure
+++ b/libgo/configure
@@ -14667,6 +14667,35 @@ $as_echo "#define HAVE_SYNC_BOOL_COMPARE_AND_SWAP_4 1" >>confdefs.h
fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for __sync_bool_compare_and_swap_8" >&5
+$as_echo_n "checking for __sync_bool_compare_and_swap_8... " >&6; }
+if test "${libgo_cv_func___sync_bool_compare_and_swap_8+set}" = set; then :
+ $as_echo_n "(cached) " >&6
+else
+ cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+
+typedef unsigned int uint64 __attribute__ ((mode (DI)));
+uint64 i;
+int main() { return __sync_bool_compare_and_swap (&i, 0, 1); }
+
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+ libgo_cv_func___sync_bool_compare_and_swap_8=yes
+else
+ libgo_cv_func___sync_bool_compare_and_swap_8=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+ conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $libgo_cv_func___sync_bool_compare_and_swap_8" >&5
+$as_echo "$libgo_cv_func___sync_bool_compare_and_swap_8" >&6; }
+if test "$libgo_cv_func___sync_bool_compare_and_swap_8" = "yes"; then
+
+$as_echo "#define HAVE_SYNC_BOOL_COMPARE_AND_SWAP_8 1" >>confdefs.h
+
+fi
+
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for __sync_fetch_and_add_4" >&5
$as_echo_n "checking for __sync_fetch_and_add_4... " >&6; }
if test "${libgo_cv_func___sync_fetch_and_add_4+set}" = set; then :
@@ -14696,6 +14725,35 @@ $as_echo "#define HAVE_SYNC_FETCH_AND_ADD_4 1" >>confdefs.h
fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for __sync_add_and_fetch_8" >&5
+$as_echo_n "checking for __sync_add_and_fetch_8... " >&6; }
+if test "${libgo_cv_func___sync_add_and_fetch_8+set}" = set; then :
+ $as_echo_n "(cached) " >&6
+else
+ cat confdefs.h - <<_ACEOF >conftest.$ac_ext
+/* end confdefs.h. */
+
+typedef unsigned int uint64 __attribute__ ((mode (DI)));
+uint64 i;
+int main() { return __sync_add_and_fetch (&i, 1); }
+
+_ACEOF
+if ac_fn_c_try_link "$LINENO"; then :
+ libgo_cv_func___sync_add_and_fetch_8=yes
+else
+ libgo_cv_func___sync_add_and_fetch_8=no
+fi
+rm -f core conftest.err conftest.$ac_objext \
+ conftest$ac_exeext conftest.$ac_ext
+fi
+{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $libgo_cv_func___sync_add_and_fetch_8" >&5
+$as_echo "$libgo_cv_func___sync_add_and_fetch_8" >&6; }
+if test "$libgo_cv_func___sync_add_and_fetch_8" = "yes"; then
+
+$as_echo "#define HAVE_SYNC_ADD_AND_FETCH_8 1" >>confdefs.h
+
+fi
+
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether compiler supports -minline-all-stringops" >&5
$as_echo_n "checking whether compiler supports -minline-all-stringops... " >&6; }
if test "${libgo_cv_c_stringops+set}" = set; then :
diff --git a/libgo/configure.ac b/libgo/configure.ac
index 9c8478d..c3c1f5e 100644
--- a/libgo/configure.ac
+++ b/libgo/configure.ac
@@ -497,6 +497,20 @@ if test "$libgo_cv_func___sync_bool_compare_and_swap_4" = "yes"; then
[Define to 1 if the compiler provides the __sync_bool_compare_and_swap function for uint32])
fi
+AC_CACHE_CHECK([for __sync_bool_compare_and_swap_8],
+[libgo_cv_func___sync_bool_compare_and_swap_8],
+[AC_LINK_IFELSE([
+typedef unsigned int uint64 __attribute__ ((mode (DI)));
+uint64 i;
+int main() { return __sync_bool_compare_and_swap (&i, 0, 1); }
+],
+[libgo_cv_func___sync_bool_compare_and_swap_8=yes],
+[libgo_cv_func___sync_bool_compare_and_swap_8=no])])
+if test "$libgo_cv_func___sync_bool_compare_and_swap_8" = "yes"; then
+ AC_DEFINE(HAVE_SYNC_BOOL_COMPARE_AND_SWAP_8, 1,
+ [Define to 1 if the compiler provides the __sync_bool_compare_and_swap function for uint64])
+fi
+
AC_CACHE_CHECK([for __sync_fetch_and_add_4],
[libgo_cv_func___sync_fetch_and_add_4],
[AC_LINK_IFELSE([
@@ -511,6 +525,20 @@ if test "$libgo_cv_func___sync_fetch_and_add_4" = "yes"; then
[Define to 1 if the compiler provides the __sync_fetch_and_add function for uint32])
fi
+AC_CACHE_CHECK([for __sync_add_and_fetch_8],
+[libgo_cv_func___sync_add_and_fetch_8],
+[AC_LINK_IFELSE([
+typedef unsigned int uint64 __attribute__ ((mode (DI)));
+uint64 i;
+int main() { return __sync_add_and_fetch (&i, 1); }
+],
+[libgo_cv_func___sync_add_and_fetch_8=yes],
+[libgo_cv_func___sync_add_and_fetch_8=no])])
+if test "$libgo_cv_func___sync_add_and_fetch_8" = "yes"; then
+ AC_DEFINE(HAVE_SYNC_ADD_AND_FETCH_8, 1,
+ [Define to 1 if the compiler provides the __sync_add_and_fetch function for uint64])
+fi
+
dnl For x86 we want to use the -minline-all-stringops option to avoid
dnl forcing a stack split when calling memcpy and friends.
AC_CACHE_CHECK([whether compiler supports -minline-all-stringops],
diff --git a/libgo/runtime/thread.c b/libgo/runtime/thread.c
index d43e224..748a62d5 100644
--- a/libgo/runtime/thread.c
+++ b/libgo/runtime/thread.c
@@ -11,7 +11,7 @@
/* For targets which don't have the required sync support. Really
these should be provided by gcc itself. FIXME. */
-#if !defined (HAVE_SYNC_BOOL_COMPARE_AND_SWAP_4) || !defined (HAVE_SYNC_FETCH_AND_ADD_4)
+#if !defined (HAVE_SYNC_BOOL_COMPARE_AND_SWAP_4) || !defined (HAVE_SYNC_BOOL_COMPARE_AND_SWAP_8) || !defined (HAVE_SYNC_FETCH_AND_ADD_4) || !defined (HAVE_SYNC_ADD_AND_FETCH_8)
static pthread_mutex_t sync_lock = PTHREAD_MUTEX_INITIALIZER;
@@ -48,6 +48,37 @@ __sync_bool_compare_and_swap_4 (uint32* ptr, uint32 old, uint32 new)
#endif
+#ifndef HAVE_SYNC_BOOL_COMPARE_AND_SWAP_8
+
+_Bool
+__sync_bool_compare_and_swap_8 (uint64*, uint64, uint64)
+ __attribute__ ((visibility ("hidden")));
+
+_Bool
+__sync_bool_compare_and_swap_8 (uint64* ptr, uint64 old, uint64 new)
+{
+ int i;
+ _Bool ret;
+
+ i = pthread_mutex_lock (&sync_lock);
+ __go_assert (i == 0);
+
+ if (*ptr != old)
+ ret = 0;
+ else
+ {
+ *ptr = new;
+ ret = 1;
+ }
+
+ i = pthread_mutex_unlock (&sync_lock);
+ __go_assert (i == 0);
+
+ return ret;
+}
+
+#endif
+
#ifndef HAVE_SYNC_FETCH_AND_ADD_4
uint32
@@ -74,6 +105,32 @@ __sync_fetch_and_add_4 (uint32* ptr, uint32 add)
#endif
+#ifndef HAVE_SYNC_ADD_AND_FETCH_8
+
+uint64
+__sync_add_and_fetch_8 (uint64*, uint64)
+ __attribute__ ((visibility ("hidden")));
+
+uint64
+__sync_add_and_fetch_8 (uint64* ptr, uint64 add)
+{
+ int i;
+ uint64 ret;
+
+ i = pthread_mutex_lock (&sync_lock);
+ __go_assert (i == 0);
+
+ *ptr += add;
+ ret = *ptr;
+
+ i = pthread_mutex_unlock (&sync_lock);
+ __go_assert (i == 0);
+
+ return ret;
+}
+
+#endif
+
// Called to initialize a new m (including the bootstrap m).
void
runtime_minit(void)