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