configure: redo pthread check to check for more things
authorSimon McVittie <simon.mcvittie@collabora.co.uk>
Mon, 13 Aug 2012 18:43:12 +0000 (19:43 +0100)
committerSimon McVittie <simon.mcvittie@collabora.co.uk>
Mon, 19 Nov 2012 15:13:42 +0000 (15:13 +0000)
In principle, anything in the pthread namespace might either be in the
platform-specific thread library (libpthread or libpthreads or libthreads
or ...), or in libc.

In particular, it seems that pthread_mutexattr_init and
pthread_mutexattr_settype are in libpthread, not libc, on Linux. We
previously didn't (intentionally) look for them in libpthread, only
in libc; so this check deserved to fail.

However, a faulty configure check for pthread_cond_timedwait
worked around this on Linux by checking for -lpthread and adding it
to THREAD_LIBS if pthread_cond_timedwait *was* found in libc (even
though that behaviour makes no sense).

The practical impact was that D-Bus would fail to compile on platforms
where pthread_cond_timedwait is in a special threading library that
is not linked by default, and at least one of
(pthread_mutexattr_init, pthread_mutexattr_settype) is also in a
special threading library. This is the case on at least OpenBSD
(fd.o #54416).

So far I've only added checks for the new symbols introduced by
using recursive pthreads mutexes. If we get reports of compilation
failures on weird platforms, we can check for more symbols.

Also clarify the indentation, which was turning into quite a mess,
and use AS_IF instead of if/elif/else/fi in accordance with Autoconf
best-practice.

Bug: https://bugs.freedesktop.org/show_bug.cgi?id=47239
Reviewed-by: Colin Walters <walters@verbum.org>
configure.ac

index b0f2ec2..1c8b705 100644 (file)
@@ -952,15 +952,53 @@ AC_SUBST([XML_CFLAGS])
 AC_SUBST([XML_LIBS])
 
 # Thread lib detection
-AC_CHECK_FUNC(pthread_cond_timedwait,[AC_CHECK_LIB(pthread,pthread_cond_timedwait,
-                                                    [THREAD_LIBS="-lpthread"])])
+AC_ARG_VAR([THREAD_LIBS])
 save_libs="$LIBS"
 LIBS="$LIBS $THREAD_LIBS"
-AC_CHECK_FUNC(pthread_condattr_setclock,have_pthread_condattr_setclock=true,have_pthread_condattr_setclock=false)
-if test x$have_pthread_condattr_setclock = xtrue; then
-    AC_SEARCH_LIBS([clock_getres],[rt],[THREAD_LIBS="$THREAD_LIBS -lrt"])
-    AC_MSG_CHECKING([for CLOCK_MONOTONIC])
-    AC_COMPILE_IFELSE([AC_LANG_PROGRAM([[#include <time.h>
+
+is_missing_pthread_function="is required when compiling D-Bus on Unix platforms, but is not in your libc or libpthread. Please open a bug on https://bugs.freedesktop.org/enter_bug.cgi?product=dbus with details of your platform."
+
+# Don't do these automatic checks if the user set THREAD_LIBS on the
+# configure command-line. If they did, we assume they're right.
+#
+# We also don't do these checks on Windows, because you don't need magical
+# linker flags to have threading support there.
+AS_IF([test "x$dbus_unix" = xyes && test "x$THREAD_LIBS" = x],
+  [
+    # Mandatory pthread functions. In principle, some of these could be made
+    # optional if there are platforms that don't have them.
+    #
+    # Currently, we only look in -lpthread.
+    # In principle we might need to look in -lpthreads, -lthreads, ...
+    # as well - please file a bug if your platform needs this.
+    AC_SEARCH_LIBS([pthread_cond_timedwait],
+        [pthread],
+        [THREAD_LIBS="$LIBS"],
+        [AC_MSG_ERROR([pthread_cond_timedwait $is_missing_pthread_function])],
+        [])
+    AC_SEARCH_LIBS([pthread_mutexattr_init],
+        [pthread],
+        [THREAD_LIBS="$LIBS"],
+        [AC_MSG_ERROR([pthread_mutexattr_init $is_missing_pthread_function])],
+        [])
+    AC_SEARCH_LIBS([pthread_mutexattr_settype],
+        [pthread],
+        [THREAD_LIBS="$LIBS"],
+        [AC_MSG_ERROR([pthread_mutexattr_settype $is_missing_pthread_function])],
+        [])
+
+    # Optional, for monotonic clocks. Because it's optional, this check
+    # is non-fatal if we don't find it.
+    AC_SEARCH_LIBS([pthread_condattr_setclock],
+        [pthread],
+        [THREAD_LIBS="$LIBS"])
+
+    AS_IF([test "x$ac_cv_search_pthread_condattr_setclock" != xno],
+      [
+        AC_SEARCH_LIBS([clock_getres], [rt], [THREAD_LIBS="$LIBS"])
+        AC_MSG_CHECKING([for CLOCK_MONOTONIC])
+        AC_COMPILE_IFELSE([AC_LANG_PROGRAM(
+[[#include <time.h>
 #include <pthread.h>
 ]], [[
 struct timespec monotonic_timer;
@@ -969,15 +1007,17 @@ pthread_condattr_init (&attr);
 pthread_condattr_setclock (&attr, CLOCK_MONOTONIC);
 clock_getres (CLOCK_MONOTONIC,&monotonic_timer);
 ]])],
-[have_clock_monotonic=true],
-[have_clock_monotonic=false])
-if test x$have_clock_monotonic = xtrue; then
-    AC_MSG_RESULT([found])
-    AC_DEFINE(HAVE_MONOTONIC_CLOCK, 1, [Define if we have CLOCK_MONOTONIC])
-else
-    AC_MSG_RESULT([not found])
-fi
-fi
+            [have_clock_monotonic=true],
+            [have_clock_monotonic=false])
+        AS_IF([test x$have_clock_monotonic = xtrue],
+         [
+            AC_MSG_RESULT([found])
+            AC_DEFINE(HAVE_MONOTONIC_CLOCK, 1, [Define if we have CLOCK_MONOTONIC])
+         ],
+          [AC_MSG_RESULT([not found])])
+      ]) dnl have pthread_condattr_setclock
+  ]) dnl on Unix
+
 LIBS="$save_libs"
 
 AC_SUBST([THREAD_LIBS])