gthread: Use pthread_cond_timedwait_monotonic() if available
authorSebastian Dröge <slomo@circular-chaos.org>
Thu, 4 Jul 2013 08:27:02 +0000 (10:27 +0200)
committerSebastian Dröge <slomo@circular-chaos.org>
Thu, 4 Jul 2013 08:41:59 +0000 (10:41 +0200)
Otherwise we have to rely on pthread_cond_timedwait() actually using
the monotonic clock, which might be true or not. On Android at least
it is using the realtime clock, no pthread_condattr_setclock() is available
but instead pthread_cond_timedwait_monotonic() can be used.

configure.ac
glib/gthread-posix.c

index 1fba2da..9bfc3d8 100644 (file)
@@ -2383,6 +2383,24 @@ AS_IF([ test x"$have_threads" = xposix], [
              AC_DEFINE(HAVE_PTHREAD_CONDATTR_SETCLOCK,1,
                 [Have function pthread_condattr_setclock])],
             [AC_MSG_RESULT(no)])
+        AC_MSG_CHECKING(for pthread_cond_timedwait_monotonic)
+        AC_LINK_IFELSE(
+            [AC_LANG_PROGRAM(
+                [#include <pthread.h>],
+                [pthread_cond_timedwait_monotonic(NULL, NULL, NULL)])],
+            [AC_MSG_RESULT(yes)
+             AC_DEFINE(HAVE_PTHREAD_COND_TIMEDWAIT_MONOTONIC,1,
+                [Have function pthread_cond_timedwait_monotonic])],
+            [AC_MSG_RESULT(no)])
+        AC_MSG_CHECKING(for pthread_cond_timedwait_monotonic_np)
+        AC_LINK_IFELSE(
+            [AC_LANG_PROGRAM(
+                [#include <pthread.h>],
+                [pthread_cond_timedwait_monotonic_np(NULL, NULL, NULL)])],
+            [AC_MSG_RESULT(yes)
+             AC_DEFINE(HAVE_PTHREAD_COND_TIMEDWAIT_MONOTONIC_NP,1,
+                [Have function pthread_cond_timedwait_monotonic_np])],
+            [AC_MSG_RESULT(no)])
         CPPFLAGS="$glib_save_CPPFLAGS"
 ])
 
index 23371ae..c7b68a0 100644 (file)
@@ -859,8 +859,17 @@ g_cond_wait_until (GCond  *cond,
   ts.tv_sec = end_time / 1000000;
   ts.tv_nsec = (end_time % 1000000) * 1000;
 
+#if defined(HAVE_PTHREAD_COND_TIMEDWAIT_MONOTONIC)
+  if ((status = pthread_cond_timedwait_monotonic (g_cond_get_impl (cond), g_mutex_get_impl (mutex), &ts)) == 0)
+    return TRUE;
+#elif defined(HAVE_PTHREAD_COND_TIMEDWAIT_MONOTONIC_NP)
+  if ((status = pthread_cond_timedwait_monotonic_np (g_cond_get_impl (cond), g_mutex_get_impl (mutex), &ts)) == 0)
+    return TRUE;
+#else
+  /* Pray that the cond is actually using the monotonic clock */
   if ((status = pthread_cond_timedwait (g_cond_get_impl (cond), g_mutex_get_impl (mutex), &ts)) == 0)
     return TRUE;
+#endif
 
   if G_UNLIKELY (status != ETIMEDOUT)
     g_thread_abort (status, "pthread_cond_timedwait");