FreeBSD Bugzilla – Attachment 10273 Details for
Bug 20646
[PATCH] /bin/cp -p whines on set[ug]id immutable files
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Help
|
New Account
|
Log In
Remember
[x]
|
Forgot Password
Login:
[x]
[patch]
file.diff
file.diff (text/plain), 3.85 KB, created by
Peter Pentchev
on 2000-08-16 16:30:00 UTC
(
hide
)
Description:
file.diff
Filename:
MIME Type:
Creator:
Peter Pentchev
Created:
2000-08-16 16:30:00 UTC
Size:
3.85 KB
patch
obsolete
>diff -u -urN src/bin/cp/cp.c mysrc/bin/cp/cp.c >--- src/bin/cp/cp.c Sun Nov 28 11:34:21 1999 >+++ mysrc/bin/cp/cp.c Wed Aug 16 18:03:29 2000 >@@ -388,7 +388,7 @@ > * umask; arguably wrong, but it's been that way > * forever. > */ >- if (pflag && setfile(curr->fts_statp, 0)) >+ if (pflag && setfile(curr->fts_statp, 0, 1)) > badcp = rval = 1; > else if (dne) > (void)chmod(to.p_path, >diff -u -urN src/bin/cp/extern.h mysrc/bin/cp/extern.h >--- src/bin/cp/extern.h Wed Aug 16 18:15:40 2000 >+++ mysrc/bin/cp/extern.h Wed Aug 16 17:46:20 2000 >@@ -51,6 +51,6 @@ > int copy_file __P((FTSENT *, int)); > int copy_link __P((FTSENT *, int)); > int copy_special __P((struct stat *, int)); >-int setfile __P((struct stat *, int)); >+int setfile __P((struct stat *, int, int)); > void usage __P((void)); > __END_DECLS >diff -u -urN src/bin/cp/utils.c mysrc/bin/cp/utils.c >--- src/bin/cp/utils.c Wed Aug 16 18:15:40 2000 >+++ mysrc/bin/cp/utils.c Wed Aug 16 18:16:37 2000 >@@ -176,7 +176,8 @@ > * to remove it if we created it and its length is 0. > */ > >- if (pflag && setfile(fs, to_fd)) >+ /* do not copy flags at this time, or the next (f)chmod() fails */ >+ if (pflag && setfile(fs, to_fd, 0)) > rval = 1; > /* > * If the source was setuid or setgid, lose the bits unless the >@@ -194,6 +195,11 @@ > rval = 1; > } > } >+ >+ /* setfile() again, just for the file flags */ >+ if (pflag && setfile(fs, to_fd, 2)) >+ rval = 1; >+ > (void)close(from_fd); > if (close(to_fd)) { > warn("%s", to.p_path); >@@ -239,7 +245,7 @@ > warn("mkfifo: %s", to.p_path); > return (1); > } >- return (pflag ? setfile(from_stat, 0) : 0); >+ return (pflag ? setfile(from_stat, 0, 1) : 0); > } > > int >@@ -255,14 +261,23 @@ > warn("mknod: %s", to.p_path); > return (1); > } >- return (pflag ? setfile(from_stat, 0) : 0); >+ return (pflag ? setfile(from_stat, 0, 1) : 0); > } > > > int >-setfile(fs, fd) >+setfile(fs, fd, setflags) > register struct stat *fs; >- int fd; >+ int fd, setflags; >+ /* values for setflags: >+ 0 - do not touch fd's flags; >+ 1 - set fd's flags to match fs's flags; >+ 2 - ONLY set fd's flags to fs's flags, do nothing more >+ >+ the only reason for setflags to be 2 is in copy_file() >+ after the set[ug]id fixup; this would be better if >+ the fixup itself were moved here. >+ */ > { > static struct timeval tv[2]; > struct stat ts; >@@ -292,28 +307,34 @@ > * the mode; current BSD behavior is to remove all setuid bits on > * chown. If chown fails, lose setuid/setgid bits. > */ >- if (!gotstat || fs->st_uid != ts.st_uid || fs->st_gid != ts.st_gid) >- if (fd ? fchown(fd, fs->st_uid, fs->st_gid) : >- chown(to.p_path, fs->st_uid, fs->st_gid)) { >- if (errno != EPERM) { >+ >+ /* Oops. Are we called *after* the copy_file() set[ug]id fixup? */ >+ if (setflags != 2) { >+ if (!gotstat || fs->st_uid != ts.st_uid || fs->st_gid != ts.st_gid) >+ if (fd ? fchown(fd, fs->st_uid, fs->st_gid) : >+ chown(to.p_path, fs->st_uid, fs->st_gid)) { >+ if (errno != EPERM) { >+ warn("chown: %s", to.p_path); >+ rval = 1; >+ } >+ fs->st_mode &= ~(S_ISUID | S_ISGID); >+ } >+ >+ if (!gotstat || fs->st_mode != ts.st_mode) >+ if (fd ? fchmod(fd, fs->st_mode) : chmod(to.p_path, fs->st_mode)) { > warn("chown: %s", to.p_path); > rval = 1; > } >- fs->st_mode &= ~(S_ISUID | S_ISGID); >- } >- >- if (!gotstat || fs->st_mode != ts.st_mode) >- if (fd ? fchmod(fd, fs->st_mode) : chmod(to.p_path, fs->st_mode)) { >- warn("chown: %s", to.p_path); >- rval = 1; >- } >+ } > >- if (!gotstat || fs->st_flags != ts.st_flags) >- if (fd ? >- fchflags(fd, fs->st_flags) : chflags(to.p_path, fs->st_flags)) { >- warn("chflags: %s", to.p_path); >- rval = 1; >- } >+ if (setflags) { >+ if (!gotstat || fs->st_flags != ts.st_flags) >+ if (fd ? >+ fchflags(fd, fs->st_flags) : chflags(to.p_path, fs->st_flags)) { >+ warn("chflags: %s", to.p_path); >+ rval = 1; >+ } >+ } > > return (rval); > }
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 20646
: 10273