Hello, I have found an error in chgrp and chown regarding symlinks. If a system supports lchown(2) calls, this call is used to change the symlink itself while chown(2) is used for changing the referenced file. In either case, lstat(2) is used for getting owner/group information of the file. This results in an apparently nondeterministic behaviour when changing the owner/group of the referenced file. Moreover, in both tools the global variable `change_symlinks' is set to 1 by default. This results in changing the link rather than the referenced file by default. While chown has the option `--dereference', chgrp is missing this option leading in not beeing able to change the group of the referenced file. Both problems are resolvedby the attached patch, relative to the current fileutils-4.0 version. Corinna Vinschen
--- ChangeLog.old Sun Apr 2 10:49:30 2000 +++ ChangeLog Sun Apr 2 10:55:40 2000 @@ -1,3 +1,13 @@ +2000-04-02 Corinna Vinschen <[EMAIL PROTECTED]> + + * src/chgrp.c: Add long option `--dereference'. + (change_file_group): Use lstat(2) if change_symlinks is set, + stat(2) otherwise. + (usage): Reflect new option `--dereference'. + (main): Add case label for new option `--dereference'. + * src/chown.c (change_file_owner): Use lstat(2) if change_symlinks + is set, stat(2) otherwise. + 1998-11-14 Jim Meyering <[EMAIL PROTECTED]> * Version 4.0. --- chgrp.c.old Sat Apr 1 14:41:57 2000 +++ chgrp.c Sat Apr 1 14:57:38 2000 @@ -104,6 +104,7 @@ static struct option const long_options[ { {"recursive", no_argument, 0, 'R'}, {"changes", no_argument, 0, 'c'}, + {"dereference", no_argument, 0, CHAR_MAX + 2}, {"no-dereference", no_argument, 0, 'h'}, {"silent", no_argument, 0, 'f'}, {"quiet", no_argument, 0, 'f'}, @@ -182,7 +183,8 @@ change_file_group (const char *file, int struct stat file_stats; int errors = 0; - if (lstat (file, &file_stats)) + if ((change_symlinks && lstat (file, &file_stats)) + || (!change_symlinks && stat (file, &file_stats))) { if (force_silent == 0) error (0, errno, "%s", file); @@ -305,6 +307,8 @@ Usage: %s [OPTION]... GROUP FILE...\n\ Change the group membership of each FILE to GROUP.\n\ \n\ -c, --changes like verbose but report only when a change is made\n\ + --dereference affect the referent of each symbolic link, rather\n\ + than the symbolic link itself\n\ -h, --no-dereference affect symbolic links instead of any referenced file\n\ (available only on systems with lchown system call)\n\ -f, --silent, --quiet suppress most error messages\n\ @@ -342,6 +346,9 @@ main (int argc, char **argv) break; case CHAR_MAX + 1: reference_file = optarg; + break; + case CHAR_MAX + 2: + change_symlinks = 0; break; case 'R': recurse = 1; --- chown.c.old Sat Apr 1 14:41:47 2000 +++ chown.c Sat Apr 1 14:43:16 2000 @@ -172,7 +172,8 @@ change_file_owner (int cmdline_arg, cons gid_t newgroup; int errors = 0; - if (lstat (file, &file_stats)) + if ((change_symlinks && lstat (file, &file_stats)) + || (!change_symlinks && stat (file, &file_stats))) { if (force_silent == 0) error (0, errno, "%s", file);