CCurrently on GNU/Hurd the timer_* functions are not implemented;
check's configure detects that and switches to the replacements
functions in lib/, which use alarm for the timer. However, using
alarm does not allow a timeout precision more than 1 second (as also
written in the comments in lib/timer_settime.c), causing the failure
of the two tests check_check_export and check_check.
As a workaround, it is possible to get a better precision using the
POSIX function setitimer [1] (declared obsolescent, but still usable)
instead of alarm.
This change checks for the existence of setitimer, and in case it
exists uses it (with its ITIMER_REAL timer) in the replacement
timer_settime and timer_delete. Given they are implemented in the
Hurd, all the tests of check passes.
[1] http://pubs.opengroup.org/onlinepubs/
9699919799/functions/getitimer.html
Patch submitted by Pino Toscano, patch#49
git-svn-id: svn+ssh://svn.code.sf.net/p/check/code/trunk@759
64e312b2-a51f-0410-8e61-
82d0ca0eb02a
Sebastian Rasmussen (duration bug fix, 64-bit API fix)
Martin Willers (rename check's internal list API to start with check_)
bross (patches for msys/mingw32 support)
+ Pino Toscano (GNU/Hurd support for subsecond timeouts)
Anybody who has contributed code to Check or Check's build system is
considered an author. Send patches to this file to
* Check compiles for the Windows using x86_64-w64-mingw32.
+* On systems without timer_settimer, use setitimer (if available) to get
+ subsecond unit test timeouts. If setitimer is unavailable, fallback
+ on alarm.
+
Thu, Apr 18, 2013: Released Check 0.9.10
based on r743 (2013-04-18 11:27:03 +0200)
AC_REPLACE_FUNCS([alarm clock_gettime timer_create timer_settime timer_delete fileno localtime_r pipe putenv setenv sleep strdup strsignal unsetenv])
AC_CHECK_DECLS([alarm, clock_gettime, timer_create, timer_settime, timer_delete, fileno, localtime_r, pipe, putenv, setenv, sleep, strdup, strsignal, unsetenv])
+AC_CHECK_FUNCS([setitimer])
+
# Check if the system's snprintf (and its variations) are C99 compliant.
# If they are not, use the version in libcompat.
HW_FUNC_VSNPRINTF
int timer_delete(timer_t timerid CK_ATTRIBUTE_UNUSED)
{
+#ifdef HAVE_SETITIMER
+ /*
+ * If the system does not have timer_settime() but does have
+ * setitimer() use that instead of alarm().
+ */
+ struct itimerval new;
+
+ /*
+ * Setting values to '0' results in disabling the running timer.
+ */
+ new.it_value.tv_sec = 0;
+ new.it_value.tv_usec = 0;
+ new.it_interval.tv_sec = 0;
+ new.it_interval.tv_usec = 0;
+
+ return setitimer(ITIMER_REAL, &new, NULL);
+#else
/*
* There is only one timer, that used by alarm.
* Setting alarm(0) will not set a new alarm, and
alarm(0);
return 0;
+#endif
}
const struct itimerspec *new_value,
struct itimerspec * old_value CK_ATTRIBUTE_UNUSED)
{
+#ifdef HAVE_SETITIMER
+ /*
+ * If the system does not have timer_settime() but does have
+ * setitimer() use that instead of alarm().
+ */
+ struct itimerval new;
+
+ new.it_value.tv_sec = new_value->it_value.tv_sec;
+ new.it_value.tv_usec = new_value->it_value.tv_nsec / 1000;
+ new.it_interval.tv_sec = new_value->it_interval.tv_sec;
+ new.it_interval.tv_usec = new_value->it_interval.tv_nsec / 1000;
+
+ return setitimer(ITIMER_REAL, &new, NULL);
+#else
int seconds = new_value->it_value.tv_sec;
/*
alarm(seconds);
return 0;
+#endif
}