Revert commit
26c5fd742f. Solaris lacks futimens and futimes, so
futimesat is the only way to change fd timestamps. But since
FreeBSD futimesat can't change fd timestamps, we need a configure
check to avoid the crash there.
* m4/utimens.m4 (gl_UTIMENS): Check for BSD bug.
* lib/utimens.c (fdutimens): Revert 2009-11-08 change; Solaris 10
can only change fd timestamps via futimesat. Instead, use an
additional witness macro to avoid BSD bug.
Reported by Jim Meyering.
Signed-off-by: Eric Blake <ebb9@byu.net>
+2009-11-18 Eric Blake <ebb9@byu.net>
+
+ utimens: fix regression on Solaris
+ * m4/utimens.m4 (gl_UTIMENS): Check for BSD bug.
+ * lib/utimens.c (fdutimens): Revert 2009-11-08 change; Solaris 10
+ can only change fd timestamps via futimesat. Instead, use an
+ additional witness macro to avoid BSD bug.
+ Reported by Jim Meyering.
+
2009-11-17 Eric Blake <ebb9@byu.net>
usleep: use it to simplify tests
}
else
{
- /* If futimesat (above) or futimes fails here, don't try to speed
- things up by returning right away. glibc can incorrectly fail
- with errno == ENOENT if /proc isn't mounted. Also, Mandrake 10.0
+ /* If futimesat or futimes fails here, don't try to speed things
+ up by returning right away. glibc can incorrectly fail with
+ errno == ENOENT if /proc isn't mounted. Also, Mandrake 10.0
in high security mode doesn't allow ordinary users to read
/proc/self, so glibc incorrectly fails with errno == EACCES.
If errno == EIO, EPERM, or EROFS, it's probably safe to fail
worth optimizing, and who knows what other messed-up systems
are out there? So play it safe and fall back on the code
below. */
-# if HAVE_FUTIMES
+# if HAVE_FUTIMESAT && !FUTIMESAT_NULL_BUG
+ if (futimesat (fd, NULL, t) == 0)
+ return 0;
+# elif HAVE_FUTIMES
if (futimes (fd, t) == 0)
return 0;
# endif
if (!file)
{
-#if ! (HAVE_FUTIMESAT || (HAVE_WORKING_UTIMES && HAVE_FUTIMES))
+#if ! ((HAVE_FUTIMESAT && !FUTIMESAT_NULL_BUG) \
+ || (HAVE_WORKING_UTIMES && HAVE_FUTIMES))
errno = ENOSYS;
#endif
return -1;
dnl gives unlimited permission to copy and/or distribute it,
dnl with or without modifications, as long as this notice is preserved.
-dnl serial 3
+dnl serial 4
AC_DEFUN([gl_UTIMENS],
[
AC_REQUIRE([gl_CHECK_TYPE_STRUCT_TIMESPEC])
AC_REQUIRE([gl_CHECK_TYPE_STRUCT_UTIMBUF])
AC_CHECK_FUNCS_ONCE([futimes futimesat futimens utimensat lutimes])
+
+ if test $ac_cv_func_futimens = no && test $ac_cv_func_futimesat = yes; then
+ dnl FreeBSD 8.0-rc2 mishandles futimesat(fd,NULL,time). It is not
+ dnl standardized, but Solaris implemented it first and uses it as
+ dnl its only means to set fd time.
+ AC_CACHE_CHECK([whether futimesat handles NULL file],
+ [gl_cv_func_futimesat_works],
+ [touch conftest.file
+ AC_RUN_IFELSE([AC_LANG_PROGRAM([[
+#include <stddef.h>
+#include <sys/times.h>
+]], [[ int fd = open ("conftest.file", O_RDWR);
+ if (fd < 0) return 1;
+ if (futimesat (fd, NULL, NULL)) return 2;
+ ]])],
+ [gl_cv_func_futimesat_works=yes],
+ [gl_cv_func_futimesat_works=no],
+ [gl_cv_func_futimesat_works="guessing no"])
+ rm -f conftest.file])
+ if test "$gl_cv_func_futimesat_works" != yes; then
+ AC_DEFINE([FUTIMESAT_NULL_BUG], [1],
+ [Define to 1 if futimesat mishandles a NULL file name.])
+ fi
+ fi
])