Clean up, WARNSify, unbreak -v option handling.

This commit is contained in:
Ruslan Ermilov 2001-09-13 14:55:59 +00:00
parent 7b24b50458
commit 8f9dacc2e6
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=83410
2 changed files with 52 additions and 52 deletions

View File

@ -3,6 +3,7 @@
PROG= chown
LINKS= ${BINDIR}/chown /usr/bin/chgrp
WARNS?= 2
MAN= chgrp.1 chown.8
.include <bsd.prog.mk>

View File

@ -49,8 +49,6 @@ static const char rcsid[] =
#include <sys/param.h>
#include <sys/stat.h>
#include <ctype.h>
#include <dirent.h>
#include <err.h>
#include <errno.h>
#include <fts.h>
@ -61,16 +59,16 @@ static const char rcsid[] =
#include <string.h>
#include <unistd.h>
void a_gid __P((char *));
void a_uid __P((char *));
void chownerr __P((char *));
u_long id __P((char *, char *));
void a_gid __P((const char *));
void a_uid __P((const char *));
void chownerr __P((const char *));
u_long id __P((const char *, const char *));
void usage __P((void));
uid_t uid;
gid_t gid;
int Rflag, ischown, fflag, hflag, vflag;
char *gname, *myname;
int ischown;
const char *gname;
int
main(argc, argv)
@ -79,25 +77,26 @@ main(argc, argv)
{
FTS *ftsp;
FTSENT *p;
int Hflag, Lflag, Pflag, ch, fts_options, hflag, rval;
int Hflag, Lflag, Rflag, fflag, hflag, vflag;
int ch, fts_options, rval;
char *cp;
myname = (cp = rindex(*argv, '/')) ? cp + 1 : *argv;
ischown = myname[2] == 'o';
cp = strrchr(argv[0], '/');
cp = (cp != NULL) ? cp + 1 : argv[0];
ischown = (strcmp(cp, "chown") == 0);
Hflag = Lflag = Pflag = hflag = vflag = 0;
Hflag = Lflag = Rflag = fflag = hflag = vflag = 0;
while ((ch = getopt(argc, argv, "HLPRfhv")) != -1)
switch (ch) {
case 'H':
Hflag = 1;
Lflag = Pflag = 0;
Lflag = 0;
break;
case 'L':
Lflag = 1;
Hflag = Pflag = 0;
Hflag = 0;
break;
case 'P':
Pflag = 1;
Hflag = Lflag = 0;
break;
case 'R':
@ -124,18 +123,20 @@ main(argc, argv)
if (Rflag) {
fts_options = FTS_PHYSICAL;
if (hflag && (Lflag || Hflag))
errx(1, "the -R and -h options may not be specified together");
if (hflag && (Hflag || Lflag))
errx(1, "the -R%c and -h options may not be "
"specified together", Hflag ? 'H' : 'L');
if (Hflag)
fts_options |= FTS_COMFOLLOW;
if (Lflag) {
else if (Lflag) {
fts_options &= ~FTS_PHYSICAL;
fts_options |= FTS_LOGICAL;
}
} else
fts_options = hflag ? FTS_PHYSICAL : FTS_LOGICAL;
uid = gid = -1;
uid = (uid_t)-1;
gid = (gid_t)-1;
if (ischown) {
if ((cp = strchr(*argv, ':')) != NULL) {
*cp++ = '\0';
@ -156,11 +157,11 @@ main(argc, argv)
for (rval = 0; (p = fts_read(ftsp)) != NULL;) {
switch (p->fts_info) {
case FTS_D: /* Change it at FTS_DP. */
case FTS_D: /* Change it at FTS_DP. */
if (!Rflag)
fts_set(ftsp, p, FTS_SKIP);
continue;
case FTS_DNR: /* Warn, chown, continue. */
case FTS_DNR: /* Warn, chown. */
warnx("%s: %s", p->fts_path, strerror(p->fts_errno));
rval = 1;
break;
@ -169,7 +170,7 @@ main(argc, argv)
warnx("%s: %s", p->fts_path, strerror(p->fts_errno));
rval = 1;
continue;
case FTS_SL: /* Ignore. */
case FTS_SL:
case FTS_SLNONE:
/*
* The only symlinks that end up here are ones that
@ -183,25 +184,17 @@ main(argc, argv)
default:
break;
}
if ((uid == -1 || uid == p->fts_statp->st_uid) &&
(gid == -1 || gid == p->fts_statp->st_gid))
if ((uid == (uid_t)-1 || uid == p->fts_statp->st_uid) &&
(gid == (gid_t)-1 || gid == p->fts_statp->st_gid))
continue;
if (hflag) {
if (lchown(p->fts_accpath, uid, gid) && !fflag) {
if ((hflag ? lchown : chown)(p->fts_accpath, uid, gid) == -1) {
if (!fflag) {
chownerr(p->fts_path);
rval = 1;
} else {
if (vflag)
(void)printf("%s\n", p->fts_accpath);
}
} else {
if (chown(p->fts_accpath, uid, gid) && !fflag) {
chownerr(p->fts_path);
rval = 1;
} else {
if (vflag)
(void)printf("%s\n", p->fts_accpath);
}
if (vflag)
printf("%s\n", p->fts_path);
}
}
if (errno)
@ -211,30 +204,30 @@ main(argc, argv)
void
a_gid(s)
char *s;
const char *s;
{
struct group *gr;
if (*s == '\0') /* Argument was "uid[:.]". */
return;
gname = s;
gid = ((gr = getgrnam(s)) == NULL) ? id(s, "group") : gr->gr_gid;
gid = ((gr = getgrnam(s)) != NULL) ? gr->gr_gid : id(s, "group");
}
void
a_uid(s)
char *s;
const char *s;
{
struct passwd *pw;
if (*s == '\0') /* Argument was "[:.]gid". */
return;
uid = ((pw = getpwnam(s)) == NULL) ? id(s, "user") : pw->pw_uid;
uid = ((pw = getpwnam(s)) != NULL) ? pw->pw_uid : id(s, "user");
}
u_long
id(name, type)
char *name, *type;
const char *name, *type;
{
u_long val;
char *ep;
@ -254,20 +247,21 @@ id(name, type)
void
chownerr(file)
char *file;
const char *file;
{
static int euid = -1, ngroups = -1;
gid_t groups[NGROUPS];
static uid_t euid = -1;
static int ngroups = -1;
gid_t groups[NGROUPS_MAX];
/* Check for chown without being root. */
if (errno != EPERM ||
(uid != -1 && euid == -1 && (euid = geteuid()) != 0))
(uid != (uid_t)-1 && euid == (uid_t)-1 && (euid = geteuid()) != 0))
err(1, "%s", file);
/* Check group membership; kernel just returns EPERM. */
if (gid != -1 && ngroups == -1 &&
euid == -1 && (euid = geteuid()) != 0) {
ngroups = getgroups(NGROUPS, groups);
if (gid != (gid_t)-1 && ngroups == -1 &&
euid == (uid_t)-1 && (euid = geteuid()) != 0) {
ngroups = getgroups(NGROUPS_MAX, groups);
while (--ngroups >= 0 && gid != groups[ngroups]);
if (ngroups < 0)
errx(1, "you are not a member of group %s", gname);
@ -278,9 +272,14 @@ chownerr(file)
void
usage()
{
(void)fprintf(stderr, "%s\n%s\n%s\n",
"usage: chown [-R [-H | -L | -P]] [-f] [-h] [-v] owner[:group] file ...",
" chown [-R [-H | -L | -P]] [-f] [-h] [-v] :group file ...",
" chgrp [-R [-H | -L | -P]] [-f] [-h] [-v] group file ...");
if (ischown)
(void)fprintf(stderr, "%s\n%s\n",
"usage: chown [-fhv] [-R [-H | -L | -P]] owner[:group]"
" file ...",
" chown [-fhv] [-R [-H | -L | -P]] :group file ...");
else
(void)fprintf(stderr, "%s\n",
"usage: chgrp [-fhv] [-R [-H | -L | -P]] group file ...");
exit(1);
}