From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.2 (2018-09-13) on dcvr.yhbt.net X-Spam-Level: X-Spam-Status: No, score=-3.9 required=3.0 tests=AWL,BAYES_00,DKIM_INVALID, DKIM_SIGNED,HEADER_FROM_DIFFERENT_DOMAINS,MAILING_LIST_MULTI, NICE_REPLY_A,RCVD_IN_DNSWL_BLOCKED,RCVD_IN_MSPIKE_H4,RCVD_IN_MSPIKE_WL, SPF_HELO_PASS,SPF_PASS shortcircuit=no autolearn=ham autolearn_force=no version=3.4.2 Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by dcvr.yhbt.net (Postfix) with ESMTPS id 01D771F4B4 for ; Sat, 9 Jan 2021 07:28:04 +0000 (UTC) Received: from localhost ([::1]:55508 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1ky8fL-0000Xd-Tr for normalperson@yhbt.net; Sat, 09 Jan 2021 02:28:03 -0500 Received: from eggs.gnu.org ([2001:470:142:3::10]:36276) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1ky8fC-0000Vq-KF for bug-gnulib@gnu.org; Sat, 09 Jan 2021 02:27:54 -0500 Received: from mo4-p00-ob.smtp.rzone.de ([85.215.255.22]:31682) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1ky8f9-0001aW-4Z for bug-gnulib@gnu.org; Sat, 09 Jan 2021 02:27:54 -0500 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; t=1610177268; s=strato-dkim-0002; d=clisp.org; h=References:In-Reply-To:Message-ID:Date:Subject:To:From:From:Subject: Sender; bh=ssiINLpkSpeDiVL/5y/IIQ0Mwe0Oo4PGLscL1PBhhwE=; b=HFbjMK75hqT+RQaFHpncWjcMzLdhvAgEfYgGylioILT4WYnxLDVD8nh8sLjvtmNHgx lwxhb42ekMRidPN9pvWzOhnoQixRtF6YEMTHc8tzZ+DOYVJ3vwgUWV/0yFXjy1OJSUl5 /7TjUvbAbvoJ2e+8hBNoL1efM7rdlH6yJ1oZEkaFmrRxIqBH2/nP54j8c8wv3SeIYtQQ rrmMiB1G6z0jk33fbP6exXDi8+xADXQZCBZP8SkjzT2nil8rwrokLwT0dcqawf8uDV5E PlvtZu8UsmHac+tSZu8H/O5L6aT/gHYLx8Le9+GpjKs/Hg3lZ7IDuIhCvBEw+AEwHVD5 +5/w== X-RZG-AUTH: ":Ln4Re0+Ic/6oZXR1YgKryK8brlshOcZlIWs+iCP5vnk6shH+AHjwLuWOHqfyyvs=" X-RZG-CLASS-ID: mo00 Received: from bruno.haible.de by smtp.strato.de (RZmta 47.12.1 DYNA|AUTH) with ESMTPSA id u0aa20x097RmDSV (using TLSv1 with cipher ECDHE-RSA-AES256-SHA (curve X9_62_prime256v1 with 256 ECDH bits, eq. 3072 bits RSA)) (Client did not present a certificate); Sat, 9 Jan 2021 08:27:48 +0100 (CET) From: Bruno Haible To: bug-gnulib@gnu.org Subject: Re: fchmod-tests, fchmodat tests, lchmod tests: Add more tests Date: Sat, 09 Jan 2021 08:27:47 +0100 Message-ID: <1947658.SbBB4bbWCc@omega> User-Agent: KMail/5.1.3 (Linux/4.4.0-197-generic; KDE/5.18.0; x86_64; ; ) In-Reply-To: <3704556.0YkK4g5aho@omega> References: <3704556.0YkK4g5aho@omega> MIME-Version: 1.0 Content-Transfer-Encoding: 7Bit Content-Type: text/plain; charset="us-ascii" Received-SPF: none client-ip=85.215.255.22; envelope-from=bruno@clisp.org; helo=mo4-p00-ob.smtp.rzone.de X-Spam_score_int: -22 X-Spam_score: -2.3 X-Spam_bar: -- X-Spam_report: (-2.3 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, NICE_REPLY_A=-0.241, RCVD_IN_DNSWL_NONE=-0.0001, RCVD_IN_MSPIKE_H3=0.001, RCVD_IN_MSPIKE_WL=0.001, SPF_HELO_PASS=-0.001, SPF_NONE=0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: bug-gnulib@gnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: Gnulib discussion list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: bug-gnulib-bounces+normalperson=yhbt.net@gnu.org Sender: "bug-gnulib" I wrote: > It smells like additional tests for fchmod(), fchmodat(), lchmod() could > uncover bugs on some platforms. So I'm adding more tests. And indeed, on AIX 7.2 one of these new tests fails: ../../gltests/test-fchmodat.c:60: assertion 'fchmodat (AT_FDCWD, BASE "file/", 0600, 0) == -1' failed FAIL test-fchmodat (exit status: 134) This patch provides a workaround. 2021-01-09 Bruno Haible fchmodat: Work around trailing slash bug in fchmodat() on AIX 7.2. * m4/fchmodat.m4 (gl_FUNC_FCHMODAT): In the test whether fchmodat works, also test for the trailing slashes behaviour. Define HAVE_NEARLY_WORKING_FCHMODAT if this is the only missing feature. * lib/fchmodat.c (fchmodat): If HAVE_NEARLY_WORKING_FCHMODAT, handle trailing slashes here. * modules/fchmodat (Depends-on): Sort by condition, not alphabetically. * doc/posix-functions/fchmodat.texi: Document the AIX bug. diff --git a/doc/posix-functions/fchmodat.texi b/doc/posix-functions/fchmodat.texi index 10821b6..aa0c0fd 100644 --- a/doc/posix-functions/fchmodat.texi +++ b/doc/posix-functions/fchmodat.texi @@ -14,6 +14,10 @@ glibc 2.3.6, Mac OS X 10.5, FreeBSD 6.0, NetBSD 5.0, OpenBSD 3.8, Minix 3.1.8, AIX 5.1, HP-UX 11, IRIX 6.5, Solaris 10, Cygwin 1.5.x, mingw, MSVC 14. But the replacement function is not safe to be used in libraries and is not multithread-safe. @item +This function does not fail when the file name argument ends in a slash +and (without the slash) names a non-directory, on some platforms: +AIX 7.2. +@item When given the @code{AT_SYMLINK_NOFOLLOW} flag, this function fails with @code{errno} set to @code{ENOTSUP}, even when the file is not a symbolic link: diff --git a/lib/fchmodat.c b/lib/fchmodat.c index d27c0d7..eb6e224 100644 --- a/lib/fchmodat.c +++ b/lib/fchmodat.c @@ -38,6 +38,7 @@ orig_fchmodat (int dir, char const *file, mode_t mode, int flags) #include #include #include +#include #include #ifdef __osf__ @@ -63,6 +64,22 @@ orig_fchmodat (int dir, char const *file, mode_t mode, int flags) int fchmodat (int dir, char const *file, mode_t mode, int flags) { +# if HAVE_NEARLY_WORKING_FCHMODAT + /* Correct the trailing slash handling. */ + size_t len = strlen (file); + if (len && file[len - 1] == '/') + { + struct stat st; + if (fstatat (dir, file, &st, flags & AT_SYMLINK_NOFOLLOW) < 0) + return -1; + if (!S_ISDIR (st.st_mode)) + { + errno = ENOTDIR; + return -1; + } + } +# endif + # if NEED_FCHMODAT_NONSYMLINK_FIX if (flags == AT_SYMLINK_NOFOLLOW) { diff --git a/m4/fchmodat.m4 b/m4/fchmodat.m4 index 0938032..66c0e30 100644 --- a/m4/fchmodat.m4 +++ b/m4/fchmodat.m4 @@ -1,4 +1,4 @@ -# fchmodat.m4 serial 5 +# fchmodat.m4 serial 6 dnl Copyright (C) 2004-2021 Free Software Foundation, Inc. dnl This file is free software; the Free Software Foundation dnl gives unlimited permission to copy and/or distribute it, @@ -16,11 +16,9 @@ AC_DEFUN([gl_FUNC_FCHMODAT], HAVE_FCHMODAT=0 else AC_CACHE_CHECK( - [whether fchmodat+AT_SYMLINK_NOFOLLOW works on non-symlinks], + [whether fchmodat works], [gl_cv_func_fchmodat_works], - [dnl This test fails on GNU/Linux with glibc 2.31 (but not on - dnl GNU/kFreeBSD nor GNU/Hurd) and Cygwin 2.9. - AC_RUN_IFELSE( + [AC_RUN_IFELSE( [AC_LANG_PROGRAM( [ AC_INCLUDES_DEFAULT[ @@ -44,27 +42,49 @@ AC_DEFUN([gl_FUNC_FCHMODAT], [[ int permissive = S_IRWXU | S_IRWXG | S_IRWXO; int desired = S_IRUSR | S_IWUSR; - static char const f[] = "conftest.fchmodat"; + int result = 0; + #define file "conftest.fchmodat" struct stat st; - if (creat (f, permissive) < 0) + if (creat (file, permissive) < 0) return 1; - if (fchmodat (AT_FDCWD, f, desired, AT_SYMLINK_NOFOLLOW) != 0) + /* Test whether fchmodat rejects a trailing slash on a non-directory. + This test fails on AIX 7.2. */ + if (fchmodat (AT_FDCWD, file "/", desired, 0) == 0) + result |= 2; + /* Test whether fchmodat+AT_SYMLINK_NOFOLLOW works on non-symlinks. + This test fails on GNU/Linux with glibc 2.31 (but not on + GNU/kFreeBSD nor GNU/Hurd) and Cygwin 2.9. */ + if (fchmodat (AT_FDCWD, file, desired, AT_SYMLINK_NOFOLLOW) != 0) + result |= 4; + if (stat (file, &st) != 0) return 1; - if (stat (f, &st) != 0) - return 1; - return ! ((st.st_mode & permissive) == desired); + if ((st.st_mode & permissive) != desired) + result |= 4; + return result; ]])], [gl_cv_func_fchmodat_works=yes], - [gl_cv_func_fchmodat_works=no], + [case $? in + 2) gl_cv_func_fchmodat_works='nearly' ;; + *) gl_cv_func_fchmodat_works=no ;; + esac + ], [case "$host_os" in - dnl Guess no on Linux with glibc and Cygwin, yes otherwise. + # Guess no on Linux with glibc and Cygwin. linux-gnu* | cygwin*) gl_cv_func_fchmodat_works="guessing no" ;; + # Guess 'nearly' on AIX. + aix*) gl_cv_func_fchmodat_works="guessing nearly" ;; + # If we don't know, obey --enable-cross-guesses. *) gl_cv_func_fchmodat_works="$gl_cross_guess_normal" ;; esac ]) rm -f conftest.fchmodat]) - case $gl_cv_func_fchmodat_works in + case "$gl_cv_func_fchmodat_works" in *yes) ;; + *nearly) + AC_DEFINE([HAVE_NEARLY_WORKING_FCHMODAT], [1], + [Define to 1 if fchmodat works, except for the trailing slash handling.]) + REPLACE_FCHMODAT=1 + ;; *) AC_DEFINE([NEED_FCHMODAT_NONSYMLINK_FIX], [1], [Define to 1 if fchmodat+AT_SYMLINK_NOFOLLOW does not work right on non-symlinks.]) diff --git a/modules/fchmodat b/modules/fchmodat index 975889b..17cfe39 100644 --- a/modules/fchmodat +++ b/modules/fchmodat @@ -9,20 +9,20 @@ m4/fchmodat.m4 Depends-on: sys_stat extensions -at-internal [test $HAVE_FCHMODAT = 0] -c99 [test $REPLACE_FCHMODAT = 1] errno [test $HAVE_FCHMODAT = 0 || test $REPLACE_FCHMODAT = 1] +fcntl-h [test $HAVE_FCHMODAT = 0 || test $REPLACE_FCHMODAT = 1] +unistd [test $HAVE_FCHMODAT = 0 || test $REPLACE_FCHMODAT = 1] +intprops [test $HAVE_FCHMODAT = 0 || test $REPLACE_FCHMODAT = 1] +c99 [test $REPLACE_FCHMODAT = 1] +fstatat [test $REPLACE_FCHMODAT = 1] +at-internal [test $HAVE_FCHMODAT = 0] extern-inline [test $HAVE_FCHMODAT = 0] fchdir [test $HAVE_FCHMODAT = 0] -fcntl-h [test $HAVE_FCHMODAT = 0 || test $REPLACE_FCHMODAT = 1] filename [test $HAVE_FCHMODAT = 0] -fstatat [test $REPLACE_FCHMODAT = 1] -intprops [test $HAVE_FCHMODAT = 0 || test $REPLACE_FCHMODAT = 1] lchmod [test $HAVE_FCHMODAT = 0] openat-die [test $HAVE_FCHMODAT = 0] openat-h [test $HAVE_FCHMODAT = 0] save-cwd [test $HAVE_FCHMODAT = 0] -unistd [test $HAVE_FCHMODAT = 0 || test $REPLACE_FCHMODAT = 1] configure.ac: gl_FUNC_FCHMODAT