|
|
1.1 root 1: /*
2: * Copyright (c) 1980 Regents of the University of California.
3: * All rights reserved. The Berkeley software License Agreement
4: * specifies the terms and conditions for redistribution.
5: */
6:
7: #ifndef lint
8: static char sccsid[] = "@(#)chgrp.c 5.7 (Berkeley) 6/4/86";
9: #endif not lint
10:
11: /*
12: * chgrp -fR gid file ...
13: */
14:
15: #include <stdio.h>
16: #include <ctype.h>
17: #include <sys/types.h>
18: #include <sys/stat.h>
19: #include <grp.h>
20: #include <pwd.h>
21: #include <sys/dir.h>
22:
23: struct group *gr, *getgrnam(), *getgrgid();
24: struct passwd *getpwuid(), *pwd;
25: struct stat stbuf;
26: int gid, uid;
27: int status;
28: int fflag, rflag;
29: /* VARARGS */
30: int fprintf();
31:
32: main(argc, argv)
33: int argc;
34: char *argv[];
35: {
36: register c, i;
37: register char *cp;
38:
39: argc--, argv++;
40: while (argc > 0 && argv[0][0] == '-') {
41: for (cp = &argv[0][1]; *cp; cp++) switch (*cp) {
42:
43: case 'f':
44: fflag++;
45: break;
46:
47: case 'R':
48: rflag++;
49: break;
50:
51: default:
52: fatal(255, "unknown option: %c", *cp);
53: /*NOTREACHED*/
54: }
55: argv++, argc--;
56: }
57: if (argc < 2) {
58: fprintf(stderr, "usage: chgrp [-fR] gid file ...\n");
59: exit(255);
60: }
61: uid = getuid();
62: if (isnumber(argv[0])) {
63: gid = atoi(argv[0]);
64: gr = getgrgid(gid);
65: if (uid && gr == NULL)
66: fatal(255, "%s: unknown group", argv[0]);
67: } else {
68: gr = getgrnam(argv[0]);
69: if (gr == NULL)
70: fatal(255, "%s: unknown group", argv[0]);
71: gid = gr->gr_gid;
72: }
73: pwd = getpwuid(uid);
74: if (pwd == NULL)
75: fatal(255, "Who are you?");
76: if (uid && pwd->pw_gid != gid) {
77: for (i=0; gr->gr_mem[i]; i++)
78: if (!(strcmp(pwd->pw_name, gr->gr_mem[i])))
79: goto ok;
80: if (fflag)
81: exit(0);
82: fatal(255, "You are not a member of the %s group", argv[0]);
83: }
84: ok:
85: for (c = 1; c < argc; c++) {
86: /* do stat for directory arguments */
87: if (lstat(argv[c], &stbuf)) {
88: status += Perror(argv[c]);
89: continue;
90: }
91: if (uid && uid != stbuf.st_uid) {
92: status += error("You are not the owner of %s", argv[c]);
93: continue;
94: }
95: if (rflag && ((stbuf.st_mode & S_IFMT) == S_IFDIR)) {
96: status += chownr(argv[c], stbuf.st_uid, gid);
97: continue;
98: }
99: if (chown(argv[c], -1, gid)) {
100: status += Perror(argv[c]);
101: continue;
102: }
103: }
104: exit(status);
105: }
106:
107: isnumber(s)
108: char *s;
109: {
110: register int c;
111:
112: while (c = *s++)
113: if (!isdigit(c))
114: return (0);
115: return (1);
116: }
117:
118: chownr(dir, uid, gid)
119: char *dir;
120: {
121: register DIR *dirp;
122: register struct direct *dp;
123: register struct stat st;
124: char savedir[1024];
125: int ecode;
126:
127: if (getwd(savedir) == 0)
128: fatal(255, "%s", savedir);
129: /*
130: * Change what we are given before doing its contents.
131: */
132: if (chown(dir, -1, gid) < 0 && Perror(dir))
133: return (1);
134: if (chdir(dir) < 0) {
135: Perror(dir);
136: return (1);
137: }
138: if ((dirp = opendir(".")) == NULL) {
139: Perror(dir);
140: return (1);
141: }
142: dp = readdir(dirp);
143: dp = readdir(dirp); /* read "." and ".." */
144: ecode = 0;
145: for (dp = readdir(dirp); dp != NULL; dp = readdir(dirp)) {
146: if (lstat(dp->d_name, &st) < 0) {
147: ecode = Perror(dp->d_name);
148: if (ecode)
149: break;
150: continue;
151: }
152: if (uid && uid != st.st_uid) {
153: ecode = error("You are not the owner of %s",
154: dp->d_name);
155: continue;
156: }
157: if ((st.st_mode & S_IFMT) == S_IFDIR) {
158: ecode = chownr(dp->d_name, st.st_uid, gid);
159: if (ecode)
160: break;
161: continue;
162: }
163: if (chown(dp->d_name, -1, gid) < 0 &&
164: (ecode = Perror(dp->d_name)))
165: break;
166: }
167: closedir(dirp);
168: if (chdir(savedir) < 0)
169: fatal(255, "can't change back to %s", savedir);
170: return (ecode);
171: }
172:
173: error(fmt, a)
174: char *fmt, *a;
175: {
176:
177: if (!fflag) {
178: fprintf(stderr, "chgrp: ");
179: fprintf(stderr, fmt, a);
180: putc('\n', stderr);
181: }
182: return (!fflag);
183: }
184:
185: fatal(status, fmt, a)
186: int status;
187: char *fmt, *a;
188: {
189:
190: fflag = 0;
191: (void) error(fmt, a);
192: exit(status);
193: }
194:
195: Perror(s)
196: char *s;
197: {
198:
199: if (!fflag) {
200: fprintf(stderr, "chgrp: ");
201: perror(s);
202: }
203: return (!fflag);
204: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.