diff options
Diffstat (limited to 'erts/aclocal.m4')
-rw-r--r-- | erts/aclocal.m4 | 361 |
1 files changed, 326 insertions, 35 deletions
diff --git a/erts/aclocal.m4 b/erts/aclocal.m4 index 3d935b7295..443d8622bf 100644 --- a/erts/aclocal.m4 +++ b/erts/aclocal.m4 @@ -386,14 +386,24 @@ AC_DEFUN(LM_SYS_IPV6, AC_CACHE_VAL(ac_cv_sys_ipv6_support, [ok_so_far=yes AC_TRY_COMPILE([#include <sys/types.h> -#include <netinet/in.h>], +#ifdef __WIN32__ +#include <winsock2.h> +#include <ws2tcpip.h> +#else +#include <netinet/in.h> +#endif], [struct in6_addr a6; struct sockaddr_in6 s6;], ok_so_far=yes, ok_so_far=no) if test $ok_so_far = yes; then ac_cv_sys_ipv6_support=yes else AC_TRY_COMPILE([#include <sys/types.h> -#include <netinet/in.h>], +#ifdef __WIN32__ +#include <winsock2.h> +#include <ws2tcpip.h> +#else +#include <netinet/in.h> +#endif], [struct in_addr6 a6; struct sockaddr_in6 s6;], ac_cv_sys_ipv6_support=in_addr6, ac_cv_sys_ipv6_support=no) fi @@ -512,6 +522,8 @@ dnl AC_DEFUN(LM_CHECK_THR_LIB, [ +NEED_NPTL_PTHREAD_H=no + dnl win32? AC_MSG_CHECKING([for native win32 threads]) if test "X$host_os" = "Xwin32"; then @@ -519,11 +531,13 @@ if test "X$host_os" = "Xwin32"; then THR_DEFS="-DWIN32_THREADS" THR_LIBS= THR_LIB_NAME=win32_threads + THR_LIB_TYPE=win32_threads else AC_MSG_RESULT(no) THR_DEFS= THR_LIBS= THR_LIB_NAME= + THR_LIB_TYPE=posix_unknown dnl Try to find POSIX threads @@ -584,8 +598,11 @@ dnl On ofs1 the '-pthread' switch should be used AC_MSG_WARN([result yes guessed because of cross compilation]) fi if test $nptl = yes; then + THR_LIB_TYPE=posix_nptl need_nptl_incldir=no - AC_CHECK_HEADER(nptl/pthread.h, need_nptl_incldir=yes) + AC_CHECK_HEADER(nptl/pthread.h, + [need_nptl_incldir=yes + NEED_NPTL_PTHREAD_H=yes]) if test $need_nptl_incldir = yes; then # Ahh... nptl_path="$C_INCLUDE_PATH:$CPATH" @@ -649,6 +666,19 @@ fi ]) +AC_DEFUN(ERL_INTERNAL_LIBS, +[ + +ERTS_INTERNAL_X_LIBS= + +AC_CHECK_LIB(kstat, kstat_open, +[AC_DEFINE(HAVE_KSTAT, 1, [Define if you have kstat]) +ERTS_INTERNAL_X_LIBS="$ERTS_INTERNAL_X_LIBS -lkstat"]) + +AC_SUBST(ERTS_INTERNAL_X_LIBS) + +]) + dnl ---------------------------------------------------------------------- dnl dnl ERL_FIND_ETHR_LIB @@ -672,10 +702,14 @@ AC_DEFUN(ERL_FIND_ETHR_LIB, [ LM_CHECK_THR_LIB +ERL_INTERNAL_LIBS +ethr_have_native_atomics=no +ethr_have_native_spinlock=no ETHR_THR_LIB_BASE="$THR_LIB_NAME" +ETHR_THR_LIB_BASE_TYPE="$THR_LIB_TYPE" ETHR_DEFS="$THR_DEFS" -ETHR_X_LIBS="$THR_LIBS" +ETHR_X_LIBS="$THR_LIBS $ERTS_INTERNAL_X_LIBS" ETHR_LIBS= ETHR_LIB_NAME= @@ -687,6 +721,7 @@ ethr_lib_name=ethread case "$THR_LIB_NAME" in win32_threads) + ETHR_THR_LIB_BASE_DIR=win # * _WIN32_WINNT >= 0x0400 is needed for # TryEnterCriticalSection # * _WIN32_WINNT >= 0x0403 is needed for @@ -712,10 +747,13 @@ case "$THR_LIB_NAME" in if test $found_win32_winnt = no; then AC_MSG_ERROR([-D_WIN32_WINNT missing in CPPFLAGS]) fi + ethr_have_native_atomics=yes + ethr_have_native_spinlock=yes AC_DEFINE(ETHR_WIN32_THREADS, 1, [Define if you have win32 threads]) ;; pthread) + ETHR_THR_LIB_BASE_DIR=pthread AC_DEFINE(ETHR_PTHREADS, 1, [Define if you have pthreads]) case $host_os in openbsd*) @@ -771,9 +809,7 @@ case "$THR_LIB_NAME" in if test $usable_sigaltstack = no; then ETHR_DEFS="$ETHR_DEFS -DETHR_UNUSABLE_SIGALTSTACK" fi - - AC_DEFINE(ETHR_INIT_MUTEX_IN_CHILD_AT_FORK, 1, \ -[Define if mutexes should be reinitialized (instead of unlocked) in child at fork.]) ;; + ;; *) ;; esac @@ -799,6 +835,15 @@ case "$THR_LIB_NAME" in AC_DEFINE(ETHR_HAVE_MIT_PTHREAD_H, 1, \ [Define if the pthread.h header file is in pthread/mit directory.])) + if test $NEED_NPTL_PTHREAD_H = yes; then + AC_DEFINE(ETHR_NEED_NPTL_PTHREAD_H, 1, \ +[Define if you need the <nptl/pthread.h> header file.]) + fi + + AC_CHECK_HEADER(sched.h, \ + AC_DEFINE(ETHR_HAVE_SCHED_H, 1, \ +[Define if you have the <sched.h> header file.])) + AC_CHECK_HEADER(sys/time.h, \ AC_DEFINE(ETHR_HAVE_SYS_TIME_H, 1, \ [Define if you have the <sys/time.h> header file.])) @@ -814,39 +859,212 @@ case "$THR_LIB_NAME" in dnl Check for functions dnl - AC_CHECK_FUNC(pthread_atfork, \ - AC_DEFINE(ETHR_HAVE_PTHREAD_ATFORK, 1, \ -[Define if you have the pthread_atfork function.])) - AC_CHECK_FUNC(pthread_mutexattr_settype, \ - AC_DEFINE(ETHR_HAVE_PTHREAD_MUTEXATTR_SETTYPE, 1, \ -[Define if you have the pthread_mutexattr_settype function.])) - AC_CHECK_FUNC(pthread_mutexattr_setkind_np, \ - AC_DEFINE(ETHR_HAVE_PTHREAD_MUTEXATTR_SETKIND_NP, 1, \ -[Define if you have the pthread_mutexattr_setkind_np function.])) AC_CHECK_FUNC(pthread_spin_lock, \ - AC_DEFINE(ETHR_HAVE_PTHREAD_SPIN_LOCK, 1, \ -[Define if you have the pthread_spin_lock function.])) - test "$force_linux_pthread_rwlocks" = "yes" || { - force_linux_pthread_rwlocks=no - } - case "$force_linux_pthread_rwlocks-$host_os" in - no-linux*) # Writers may get starved - # TODO: write a test that tests the implementation - ;; - *) - AC_CHECK_FUNC(pthread_rwlock_init, \ - AC_DEFINE(ETHR_HAVE_PTHREAD_RWLOCK_INIT, 1, \ -[Define if you have a pthread_rwlock implementation that can be used.])) - ;; - esac + [ethr_have_native_spinlock=yes \ + AC_DEFINE(ETHR_HAVE_PTHREAD_SPIN_LOCK, 1, \ +[Define if you have the pthread_spin_lock function.])]) + + have_sched_yield=no + have_librt_sched_yield=no + AC_CHECK_FUNC(sched_yield, [have_sched_yield=yes]) + if test $have_sched_yield = no; then + AC_CHECK_LIB(rt, sched_yield, + [have_librt_sched_yield=yes + ETHR_X_LIBS="$ETHR_X_LIBS -lrt"]) + fi + if test $have_sched_yield = yes || test $have_librt_sched_yield = yes; then + AC_DEFINE(ETHR_HAVE_SCHED_YIELD, 1, [Define if you have the sched_yield() function.]) + AC_MSG_CHECKING([whether sched_yield() returns an int]) + sched_yield_ret_int=no + AC_TRY_COMPILE([ + #ifdef ETHR_HAVE_SCHED_H + #include <sched.h> + #endif + ], + [int sched_yield();], + [sched_yield_ret_int=yes]) + AC_MSG_RESULT([$sched_yield_ret_int]) + if test $sched_yield_ret_int = yes; then + AC_DEFINE(ETHR_SCHED_YIELD_RET_INT, 1, [Define if sched_yield() returns an int.]) + fi + fi + + have_pthread_yield=no + AC_CHECK_FUNC(pthread_yield, [have_pthread_yield=yes]) + if test $have_pthread_yield = yes; then + AC_DEFINE(ETHR_HAVE_PTHREAD_YIELD, 1, [Define if you have the pthread_yield() function.]) + AC_MSG_CHECKING([whether pthread_yield() returns an int]) + pthread_yield_ret_int=no + AC_TRY_COMPILE([ + #if defined(ETHR_NEED_NPTL_PTHREAD_H) + #include <nptl/pthread.h> + #elif defined(ETHR_HAVE_MIT_PTHREAD_H) + #include <pthread/mit/pthread.h> + #elif defined(ETHR_HAVE_PTHREAD_H) + #include <pthread.h> + #endif + ], + [int pthread_yield();], + [pthread_yield_ret_int=yes]) + AC_MSG_RESULT([$pthread_yield_ret_int]) + if test $pthread_yield_ret_int = yes; then + AC_DEFINE(ETHR_PTHREAD_YIELD_RET_INT, 1, [Define if pthread_yield() returns an int.]) + fi + fi + + have_pthread_rwlock_init=no + AC_CHECK_FUNC(pthread_rwlock_init, [have_pthread_rwlock_init=yes]) + if test $have_pthread_rwlock_init = yes; then + + ethr_have_pthread_rwlockattr_setkind_np=no + AC_CHECK_FUNC(pthread_rwlockattr_setkind_np, + [ethr_have_pthread_rwlockattr_setkind_np=yes]) + + if test $ethr_have_pthread_rwlockattr_setkind_np = yes; then + AC_DEFINE(ETHR_HAVE_PTHREAD_RWLOCKATTR_SETKIND_NP, 1, \ +[Define if you have the pthread_rwlockattr_setkind_np() function.]) + + AC_MSG_CHECKING([for PTHREAD_RWLOCK_PREFER_WRITER_NONRECURSIVE_NP]) + ethr_pthread_rwlock_writer_nonrecursive_initializer_np=no + AC_TRY_LINK([ + #if defined(ETHR_NEED_NPTL_PTHREAD_H) + #include <nptl/pthread.h> + #elif defined(ETHR_HAVE_MIT_PTHREAD_H) + #include <pthread/mit/pthread.h> + #elif defined(ETHR_HAVE_PTHREAD_H) + #include <pthread.h> + #endif + ], + [ + pthread_rwlockattr_t *attr; + return pthread_rwlockattr_setkind_np(attr, + PTHREAD_RWLOCK_PREFER_WRITER_NONRECURSIVE_NP); + ], + [ethr_pthread_rwlock_writer_nonrecursive_initializer_np=yes]) + AC_MSG_RESULT([$ethr_pthread_rwlock_writer_nonrecursive_initializer_np]) + if test $ethr_pthread_rwlock_writer_nonrecursive_initializer_np = yes; then + AC_DEFINE(ETHR_HAVE_PTHREAD_RWLOCK_PREFER_WRITER_NONRECURSIVE_NP, 1, \ +[Define if you have the PTHREAD_RWLOCK_PREFER_WRITER_NONRECURSIVE_NP rwlock attribute.]) + fi + fi + fi + + if test "$force_pthread_rwlocks" = "yes"; then + + AC_DEFINE(ETHR_FORCE_PTHREAD_RWLOCK, 1, \ +[Define if you want to force usage of pthread rwlocks]) + + if test $have_pthread_rwlock_init = yes; then + AC_MSG_WARN([Forced usage of pthread rwlocks. Note that this implementation may suffer from starvation issues.]) + else + AC_MSG_ERROR([User forced usage of pthread rwlock, but no such implementation was found]) + fi + fi + AC_CHECK_FUNC(pthread_attr_setguardsize, \ AC_DEFINE(ETHR_HAVE_PTHREAD_ATTR_SETGUARDSIZE, 1, \ [Define if you have the pthread_attr_setguardsize function.])) + linux_futex=no + AC_MSG_CHECKING([for Linux futexes]) + AC_TRY_LINK([ + #include <sys/syscall.h> + #include <unistd.h> + #include <linux/futex.h> + #include <sys/time.h> + ], + [ + int i = 1; + syscall(__NR_futex, (void *) &i, FUTEX_WAKE, 1, + (void*)0,(void*)0, 0); + syscall(__NR_futex, (void *) &i, FUTEX_WAIT, 0, + (void*)0,(void*)0, 0); + return 0; + ], + linux_futex=yes) + AC_MSG_RESULT([$linux_futex]) + test $linux_futex = yes && AC_DEFINE(ETHR_HAVE_LINUX_FUTEX, 1, [Define if you have a linux futex implementation.]) + + AC_MSG_CHECKING([for GCC atomic operations]) + ethr_have_gcc_atomic_ops=no + AC_TRY_LINK([], + [ + long res; + volatile long val; + res = __sync_val_compare_and_swap(&val, (long) 1, (long) 0); + res = __sync_add_and_fetch(&val, (long) 1); + res = __sync_sub_and_fetch(&val, (long) 1); + res = __sync_fetch_and_and(&val, (long) 1); + res = __sync_fetch_and_or(&val, (long) 1); + ], + [ethr_have_native_atomics=yes + ethr_have_gcc_atomic_ops=yes]) + AC_MSG_RESULT([$ethr_have_gcc_atomic_ops]) + test $ethr_have_gcc_atomic_ops = yes && AC_DEFINE(ETHR_HAVE_GCC_ATOMIC_OPS, 1, [Define if you have gcc atomic operations]) + + case "$host_cpu" in + sun4u | sparc64 | sun4v) + ethr_have_native_atomics=yes;; + i86pc | i*86 | x86_64 | amd64) + ethr_have_native_atomics=yes;; + macppc | ppc | "Power Macintosh") + ethr_have_native_atomics=yes;; + tile) + ethr_have_native_atomics=yes;; + *) + ;; + esac + + AC_MSG_CHECKING([for a usable libatomic_ops implementation]) + case "x$with_libatomic_ops" in + xno | xyes | x) + libatomic_ops_include= + ;; + *) + if test -d "${with_libatomic_ops}/include"; then + libatomic_ops_include="-I$with_libatomic_ops/include" + CPPFLAGS="$CPPFLAGS $libatomic_ops_include" + else + AC_MSG_ERROR([libatomic_ops include directory $with_libatomic_ops/include not found]) + fi;; + esac + ethr_have_libatomic_ops=no + AC_TRY_LINK([#include "atomic_ops.h"], + [ + volatile AO_t x; + AO_t y; + int z; + + AO_nop_full(); + AO_store(&x, (AO_t) 0); + z = AO_load(&x); + z = AO_compare_and_swap(&x, (AO_t) 0, (AO_t) 1); + ], + [ethr_have_native_atomics=yes + ethr_have_libatomic_ops=yes]) + AC_MSG_RESULT([$ethr_have_libatomic_ops]) + if test $ethr_have_libatomic_ops = yes; then + AC_CHECK_SIZEOF(AO_t, , + [ + #include <stdio.h> + #include "atomic_ops.h" + ]) + AC_DEFINE_UNQUOTED(ETHR_SIZEOF_AO_T, $ac_cv_sizeof_AO_t, [Define to the size of AO_t if libatomic_ops is used]) + + AC_DEFINE(ETHR_HAVE_LIBATOMIC_OPS, 1, [Define if you have libatomic_ops atomic operations]) + if test "x$with_libatomic_ops" != "xno" && test "x$with_libatomic_ops" != "x"; then + AC_DEFINE(ETHR_PREFER_LIBATOMIC_OPS_NATIVE_IMPLS, 1, [Define if you prefer libatomic_ops native ethread implementations]) + fi + ETHR_DEFS="$ETHR_DEFS $libatomic_ops_include" + elif test "x$with_libatomic_ops" != "xno" && test "x$with_libatomic_ops" != "x"; then + AC_MSG_ERROR([No usable libatomic_ops implementation found]) + fi + dnl Restore LIBS LIBS=$saved_libs dnl restore CPPFLAGS CPPFLAGS=$saved_cppflags + ;; *) ;; @@ -862,16 +1080,88 @@ fi if test "x$ETHR_THR_LIB_BASE" != "x"; then ETHR_DEFS="-DUSE_THREADS $ETHR_DEFS" - ETHR_LIBS="-l$ethr_lib_name $ETHR_X_LIBS" + ETHR_LIBS="-l$ethr_lib_name -lerts_internal_r $ETHR_X_LIBS" ETHR_LIB_NAME=$ethr_lib_name fi AC_CHECK_SIZEOF(void *) AC_DEFINE_UNQUOTED(ETHR_SIZEOF_PTR, $ac_cv_sizeof_void_p, [Define to the size of pointers]) -if test "X$disable_native_ethr_impls" = "Xyes"; then - AC_DEFINE(ETHR_DISABLE_NATIVE_IMPLS, 1, [Define if you want to disable native ethread implementations]) -fi +AC_ARG_ENABLE(native-ethr-impls, + AS_HELP_STRING([--disable-native-ethr-impls], + [disable native ethread implementations]), +[ case "$enableval" in + no) disable_native_ethr_impls=yes ;; + *) disable_native_ethr_impls=no ;; + esac ], disable_native_ethr_impls=no) + +test "X$disable_native_ethr_impls" = "Xyes" && + AC_DEFINE(ETHR_DISABLE_NATIVE_IMPLS, 1, [Define if you want to disable native ethread implementations]) + +AC_ARG_ENABLE(prefer-gcc-native-ethr-impls, + AS_HELP_STRING([--enable-prefer-gcc-native-ethr-impls], + [prefer gcc native ethread implementations]), +[ case "$enableval" in + yes) enable_prefer_gcc_native_ethr_impls=yes ;; + *) enable_prefer_gcc_native_ethr_impls=no ;; + esac ], enable_prefer_gcc_native_ethr_impls=no) + +test $enable_prefer_gcc_native_ethr_impls = yes && + AC_DEFINE(ETHR_PREFER_GCC_NATIVE_IMPLS, 1, [Define if you prefer gcc native ethread implementations]) + +AC_ARG_WITH(libatomic_ops, + AS_HELP_STRING([--with-libatomic_ops=PATH], + [specify and prefer usage of libatomic_ops in the ethread library])) + +AC_ARG_ENABLE(ethread-pre-pentium4-compatibility, + AS_HELP_STRING([--enable-ethread-pre-pentium4-compatibility], + [enable compatibility with x86 processors before pentium 4 (back to 486) in the ethread library]), +[ + case "$enable_ethread_pre_pentium4_compatibility" in + yes|no) ;; + *) enable_ethread_pre_pentium4_compatibility=check;; + esac +], +[enable_ethread_pre_pentium4_compatibility=check]) + +test "$cross_compiling" != "yes" || enable_ethread_pre_pentium4_compatibility=no + +case "$enable_ethread_pre_pentium4_compatibility-$host_cpu" in + check-i86pc | check-i*86) + AC_MSG_CHECKING([whether pre pentium 4 compatibility should forced]) + AC_RUN_IFELSE([ +#if defined(__GNUC__) +# if defined(ETHR_PREFER_LIBATOMIC_OPS_NATIVE_IMPLS) +# define CHECK_LIBATOMIC_OPS__ +# else +# define CHECK_GCC_ASM__ +# endif +#elif defined(ETHR_HAVE_LIBATOMIC_OPS) +# define CHECK_LIBATOMIC_OPS__ +#endif +#if defined(CHECK_LIBATOMIC_OPS__) +#include "atomic_ops.h" +#endif +int main(void) +{ +#if defined(CHECK_GCC_ASM__) + __asm__ __volatile__("mfence" : : : "memory"); +#elif defined(CHECK_LIBATOMIC_OPS__) + AO_nop_full(); +#endif + return 0; +} + ], + [enable_ethread_pre_pentium4_compatibility=no], + [enable_ethread_pre_pentium4_compatibility=yes], + [enable_ethread_pre_pentium4_compatibility=no]) + AC_MSG_RESULT([$enable_ethread_pre_pentium4_compatibility]);; + *) + ;; +esac + +test $enable_ethread_pre_pentium4_compatibility = yes && + AC_DEFINE(ETHR_PRE_PENTIUM4_COMPAT, 1, [Define if you want compatibilty with x86 processors before pentium4.]) AC_DEFINE(ETHR_HAVE_ETHREAD_DEFINES, 1, \ [Define if you have all ethread defines]) @@ -881,6 +1171,7 @@ AC_SUBST(ETHR_LIBS) AC_SUBST(ETHR_LIB_NAME) AC_SUBST(ETHR_DEFS) AC_SUBST(ETHR_THR_LIB_BASE) +AC_SUBST(ETHR_THR_LIB_BASE_DIR) ]) |