Commit | Line | Data |
---|---|---|
be1dd919 | 1 | /*- |
ad787160 C |
2 | * Copyright (c) 1991, 1993 |
3 | * The Regents of the University of California. All rights reserved. | |
be1dd919 | 4 | * |
ad787160 C |
5 | * Redistribution and use in source and binary forms, with or without |
6 | * modification, are permitted provided that the following conditions | |
7 | * are met: | |
8 | * 1. Redistributions of source code must retain the above copyright | |
9 | * notice, this list of conditions and the following disclaimer. | |
10 | * 2. Redistributions in binary form must reproduce the above copyright | |
11 | * notice, this list of conditions and the following disclaimer in the | |
12 | * documentation and/or other materials provided with the distribution. | |
13 | * 3. All advertising materials mentioning features or use of this software | |
14 | * must display the following acknowledgement: | |
15 | * This product includes software developed by the University of | |
16 | * California, Berkeley and its contributors. | |
17 | * 4. Neither the name of the University nor the names of its contributors | |
18 | * may be used to endorse or promote products derived from this software | |
19 | * without specific prior written permission. | |
20 | * | |
21 | * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND | |
22 | * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | |
23 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | |
24 | * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE | |
25 | * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | |
26 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | |
27 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | |
28 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | |
29 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | |
30 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | |
31 | * SUCH DAMAGE. | |
be1dd919 KB |
32 | */ |
33 | ||
34 | #ifndef lint | |
ad787160 C |
35 | static char copyright[] = |
36 | "@(#) Copyright (c) 1991, 1993\n\ | |
37 | The Regents of the University of California. All rights reserved.\n"; | |
be1dd919 KB |
38 | #endif /* not lint */ |
39 | ||
40 | #ifndef lint | |
ad787160 | 41 | static char sccsid[] = "@(#)id.c 8.1 (Berkeley) 6/6/93"; |
be1dd919 KB |
42 | #endif /* not lint */ |
43 | ||
44 | #include <sys/param.h> | |
45 | #include <pwd.h> | |
46 | #include <grp.h> | |
47 | #include <errno.h> | |
48 | #include <unistd.h> | |
49 | #include <stdlib.h> | |
50 | #include <stdio.h> | |
51 | #include <string.h> | |
52 | ||
be1dd919 KB |
53 | void current __P((void)); |
54 | void err __P((const char *, ...)); | |
d500843c KB |
55 | void pretty __P((struct passwd *)); |
56 | void group __P((struct passwd *, int)); | |
be1dd919 | 57 | void usage __P((void)); |
d500843c KB |
58 | void user __P((struct passwd *)); |
59 | struct passwd * | |
60 | who __P((char *)); | |
be1dd919 | 61 | |
d500843c | 62 | int |
be1dd919 KB |
63 | main(argc, argv) |
64 | int argc; | |
65 | char *argv[]; | |
66 | { | |
d500843c KB |
67 | struct group *gr; |
68 | struct passwd *pw; | |
69 | int Gflag, ch, gflag, id, nflag, pflag, rflag, uflag; | |
be1dd919 | 70 | |
d500843c KB |
71 | Gflag = gflag = nflag = pflag = rflag = uflag = 0; |
72 | while ((ch = getopt(argc, argv, "Ggnpru")) != EOF) | |
be1dd919 KB |
73 | switch(ch) { |
74 | case 'G': | |
75 | Gflag = 1; | |
76 | break; | |
77 | case 'g': | |
78 | gflag = 1; | |
79 | break; | |
80 | case 'n': | |
81 | nflag = 1; | |
82 | break; | |
d500843c KB |
83 | case 'p': |
84 | pflag = 1; | |
85 | break; | |
be1dd919 KB |
86 | case 'r': |
87 | rflag = 1; | |
88 | break; | |
89 | case 'u': | |
90 | uflag = 1; | |
91 | break; | |
92 | case '?': | |
93 | default: | |
94 | usage(); | |
95 | } | |
96 | argc -= optind; | |
97 | argv += optind; | |
98 | ||
d500843c | 99 | switch(Gflag + gflag + pflag + uflag) { |
7ac05a89 KB |
100 | case 1: |
101 | break; | |
102 | case 0: | |
103 | if (!nflag && !rflag) | |
104 | break; | |
105 | /* FALLTHROUGH */ | |
106 | default: | |
be1dd919 | 107 | usage(); |
7ac05a89 | 108 | } |
be1dd919 | 109 | |
d500843c | 110 | pw = *argv ? who(*argv) : NULL; |
be1dd919 KB |
111 | |
112 | if (gflag) { | |
113 | id = pw ? pw->pw_gid : rflag ? getgid() : getegid(); | |
d500843c | 114 | if (nflag && (gr = getgrgid(id))) |
be1dd919 | 115 | (void)printf("%s\n", gr->gr_name); |
d500843c KB |
116 | else |
117 | (void)printf("%u\n", id); | |
be1dd919 KB |
118 | exit(0); |
119 | } | |
120 | ||
121 | if (uflag) { | |
122 | id = pw ? pw->pw_uid : rflag ? getuid() : geteuid(); | |
d500843c | 123 | if (nflag && (pw = getpwuid(id))) |
be1dd919 | 124 | (void)printf("%s\n", pw->pw_name); |
d500843c KB |
125 | else |
126 | (void)printf("%u\n", id); | |
127 | exit(0); | |
128 | } | |
129 | ||
130 | if (Gflag) { | |
131 | group(pw, nflag); | |
132 | exit(0); | |
133 | } | |
134 | ||
135 | if (pflag) { | |
136 | pretty(pw); | |
be1dd919 KB |
137 | exit(0); |
138 | } | |
139 | ||
140 | if (pw) | |
141 | user(pw); | |
142 | else | |
143 | current(); | |
144 | exit(0); | |
145 | } | |
146 | ||
147 | void | |
d500843c KB |
148 | pretty(pw) |
149 | struct passwd *pw; | |
be1dd919 | 150 | { |
d500843c KB |
151 | struct group *gr; |
152 | u_int eid, rid; | |
153 | char *login; | |
be1dd919 | 154 | |
524408bd | 155 | if (pw) { |
d500843c | 156 | (void)printf("uid\t%s\n", pw->pw_name); |
524408bd KB |
157 | (void)printf("groups\t"); |
158 | group(pw, 1); | |
159 | } else { | |
d500843c KB |
160 | if ((login = getlogin()) == NULL) |
161 | err("getlogin: %s", strerror(errno)); | |
162 | ||
163 | pw = getpwuid(rid = getuid()); | |
164 | if (pw == NULL || strcmp(login, pw->pw_name)) | |
165 | (void)printf("login\t%s\n", login); | |
166 | if (pw) | |
167 | (void)printf("uid\t%s\n", pw->pw_name); | |
168 | else | |
169 | (void)printf("uid\t%u\n", rid); | |
170 | ||
171 | if ((eid = geteuid()) != rid) | |
172 | if (pw = getpwuid(eid)) | |
173 | (void)printf("euid\t%s", pw->pw_name); | |
be1dd919 | 174 | else |
d500843c KB |
175 | (void)printf("euid\t%u", eid); |
176 | if ((rid = getgid()) != (eid = getegid())) | |
177 | if (gr = getgrgid(rid)) | |
178 | (void)printf("rgid\t%s\n", gr->gr_name); | |
179 | else | |
180 | (void)printf("rgid\t%u\n", rid); | |
524408bd KB |
181 | (void)printf("groups\t"); |
182 | group(NULL, 1); | |
be1dd919 | 183 | } |
be1dd919 KB |
184 | } |
185 | ||
186 | void | |
187 | current() | |
188 | { | |
d500843c KB |
189 | struct group *gr; |
190 | struct passwd *pw; | |
e157e33b | 191 | int cnt, id, eid, lastid, ngroups, groups[NGROUPS]; |
be1dd919 KB |
192 | char *fmt; |
193 | ||
194 | id = getuid(); | |
195 | (void)printf("uid=%u", id); | |
196 | if (pw = getpwuid(id)) | |
197 | (void)printf("(%s)", pw->pw_name); | |
198 | if ((eid = geteuid()) != id) { | |
199 | (void)printf(" euid=%u", eid); | |
200 | if (pw = getpwuid(eid)) | |
201 | (void)printf("(%s)", pw->pw_name); | |
202 | } | |
203 | id = getgid(); | |
204 | (void)printf(" gid=%u", id); | |
205 | if (gr = getgrgid(id)) | |
206 | (void)printf("(%s)", gr->gr_name); | |
207 | if ((eid = getegid()) != id) { | |
208 | (void)printf(" egid=%u", eid); | |
209 | if (gr = getgrgid(eid)) | |
210 | (void)printf("(%s)", gr->gr_name); | |
211 | } | |
212 | if (ngroups = getgroups(NGROUPS, groups)) { | |
e157e33b | 213 | for (fmt = " groups=%u", lastid = -1, cnt = 0; cnt < ngroups; |
be1dd919 | 214 | fmt = ", %u", lastid = id) { |
e157e33b | 215 | id = groups[cnt++]; |
be1dd919 KB |
216 | if (lastid == id) |
217 | continue; | |
218 | (void)printf(fmt, id); | |
219 | if (gr = getgrgid(id)) | |
220 | (void)printf("(%s)", gr->gr_name); | |
221 | } | |
222 | } | |
223 | (void)printf("\n"); | |
224 | } | |
225 | ||
226 | void | |
227 | user(pw) | |
d500843c | 228 | register struct passwd *pw; |
be1dd919 | 229 | { |
d500843c | 230 | register struct group *gr; |
be1dd919 | 231 | register char *fmt, **p; |
e157e33b | 232 | int cnt, id, lastid, ngroups, groups[NGROUPS + 1]; |
be1dd919 KB |
233 | |
234 | id = pw->pw_uid; | |
235 | (void)printf("uid=%u(%s)", id, pw->pw_name); | |
236 | (void)printf(" gid=%u", pw->pw_gid); | |
237 | if (gr = getgrgid(id)) | |
238 | (void)printf("(%s)", gr->gr_name); | |
e157e33b KM |
239 | ngroups = NGROUPS + 1; |
240 | (void) getgrouplist(pw->pw_name, pw->pw_gid, groups, &ngroups); | |
241 | fmt = " groups=%u"; | |
242 | for (lastid = -1, cnt = 0; cnt < ngroups; ++cnt) { | |
243 | if (lastid == (id = groups[cnt])) | |
be1dd919 | 244 | continue; |
e157e33b KM |
245 | (void)printf(fmt, id); |
246 | fmt = " %u"; | |
247 | if (gr = getgrgid(id)) | |
248 | (void)printf("(%s)", gr->gr_name); | |
249 | lastid = id; | |
be1dd919 KB |
250 | } |
251 | (void)printf("\n"); | |
252 | } | |
253 | ||
d500843c KB |
254 | void |
255 | group(pw, nflag) | |
256 | struct passwd *pw; | |
257 | int nflag; | |
258 | { | |
259 | struct group *gr; | |
524408bd | 260 | int cnt, id, lastid, ngroups, groups[NGROUPS + 1]; |
e157e33b | 261 | char *fmt; |
d500843c | 262 | |
d500843c | 263 | if (pw) { |
e157e33b KM |
264 | ngroups = NGROUPS + 1; |
265 | (void) getgrouplist(pw->pw_name, pw->pw_gid, groups, &ngroups); | |
d500843c KB |
266 | } else { |
267 | groups[0] = getgid(); | |
268 | ngroups = getgroups(NGROUPS, groups + 1) + 1; | |
e157e33b KM |
269 | } |
270 | fmt = nflag ? "%s" : "%u"; | |
271 | for (lastid = -1, cnt = 0; cnt < ngroups; ++cnt) { | |
272 | if (lastid == (id = groups[cnt])) | |
273 | continue; | |
274 | if (nflag) { | |
275 | if (gr = getgrgid(id)) | |
276 | (void)printf(fmt, gr->gr_name); | |
277 | else | |
278 | (void)printf(*fmt == ' ' ? " %u" : "%u", | |
279 | id); | |
280 | fmt = " %s"; | |
281 | } else { | |
282 | (void)printf(fmt, id); | |
283 | fmt = " %u"; | |
d500843c | 284 | } |
e157e33b | 285 | lastid = id; |
d500843c KB |
286 | } |
287 | (void)printf("\n"); | |
288 | } | |
289 | ||
290 | struct passwd * | |
be1dd919 KB |
291 | who(u) |
292 | char *u; | |
293 | { | |
d500843c | 294 | struct passwd *pw; |
be1dd919 KB |
295 | long id; |
296 | char *ep; | |
297 | ||
298 | /* | |
299 | * Translate user argument into a pw pointer. First, try to | |
300 | * get it as specified. If that fails, try it as a number. | |
301 | */ | |
302 | if (pw = getpwnam(u)) | |
303 | return(pw); | |
304 | id = strtol(u, &ep, 10); | |
305 | if (*u && !*ep && (pw = getpwuid(id))) | |
306 | return(pw); | |
307 | err("%s: No such user", u); | |
308 | /* NOTREACHED */ | |
309 | } | |
310 | ||
be1dd919 KB |
311 | #if __STDC__ |
312 | #include <stdarg.h> | |
313 | #else | |
314 | #include <varargs.h> | |
315 | #endif | |
316 | ||
317 | void | |
318 | #if __STDC__ | |
319 | err(const char *fmt, ...) | |
320 | #else | |
321 | err(fmt, va_alist) | |
322 | char *fmt; | |
323 | va_dcl | |
324 | #endif | |
325 | { | |
326 | va_list ap; | |
327 | #if __STDC__ | |
328 | va_start(ap, fmt); | |
329 | #else | |
330 | va_start(ap); | |
331 | #endif | |
332 | (void)fprintf(stderr, "id: "); | |
333 | (void)vfprintf(stderr, fmt, ap); | |
334 | va_end(ap); | |
335 | (void)fprintf(stderr, "\n"); | |
336 | exit(1); | |
337 | /* NOTREACHED */ | |
338 | } | |
339 | ||
340 | void | |
341 | usage() | |
342 | { | |
343 | (void)fprintf(stderr, "usage: id [user]\n"); | |
344 | (void)fprintf(stderr, " id -G [-n] [user]\n"); | |
345 | (void)fprintf(stderr, " id -g [-nr] [user]\n"); | |
346 | (void)fprintf(stderr, " id -u [-nr] [user]\n"); | |
347 | exit(1); | |
348 | } |