ubase

suckless linux base utils
git clone git://git.suckless.org/ubase
Log | Files | Refs | README | LICENSE

id.c (2942B)


      1 /* See LICENSE file for copyright and license details. */
      2 #include <sys/types.h>
      3 
      4 #include <ctype.h>
      5 #include <errno.h>
      6 #include <grp.h>
      7 #include <limits.h>
      8 #include <pwd.h>
      9 #include <stdio.h>
     10 #include <stdlib.h>
     11 #include <unistd.h>
     12 
     13 #include "util.h"
     14 
     15 static void groupid(struct passwd *pw);
     16 static void user(struct passwd *pw);
     17 static void userid(uid_t id);
     18 static void usernam(const char *nam);
     19 
     20 static int gflag = 0;
     21 static int uflag = 0;
     22 static int Gflag = 0;
     23 static int nflag = 0;
     24 
     25 static void
     26 groupid(struct passwd *pw)
     27 {
     28 	gid_t gid, groups[NGROUPS_MAX];
     29 	struct group *gr;
     30 	int ngroups;
     31 	int i;
     32 
     33 	ngroups = NGROUPS_MAX;
     34 	getgrouplist(pw->pw_name, pw->pw_gid, groups, &ngroups);
     35 	for (i = 0; i < ngroups; i++) {
     36 		gid = groups[i];
     37 		if (nflag) {
     38 			if (!(gr = getgrgid(gid)))
     39 				eprintf("getgrgid:");
     40 			printf("%s", gr->gr_name);
     41 		} else
     42 			printf("%u", gid);
     43 
     44 		if (i < ngroups - 1)
     45 			putchar(' ');
     46 	}
     47 	putchar('\n');
     48 }
     49 
     50 static void
     51 user(struct passwd *pw)
     52 {
     53 	struct group *gr;
     54 	gid_t gid, groups[NGROUPS_MAX];
     55 	int ngroups;
     56 	int i;
     57 
     58 	if (uflag) {
     59 		if (nflag)
     60 			printf("%s\n", pw->pw_name);
     61 		else
     62 			printf("%u\n", pw->pw_uid);
     63 		return;
     64 	} else if (gflag) {
     65 		if (nflag) {
     66 			if (!(gr = getgrgid(pw->pw_gid)))
     67 				eprintf("getgrgid:");
     68 			printf("%s\n", gr->gr_name);
     69 		} else
     70 			printf("%u\n", pw->pw_gid);
     71 		return;
     72 	}
     73 
     74 	printf("uid=%u(%s)", pw->pw_uid, pw->pw_name);
     75 	printf(" gid=%u", pw->pw_gid);
     76 	if (!(gr = getgrgid(pw->pw_gid)))
     77 		eprintf("getgrgid:");
     78 	printf("(%s)", gr->gr_name);
     79 
     80 	ngroups = NGROUPS_MAX;
     81 	getgrouplist(pw->pw_name, pw->pw_gid, groups, &ngroups);
     82 	for (i = 0; i < ngroups; i++) {
     83 		gid = groups[i];
     84 		printf("%s%u", !i ? " groups=" : ",", gid);
     85 		if (!(gr = getgrgid(gid)))
     86 			eprintf("getgrgid:");
     87 		printf("(%s)", gr->gr_name);
     88 	}
     89 	putchar('\n');
     90 }
     91 
     92 static void
     93 usernam(const char *nam)
     94 {
     95 	struct passwd *pw;
     96 
     97 	errno = 0;
     98 	pw = getpwnam(nam);
     99 	if (!pw) {
    100 		if (errno)
    101 			eprintf("getpwnam %s:", nam);
    102 		else
    103 			eprintf("getpwnam %s: no such user\n", nam);
    104 	}
    105 	if (Gflag)
    106 		groupid(pw);
    107 	else
    108 		user(pw);
    109 }
    110 
    111 static void
    112 userid(uid_t id)
    113 {
    114 	struct passwd *pw;
    115 
    116 	errno = 0;
    117 	pw = getpwuid(id);
    118 	if (!pw) {
    119 		if (errno)
    120 			eprintf("getpwuid %d:", id);
    121 		else
    122 			eprintf("getpwuid %d: no such user\n", id);
    123 	}
    124 	if (Gflag)
    125 		groupid(pw);
    126 	else
    127 		user(pw);
    128 }
    129 
    130 static void
    131 usage(void)
    132 {
    133 	eprintf("usage: %s [-n] [-g | -u | -G] [user | uid]\n", argv0);
    134 }
    135 
    136 int
    137 main(int argc, char *argv[])
    138 {
    139 	ARGBEGIN {
    140 	case 'g':
    141 		gflag = 1;
    142 		break;
    143 	case 'u':
    144 		uflag = 1;
    145 		break;
    146 	case 'G':
    147 		Gflag = 1;
    148 		break;
    149 	case 'n':
    150 		nflag = 1;
    151 		break;
    152 	default:
    153 		usage();
    154 	} ARGEND;
    155 
    156 	/* ensure that only one of -g, -u, or -G was specified */
    157 	if (gflag + uflag + Gflag > 1)
    158 		usage();
    159 
    160 	switch (argc) {
    161 	case 0:
    162 		userid(getuid());
    163 		break;
    164 	case 1:
    165 		/* user names can't begin [0-9] */
    166 		if (isdigit(argv[0][0]))
    167 			userid(estrtol(argv[0], 0));
    168 		else
    169 			usernam(argv[0]);
    170 		break;
    171 	default:
    172 		usage();
    173 	}
    174 
    175 	return 0;
    176 }