sbase

suckless unix tools
git clone git://git.2f30.org/sbase
Log | Files | Refs | README | LICENSE

chgrp.c (1533B)


      1 /* See LICENSE file for copyright and license details. */
      2 #include <sys/stat.h>
      3 
      4 #include <errno.h>
      5 #include <grp.h>
      6 #include <unistd.h>
      7 
      8 #include "fs.h"
      9 #include "util.h"
     10 
     11 static int   hflag = 0;
     12 static gid_t gid = -1;
     13 static int   ret = 0;
     14 
     15 static void
     16 chgrp(const char *path, struct stat *st, void *data, struct recursor *r)
     17 {
     18 	char *chownf_name;
     19 	int (*chownf)(const char *, uid_t, gid_t);
     20 
     21 	if ((r->maxdepth == 0 && r->follow == 'P') || (r->follow == 'H' && r->depth) || (hflag && !(r->depth))) {
     22 		chownf_name = "lchown";
     23 		chownf = lchown;
     24 	} else {
     25 		chownf_name = "chown";
     26 		chownf = chown;
     27 	}
     28 
     29 	if (chownf(path, st->st_uid, gid) < 0) {
     30 		weprintf("%s %s:", chownf_name, path);
     31 		ret = 1;
     32 	} else if (S_ISDIR(st->st_mode)) {
     33 		recurse(path, NULL, r);
     34 	}
     35 }
     36 
     37 static void
     38 usage(void)
     39 {
     40 	eprintf("usage: %s [-h] [-R [-H | -L | -P]] group file ...\n", argv0);
     41 }
     42 
     43 int
     44 main(int argc, char *argv[])
     45 {
     46 	struct group *gr;
     47 	struct recursor r = { .fn = chgrp, .hist = NULL, .depth = 0, .maxdepth = 1,
     48 	                      .follow = 'P', .flags = 0 };
     49 
     50 	ARGBEGIN {
     51 	case 'h':
     52 		hflag = 1;
     53 		break;
     54 	case 'R':
     55 		r.maxdepth = 0;
     56 		break;
     57 	case 'H':
     58 	case 'L':
     59 	case 'P':
     60 		r.follow = ARGC();
     61 		break;
     62 	default:
     63 		usage();
     64 	} ARGEND
     65 
     66 	if (argc < 2)
     67 		usage();
     68 
     69 	errno = 0;
     70 	if ((gr = getgrnam(argv[0]))) {
     71 		gid = gr->gr_gid;
     72 	} else {
     73 		if (errno)
     74 			eprintf("getgrnam %s:", argv[0]);
     75 		gid = estrtonum(argv[0], 0, UINT_MAX);
     76 	}
     77 
     78 	for (argc--, argv++; *argv; argc--, argv++)
     79 		recurse(*argv, NULL, &r);
     80 
     81 	return ret || recurse_status;
     82 }