]> git.ipfire.org Git - thirdparty/gnulib.git/commitdiff
fchownat: Fix test failure on OpenBSD and Cygwin 2.9 (regr. 2025-09-20).
authorBruno Haible <bruno@clisp.org>
Mon, 22 Sep 2025 11:44:06 +0000 (13:44 +0200)
committerBruno Haible <bruno@clisp.org>
Mon, 22 Sep 2025 11:44:06 +0000 (13:44 +0200)
* doc/posix-functions/fchownat.texi: Document that the dereferencing bug
also affects OpenBSD and Cygwin 2.9.
* m4/chown.m4 (gl_FUNC_CHOWN_CTIME): New macro, extracted from
gl_FUNC_CHOWN.
(gl_FUNC_CHOWN): Invoke it.
* m4/fchownat.m4 (gl_FUNC_FCHOWNAT_DEREF_BUG): Guess that a platform
that has the chown ctime bug also has the fchownat AT_SYMLINK_NOFOLLOW
bug.
* modules/fchownat (Files): Add m4/chown.m4.

ChangeLog
doc/posix-functions/fchownat.texi
m4/chown.m4
m4/fchownat.m4
modules/fchownat

index f61718951ef9ff0c809896c004ec1d4927799b48..e845a3c76e523d24fca86050586938f55a115cea 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,16 @@
+2025-09-22  Bruno Haible  <bruno@clisp.org>
+
+       fchownat: Fix test failure on OpenBSD and Cygwin 2.9 (regr. 2025-09-20).
+       * doc/posix-functions/fchownat.texi: Document that the dereferencing bug
+       also affects OpenBSD and Cygwin 2.9.
+       * m4/chown.m4 (gl_FUNC_CHOWN_CTIME): New macro, extracted from
+       gl_FUNC_CHOWN.
+       (gl_FUNC_CHOWN): Invoke it.
+       * m4/fchownat.m4 (gl_FUNC_FCHOWNAT_DEREF_BUG): Guess that a platform
+       that has the chown ctime bug also has the fchownat AT_SYMLINK_NOFOLLOW
+       bug.
+       * modules/fchownat (Files): Add m4/chown.m4.
+
 2025-09-21  Paul Eggert  <eggert@cs.ucla.edu>
 
        fchownat: fix recently introduced flag typo
index 34c1d724f142192829f2f9f43723a14d88f8514c..c5669499118ef95dedc4fbeac26edf8b0a3aa6ca 100644 (file)
@@ -32,7 +32,7 @@ OpenBSD 7.7.
 @item
 Some platforms mistakenly dereference symlinks when using
 @code{AT_SYMLINK_NOFOLLOW}:
-Linux kernel 2.6.17.
+Linux kernel 2.6.17, OpenBSD 7.6, Cygwin 2.9.0.
 @item
 This function does not fail for an empty filename on some platforms:
 Linux with glibc < 2.11.
index f899f3b680d4626a61986ed152ca694ef2ebe747..3b377f2989d20956a367f44296c03528faff901a 100644 (file)
@@ -1,5 +1,5 @@
 # chown.m4
-# serial 39
+# serial 40
 dnl Copyright (C) 1997-2001, 2003-2005, 2007, 2009-2025 Free Software
 dnl Foundation, Inc.
 dnl This file is free software; the Free Software Foundation
@@ -130,39 +130,7 @@ AC_DEFUN_ONCE([gl_FUNC_CHOWN],
         ;;
     esac
 
-    dnl OpenBSD fails to update ctime if ownership does not change.
-    AC_CACHE_CHECK([whether chown updates ctime per POSIX],
-      [gl_cv_func_chown_ctime_works],
-      [dnl This test is tricky as it depends on timing and file timestamp
-       dnl resolution, and there were false positives when configuring with
-       dnl Linux fakeroot. Since the problem occurs only on OpenBSD and Cygwin,
-       dnl test only on these platforms.
-       AS_CASE([$host_os],
-         [openbsd* | cygwin*],
-          [AC_RUN_IFELSE([AC_LANG_PROGRAM([[
-#include <unistd.h>
-#include <stdlib.h>
-#include <errno.h>
-#include <fcntl.h>
-#include <sys/stat.h>
-]GL_MDA_DEFINES],
-             [[struct stat st1, st2;
-               if (close (creat ("conftest.file", 0600))) return 1;
-               if (stat ("conftest.file", &st1)) return 2;
-               sleep (1);
-               if (chown ("conftest.file", st1.st_uid, st1.st_gid)) return 3;
-               if (stat ("conftest.file", &st2)) return 4;
-               if (st2.st_ctime <= st1.st_ctime) return 5;
-             ]])],
-             [gl_cv_func_chown_ctime_works=yes],
-             [gl_cv_func_chown_ctime_works=no],
-             [# Obey --enable-cross-guesses.
-              gl_cv_func_chown_ctime_works="$gl_cross_guess_normal"
-             ])
-           rm -f conftest.file
-          ],
-         [gl_cv_func_chown_ctime_works=yes])
-      ])
+    gl_FUNC_CHOWN_CTIME
     case "$gl_cv_func_chown_ctime_works" in
       *yes) ;;
       *)
@@ -221,3 +189,47 @@ AC_DEFUN_ONCE([gl_FUNC_CHOWN_FOLLOWS_SYMLINK],
       ;;
   esac
 ])
+
+AC_DEFUN_ONCE([gl_FUNC_CHOWN_CTIME],
+[
+  AC_REQUIRE([AC_CANONICAL_HOST]) dnl for cross-compiles
+  AC_CHECK_FUNCS_ONCE([chown])
+
+  dnl mingw lacks chown altogether.
+  if test $ac_cv_func_chown != no; then
+    dnl OpenBSD and Cygwin 2.9.0 fail to update ctime if ownership does not
+    dnl change.
+    AC_CACHE_CHECK([whether chown updates ctime per POSIX],
+      [gl_cv_func_chown_ctime_works],
+      [dnl This test is tricky as it depends on timing and file timestamp
+       dnl resolution, and there were false positives when configuring with
+       dnl Linux fakeroot. Since the problem occurs only on OpenBSD and Cygwin,
+       dnl test only on these platforms.
+       AS_CASE([$host_os],
+         [openbsd* | cygwin*],
+          [AC_RUN_IFELSE([AC_LANG_PROGRAM([[
+#include <unistd.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <sys/stat.h>
+]GL_MDA_DEFINES],
+             [[struct stat st1, st2;
+               if (close (creat ("conftest.file", 0600))) return 1;
+               if (stat ("conftest.file", &st1)) return 2;
+               sleep (1);
+               if (chown ("conftest.file", st1.st_uid, st1.st_gid)) return 3;
+               if (stat ("conftest.file", &st2)) return 4;
+               if (st2.st_ctime <= st1.st_ctime) return 5;
+             ]])],
+             [gl_cv_func_chown_ctime_works=yes],
+             [gl_cv_func_chown_ctime_works=no],
+             [# Obey --enable-cross-guesses.
+              gl_cv_func_chown_ctime_works="$gl_cross_guess_normal"
+             ])
+           rm -f conftest.file
+          ],
+         [gl_cv_func_chown_ctime_works=yes])
+      ])
+  fi
+])
index 300a254225d0eec29a723c39f26a13536f228ea0..bad9b583602cb556255b069691b16066353e2133 100644 (file)
@@ -1,5 +1,5 @@
 # fchownat.m4
-# serial 8
+# serial 9
 dnl Copyright (C) 2004-2025 Free Software Foundation, Inc.
 dnl This file is free software; the Free Software Foundation
 dnl gives unlimited permission to copy and/or distribute it,
@@ -46,16 +46,18 @@ AC_DEFUN([gl_FUNC_FCHOWNAT_DEREF_BUG],
 
   AC_CACHE_CHECK([whether fchownat works with AT_SYMLINK_NOFOLLOW],
     [gl_cv_func_fchownat_nofollow_works],
-    [
-     gl_dangle=conftest.dangle
-     # Remove any remnants of a previous test.
-     rm -f $gl_dangle
-     # Arrange for deletion of the temporary file this test creates.
-     ac_clean_files="$ac_clean_files $gl_dangle"
-     ln -s conftest.no-such $gl_dangle
-     AC_RUN_IFELSE(
-       [AC_LANG_SOURCE(
-          [[
+    [gl_FUNC_CHOWN_CTIME
+     case "$gl_cv_func_chown_ctime_works" in
+       *yes)
+         gl_dangle=conftest.dangle
+         # Remove any remnants of a previous test.
+         rm -f $gl_dangle
+         # Arrange for deletion of the temporary file this test creates.
+         ac_clean_files="$ac_clean_files $gl_dangle"
+         ln -s conftest.no-such $gl_dangle
+         AC_RUN_IFELSE(
+           [AC_LANG_SOURCE(
+              [[
 #include <fcntl.h>
 #include <unistd.h>
 /* Android 4.3 declares fchownat() in <sys/stat.h> instead.  */
@@ -70,12 +72,27 @@ main ()
                     AT_SYMLINK_NOFOLLOW) != 0
           && errno == ENOENT);
 }
-          ]])],
-       [gl_cv_func_fchownat_nofollow_works=yes],
-       [gl_cv_func_fchownat_nofollow_works=no],
-       [gl_cv_func_fchownat_nofollow_works="$gl_cross_guess_normal"])
-  ])
-  AS_IF([test "$gl_cv_func_fchownat_nofollow_works" != yes], [$1], [$2])
+              ]])],
+           [gl_cv_func_fchownat_nofollow_works=yes],
+           [gl_cv_func_fchownat_nofollow_works=no],
+           [gl_cv_func_fchownat_nofollow_works="$gl_cross_guess_normal"])
+         ;;
+       *)
+         dnl On OpenBSD and Cygwin 2.9.0, the test above would produce
+         dnl gl_cv_func_fchownat_nofollow_works=yes, and this would then
+         dnl lead to an fchownat test failure:
+         dnl   test-lchown.h:185: assertion 'st1.st_gid == st2.st_gid' failed
+         dnl Since testing for this bug directly is only possible on machines
+         dnl where the current user is in at least two groups, we use
+         dnl gl_FUNC_CHOWN_CTIME as a substitute test.
+         gl_cv_func_fchownat_nofollow_works="guessing no"
+         ;;
+     esac
+    ])
+  case "$gl_cv_func_fchownat_nofollow_works" in
+    *yes) $2 ;;
+    *)    $1 ;;
+  esac
 ])
 
 # gl_FUNC_FCHOWNAT_EMPTY_FILENAME_BUG([ACTION-IF-BUGGY[, ACTION-IF-NOT_BUGGY]])
index 31e722c89cb3732005891bc24644c2a781621462..61e1d215a15ee1b1e6957fef3db42a8c51b54325 100644 (file)
@@ -5,6 +5,7 @@ Files:
 lib/fchownat.c
 lib/at-func.c
 m4/fchownat.m4
+m4/chown.m4
 
 Depends-on:
 unistd-h