Path: utzoo!utgpu!jarvis.csri.toronto.edu!rutgers!mit-eddie!bloom-beacon!bionet!csd4.milw.wisc.edu!leah!rpi!rpi.edu!tale From: tale@pawl.rpi.edu (David C Lawrence) Newsgroups: alt.sources Subject: Re: chmod args Message-ID: Date: 3 Jun 89 08:13:46 GMT References: <8923@csli.Stanford.EDU> <11680@s.ms.uky.edu> <8928@csli.Stanford.EDU> <12743@ihlpy.ATT.COM> <1953@ur-cc.UUCP> <2126@amelia.nas.nasa.gov> <8605@chinet.chi.il.us> <1771@papaya.bbn.com> Sender: usenet@rpi.edu Reply-To: tale@pawl.rpi.edu Distribution: usa Lines: 141 In-reply-to: rsalz@bbn.com's message of 2 Jun 89 03:12:32 GMT /* -*- Mode: C -*- * permit.c --- change the permission of a file/directory using long form * Author : David C Lawrence * Created On : Sat Jun 3 03:32:10 1989 * Last Modified By: David C Lawrence * Last Modified On: Sat Jun 3 04:04:08 1989 * Update Count : 4 * Status : Works just fine for BSD/Sun, maybe SYSV */ /* * Usage is: permit rwxrwxrwx-pattern file(s) * * This deals fine with all current permission schemes on Sun/BSD * (and mostly on SYSV) systems of which I am aware. I'm not sure * how portable it is beyond that. * * It will accept patterns like rwsr-S--t (bozotic, I realize) without * complaint and try to permit accordingly. It even gives you a warning * message if you try to set the sticky bit on a file without being * the superuser (the regular chmod doesn't). * * Caveat: I couldn't get to a SYSV machine to try this out; I * have a feeling sticky bit stuff might be wrong there, but I am * not sure. * * BUGS: none that I know of at the moment, but it does have really * dorky error messages. */ #include #include #include #include char *pname; /* for the programme name (error messages) */ extern int errno; extern char *sys_errlist[]; extern char *strcpy(); int decipher_permission(perm_str) char *perm_str; { int loop, ch, perm=0; for (loop=0;loop<9;loop++) { ch=perm_str[loop]; switch (ch) { /* A switch statement probably isn't the */ case 'r': /* most efficient, but it only gets called */ if (loop%3 != 0) { /* nine times anyway. */ (void)fprintf(stderr,"%s: 'r'ead permission misplaced\n",pname); exit(99); } perm |= S_IREAD >> ((int)(loop/3))*3; break; case 'w': if (loop%3 != 1) { (void)fprintf(stderr,"%s: 'w'rite permission misplaced\n",pname); exit(99); } perm |= S_IWRITE >> ((int)(loop/3))*3; break; case 'x': if (loop%3 != 2) { (void)fprintf(stderr,"%s: e'x'ecute permisson misplaced\n",pname); exit(99); } perm |= S_IEXEC >> ((int)(loop/3))*3; break; case 'S': case 's': case 'l': /* 'l' is SYSV 'S' for setgid (?) */ if (loop%3 != 2 || loop == 8 || (ch == 'l' && loop != 5)) { (void)fprintf(stderr,"%s: 's'et[ug]id permission misplaced\n",pname); exit(99); } perm |= (loop==2 ? S_ISUID : S_ISGID); /* add execute permission, too */ if (ch == 's') perm |= S_IEXEC >> ((int)(loop/3))*3; break; case 'T': case 't': if (loop != 8) { (void)fprintf(stderr,"%s: s't'icky permission misplaced\n",pname); exit(99); } perm |= S_ISVTX; /* add execute permission, too */ if (ch == 't') perm |= S_IXOTH; break; case '-': break; default: (void)fprintf(stderr,"%s: unknown permission: %c\n",pname,ch); exit(99); } } return(perm); } int main(argc,argv) int argc; char **argv; { int permission, rc=0; struct stat *statbuf; if (argc < 3 || strlen(argv[1]) != 9) { (void)fprintf(stderr,"Usage: %s 9-char-permission file(s)\n",argv[0]); exit(101); } if((pname=malloc((unsigned)strlen(argv[0])+1))==NULL) { (void)fprintf(stderr,"%s: malloc: couldn't allocate space\n",argv[0]); exit(102); } (void)strcpy(pname,argv[0]); permission=decipher_permission(argv[1]); for(argc--;argc>1;argc--) { if (chmod(argv[argc],permission) == -1) { (void)fprintf(stderr,"%s: %s: %s\n",pname,argv[argc],sys_errlist[errno]); rc++; } else { (void)stat(argv[argc], statbuf); /* since chmod succeeded, stat should */ /* could possibly check here for clearing of setgid, too */ if ((geteuid() != 0) && (permission & S_ISVTX) && !(statbuf->st_mode & S_IFDIR)) { (void)fprintf(stderr, "%s: couldn't set sticky bit for %s\n",pname,argv[argc]); rc++; } } } /* exit with the number of files we were not able to permit as requested */ exit(rc); } -- (setq mail '("tale@pawl.rpi.edu" "tale@itsgw.rpi.edu" "tale@rpitsmts.bitnet"))