X-Git-Url: http://erislabs.net/gitweb/?a=blobdiff_plain;f=m4%2Fchown.m4;h=ea3fe4c4c891dffc953553b735d01279d08fc606;hb=c47e73f47733362996652ecbb683347920a183b6;hp=430bc8073a2072d7fcf28ac1ce7d3c0ff8a557c2;hpb=c4da5fc90ff7ff8ef395c84be4b14e0a3d404cbb;p=gnulib.git diff --git a/m4/chown.m4 b/m4/chown.m4 index 430bc8073..ea3fe4c4c 100644 --- a/m4/chown.m4 +++ b/m4/chown.m4 @@ -1,76 +1,140 @@ -#serial 10 -# Determine whether we need the chown wrapper. chown should accept -# arguments of -1 for uid and gid, and it should dereference symlinks. -# If it doesn't, arrange to use the replacement function. +# serial 23 +# Determine whether we need the chown wrapper. + +dnl Copyright (C) 1997-2001, 2003-2005, 2007, 2009-2010 Free Software +dnl Foundation, Inc. + +dnl This file is free software; the Free Software Foundation +dnl gives unlimited permission to copy and/or distribute it, +dnl with or without modifications, as long as this notice is preserved. + +# chown should accept arguments of -1 for uid and gid, and it should +# dereference symlinks. If it doesn't, arrange to use the replacement +# function. + # From Jim Meyering. -AC_DEFUN([gl_FUNC_CHOWN], +AC_DEFUN_ONCE([gl_FUNC_CHOWN], [ + AC_REQUIRE([gl_UNISTD_H_DEFAULTS]) AC_REQUIRE([AC_TYPE_UID_T]) AC_REQUIRE([AC_FUNC_CHOWN]) AC_REQUIRE([gl_FUNC_CHOWN_FOLLOWS_SYMLINK]) + AC_CHECK_FUNCS_ONCE([chown fchown]) - if test $ac_cv_func_chown_works = yes; then - AC_DEFINE(CHOWN_FAILS_TO_HONOR_ID_OF_NEGATIVE_ONE, 1, - [Define if chown is not POSIX compliant regarding IDs of -1.]) - fi - - # If chown has either of the above problems, then we need the wrapper. - if test $ac_cv_func_chown_works$gl_cv_func_chown_follows_symlink = yesyes; then - : # no wrapper needed + dnl mingw lacks chown altogether. + if test $ac_cv_func_chown = no; then + HAVE_CHOWN=0 + AC_LIBOBJ([chown]) else - AC_LIBOBJ(chown) - AC_DEFINE(chown, rpl_chown, - [Define to rpl_chown if the replacement function should be used.]) - gl_PREREQ_CHOWN + dnl Some old systems treated chown like lchown. + if test $gl_cv_func_chown_follows_symlink = no; then + REPLACE_CHOWN=1 + AC_LIBOBJ([chown]) + fi + + dnl Some old systems tried to use uid/gid -1 literally. + if test $ac_cv_func_chown_works = no; then + AC_DEFINE([CHOWN_FAILS_TO_HONOR_ID_OF_NEGATIVE_ONE], [1], + [Define if chown is not POSIX compliant regarding IDs of -1.]) + REPLACE_CHOWN=1 + AC_LIBOBJ([chown]) + fi + + dnl Solaris 9 ignores trailing slash. + dnl FreeBSD 7.2 mishandles trailing slash on symlinks. + dnl Likewise for AIX 7.1. + AC_CACHE_CHECK([whether chown honors trailing slash], + [gl_cv_func_chown_slash_works], + [touch conftest.file && rm -f conftest.link + AC_RUN_IFELSE([AC_LANG_PROGRAM([[ +#include +#include +#include +]], [[ if (symlink ("conftest.file", "conftest.link")) return 1; + if (chown ("conftest.link/", getuid (), getgid ()) == 0) return 2; + ]])], + [gl_cv_func_chown_slash_works=yes], + [gl_cv_func_chown_slash_works=no], + [gl_cv_func_chown_slash_works="guessing no"]) + rm -f conftest.link conftest.file]) + if test "$gl_cv_func_chown_slash_works" != yes; then + AC_DEFINE([CHOWN_TRAILING_SLASH_BUG], [1], + [Define to 1 if chown mishandles trailing slash.]) + REPLACE_CHOWN=1 + AC_LIBOBJ([chown]) + fi + + dnl OpenBSD fails to update ctime if ownership does not change. + AC_CACHE_CHECK([whether chown always updates ctime], + [gl_cv_func_chown_ctime_works], + [AC_RUN_IFELSE([AC_LANG_PROGRAM([[ +#include +#include +#include +#include +#include +]], [[ 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], + [gl_cv_func_chown_ctime_works="guessing no"]) + rm -f conftest.file]) + if test "$gl_cv_func_chown_ctime_works" != yes; then + AC_DEFINE([CHOWN_CHANGE_TIME_BUG], [1], [Define to 1 if chown fails + to change ctime when at least one argument was not -1.]) + REPLACE_CHOWN=1 + AC_LIBOBJ([chown]) + fi + + if test $REPLACE_CHOWN = 1 && test $ac_cv_func_fchown = no; then + AC_LIBOBJ([fchown-stub]) + fi fi ]) # Determine whether chown follows symlinks (it should). -AC_DEFUN([gl_FUNC_CHOWN_FOLLOWS_SYMLINK], +AC_DEFUN_ONCE([gl_FUNC_CHOWN_FOLLOWS_SYMLINK], [ AC_CACHE_CHECK( - [whether chown(2) dereferences symlinks], - gl_cv_func_chown_follows_symlink, + [whether chown dereferences symlinks], + [gl_cv_func_chown_follows_symlink], [ AC_RUN_IFELSE([AC_LANG_SOURCE([[ -#ifdef HAVE_UNISTD_H -# include -#endif +#include #include #include - int - main () - { - char const *dangling_symlink = "conftest.dangle"; + int + main () + { + char const *dangling_symlink = "conftest.dangle"; - unlink (dangling_symlink); - if (symlink ("conftest.no-such", dangling_symlink)) - abort (); + unlink (dangling_symlink); + if (symlink ("conftest.no-such", dangling_symlink)) + abort (); - /* Exit successfully on a conforming system, - i.e., where chown must fail with ENOENT. */ - exit ( ! (chown (dangling_symlink, getuid (), getgid ()) != 0 - && errno == ENOENT)); - } - ]])], - [gl_cv_func_chown_follows_symlink=yes], - [gl_cv_func_chown_follows_symlink=no], - [gl_cv_func_chown_follows_symlink=no] + /* Exit successfully on a conforming system, + i.e., where chown must fail with ENOENT. */ + exit ( ! (chown (dangling_symlink, getuid (), getgid ()) != 0 + && errno == ENOENT)); + } + ]])], + [gl_cv_func_chown_follows_symlink=yes], + [gl_cv_func_chown_follows_symlink=no], + [gl_cv_func_chown_follows_symlink=yes] ) ] ) if test $gl_cv_func_chown_follows_symlink = no; then - AC_DEFINE(CHOWN_MODIFIES_SYMLINK, 1, + AC_DEFINE([CHOWN_MODIFIES_SYMLINK], [1], [Define if chown modifies symlinks.]) fi ]) - -# Prerequisites of lib/chown.c. -AC_DEFUN([gl_PREREQ_CHOWN], -[ - AC_CHECK_HEADERS_ONCE(unistd.h fcntl.h) - AC_CHECK_FUNC([fchown], , [AC_LIBOBJ(fchown-stub)]) -])