1 dnl Check whether the target supports TLS. 2 AC_DEFUN([GCC_CHECK_TLS], [ 3 AC_REQUIRE([AC_CANONICAL_HOST]) 4 GCC_ENABLE(tls, yes, [], [Use thread-local storage]) 5 AC_CACHE_CHECK([whether the target supports thread-local storage], 6 gcc_cv_have_tls, [ 7 AC_RUN_IFELSE([__thread int a; int b; int main() { return a = b; }], 8 [dnl If the test case passed with dynamic linking, try again with 9 dnl static linking, but only if static linking is supported (not 10 dnl on Solaris 10). This fails with some older Red Hat releases. 11 chktls_save_LDFLAGS="$LDFLAGS" 12 LDFLAGS="-static $LDFLAGS" 13 AC_LINK_IFELSE([int main() { return 0; }], 14 [AC_RUN_IFELSE([__thread int a; int b; int main() { return a = b; }], 15 [gcc_cv_have_tls=yes], [gcc_cv_have_tls=no],[])], 16 [gcc_cv_have_tls=yes]) 17 LDFLAGS="$chktls_save_LDFLAGS" 18 if test $gcc_cv_have_tls = yes; then 19 dnl So far, the binutils and the compiler support TLS. 20 dnl Also check whether the libc supports TLS, i.e. whether a variable 21 dnl with __thread linkage has a different address in different threads. 22 dnl First, find the thread_CFLAGS necessary for linking a program that 23 dnl calls pthread_create. 24 chktls_save_CFLAGS="$CFLAGS" 25 thread_CFLAGS=failed 26 for flag in '' '-pthread' '-lpthread'; do 27 CFLAGS="$flag $chktls_save_CFLAGS" 28 AC_LINK_IFELSE( 29 [AC_LANG_PROGRAM( 30 [#include <pthread.h> 31 void *g(void *d) { return NULL; }], 32 [pthread_t t; pthread_create(&t,NULL,g,NULL);])], 33 [thread_CFLAGS="$flag"]) 34 if test "X$thread_CFLAGS" != Xfailed; then 35 break 36 fi 37 done 38 CFLAGS="$chktls_save_CFLAGS" 39 if test "X$thread_CFLAGS" != Xfailed; then 40 CFLAGS="$thread_CFLAGS $chktls_save_CFLAGS" 41 dnl Test for an old glibc bug that violated the __thread property. 42 dnl Use volatile to ensure the compiler won't optimize away pointer 43 dnl accesses it might otherwise assume to be redundant, or reorder 44 dnl them and reuse storage, which might lead to them pointing to 45 dnl the same location. 46 AC_RUN_IFELSE( 47 [AC_LANG_PROGRAM( 48 [#include <pthread.h> 49 __thread int a; 50 static int *volatile a_in_other_thread; 51 static void * 52 thread_func (void *arg) 53 { 54 a_in_other_thread = &a; 55 return (void *)0; 56 }], 57 [pthread_t thread; 58 void *thread_retval; 59 int *volatile a_in_main_thread; 60 a_in_main_thread = &a; 61 if (pthread_create (&thread, (pthread_attr_t *)0, 62 thread_func, (void *)0)) 63 return 0; 64 if (pthread_join (thread, &thread_retval)) 65 return 0; 66 return (a_in_other_thread == a_in_main_thread);])], 67 [gcc_cv_have_tls=yes], [gcc_cv_have_tls=no], []) 68 CFLAGS="$chktls_save_CFLAGS" 69 fi 70 fi], 71 [gcc_cv_have_tls=no], 72 [dnl This is the cross-compiling case. Assume libc supports TLS if the 73 dnl binutils and the compiler do. 74 AC_LINK_IFELSE([__thread int a; int b; int main() { return a = b; }], 75 [chktls_save_LDFLAGS="$LDFLAGS" 76 dnl Shared library options may depend on the host; this check 77 dnl is only known to be needed for GNU/Linux. 78 case $host in 79 *-*-linux*) 80 LDFLAGS="-shared -Wl,--no-undefined $LDFLAGS" 81 ;; 82 esac 83 chktls_save_CFLAGS="$CFLAGS" 84 CFLAGS="-fPIC $CFLAGS" 85 dnl If -shared works, test if TLS works in a shared library. 86 AC_LINK_IFELSE([int f() { return 0; }], 87 [AC_LINK_IFELSE([__thread int a; int b; int f() { return a = b; }], 88 [gcc_cv_have_tls=yes], 89 [gcc_cv_have_tls=no])], 90 [gcc_cv_have_tls=yes]) 91 CFLAGS="$chktls_save_CFLAGS" 92 LDFLAGS="$chktls_save_LDFLAGS"], [gcc_cv_have_tls=no]) 93 ] 94 )]) 95 if test "$enable_tls $gcc_cv_have_tls" = "yes yes"; then 96 AC_DEFINE(HAVE_TLS, 1, 97 [Define to 1 if the target supports thread-local storage.]) 98 fi]) 99 100 dnl Check whether the target assembler supports TLS. 101 AC_DEFUN([GCC_CHECK_CC_TLS], [ 102 GCC_ENABLE(tls, yes, [], [Use thread-local storage]) 103 AC_CACHE_CHECK([whether the target assembler supports thread-local storage], 104 gcc_cv_have_cc_tls, [ 105 AC_COMPILE_IFELSE([__thread int a; int b; int main() { return a = b; }], 106 [gcc_cv_have_cc_tls=yes], [gcc_cv_have_cc_tls=no])] 107 )]) 108 if test "$enable_tls $gcc_cv_have_cc_tls" = "yes yes"; then 109 AC_DEFINE(HAVE_CC_TLS, 1, 110 [Define to 1 if the target assembler supports thread-local storage.]) 111 fi]) 112 113 dnl Check whether TLS is emulated. 114 AC_DEFUN([GCC_CHECK_EMUTLS], [ 115 AC_CACHE_CHECK([whether the thread-local storage support is from emutls], 116 gcc_cv_use_emutls, [ 117 gcc_cv_use_emutls=no 118 echo '__thread int a; int b; int main() { return a = b; }' > conftest.c 119 if AC_TRY_COMMAND(${CC-cc} -Werror -S -o conftest.s conftest.c 1>&AS_MESSAGE_LOG_FD); then 120 if grep __emutls_get_address conftest.s > /dev/null; then 121 gcc_cv_use_emutls=yes 122 fi 123 fi 124 rm -f conftest.* 125 ]) 126 if test "$gcc_cv_use_emutls" = "yes" ; then 127 AC_DEFINE(USE_EMUTLS, 1, 128 [Define to 1 if the target use emutls for thread-local storage.]) 129 fi]) 130