xref: /original-bsd/old/whereis/whereis.c (revision 6c57d260)
1 static char *sccsid = "@(#)whereis.c	4.3 (Berkeley) 02/07/81";
2 #include <sys/types.h>
3 #include <stdio.h>
4 #include <ctype.h>
5 #include <sys/dir.h>
6 #include <whoami.h>
7 
8 static char *bindirs[] = {
9 	"/etc",
10 	"/bin",
11 	"/usr/bin",
12 	"/usr/games",
13 #ifdef CSVAX
14 	"/lib",
15 	"/usr/ucb",
16 	"/usr/lib",
17 	"/usr/local",
18 	"/usr/new",
19 	"/usr/old",
20 #endif
21 #ifdef CORY
22 	"/usr/bin/eecs",
23 	"/usr/bin/new",
24 	"/usr/bin/v7",
25 	"/usr/bin/old",
26 	"/usr/bin/UNSUPPORTED",
27 #endif
28 #ifdef ARPAVAX
29 	"/lib",
30 	"/usr/ucb",
31 	"/usr/lib",
32 	"/usr/local",
33 	"/usr/new",
34 	"/usr/old",
35 #endif
36 	0
37 };
38 static char *mandirs[] = {
39 	"/usr/man/man1",
40 	"/usr/man/man2",
41 	"/usr/man/man3",
42 	"/usr/man/man4",
43 	"/usr/man/man5",
44 	"/usr/man/man6",
45 	"/usr/man/man7",
46 	"/usr/man/man8",
47 #ifdef CORY
48 	"/usr/man/manu",
49 	"/usr/man/manc",
50 	"/usr/man/manv7",
51 	"/usr/bin/eecs/mane",
52 #endif
53 	0
54 };
55 static char *srcdirs[]  = {
56 	"/usr/src/cmd",
57 	"/usr/src/games",
58 	"/usr/src/libc/gen",
59 	"/usr/src/libc/stdio",
60 #ifdef CSVAX
61 	"/usr/src/libc/sys",
62 	"/usr/src/new",
63 	"/usr/src/old",
64 	"/usr/src/local",
65 	"/usr/src/undoc",
66 #endif
67 #ifdef CORY
68 	"/usr/bin/eecs/src",
69 	"/usr/src/cmd/v7",
70 	"/usr/src/cmd/new",
71 	"/usr/src/cmd/old",
72 	"/usr/src/cmd/UNSUPPORTED",
73 #endif
74 #ifdef	ARPAVAX
75 	"/ra/src/cmd",
76 	"/ra/src/new",
77 	"/ra/src/old",
78 	"/ra/src/libc/gen",
79 	"/ra/src/libc/stdio",
80 #endif
81 	0
82 };
83 
84 char	sflag = 1;
85 char	bflag = 1;
86 char	mflag = 1;
87 char	**Sflag;
88 int	Scnt;
89 char	**Bflag;
90 int	Bcnt;
91 char	**Mflag;
92 int	Mcnt;
93 char	uflag;
94 /*
95  * whereis name
96  * look for source, documentation and binaries
97  */
98 main(argc, argv)
99 	int argc;
100 	char *argv[];
101 {
102 
103 #ifdef CORY
104 	if (getuid() == 0)
105 		nice(-20);
106 	if (((getuid() >> 8) & 0377) > 10)
107 		setuid(getuid());
108 #endif
109 	argc--, argv++;
110 	if (argc == 0) {
111 usage:
112 		fprintf(stderr, "whereis [ -sbmu ] [ -SBM dir ... -f ] name...\n");
113 		exit(1);
114 	}
115 	do
116 		if (argv[0][0] == '-') {
117 			register char *cp = argv[0] + 1;
118 			while (*cp) switch (*cp++) {
119 
120 			case 'f':
121 				break;
122 
123 			case 'S':
124 				getlist(&argc, &argv, &Sflag, &Scnt);
125 				break;
126 
127 			case 'B':
128 				getlist(&argc, &argv, &Bflag, &Bcnt);
129 				break;
130 
131 			case 'M':
132 				getlist(&argc, &argv, &Mflag, &Mcnt);
133 				break;
134 
135 			case 's':
136 				zerof();
137 				sflag++;
138 				continue;
139 
140 			case 'u':
141 				uflag++;
142 				continue;
143 
144 			case 'b':
145 				zerof();
146 				bflag++;
147 				continue;
148 
149 			case 'm':
150 				zerof();
151 				mflag++;
152 				continue;
153 
154 			default:
155 				goto usage;
156 			}
157 			argv++;
158 		} else
159 			lookup(*argv++);
160 	while (--argc > 0);
161 }
162 
163 getlist(argcp, argvp, flagp, cntp)
164 	char ***argvp;
165 	int *argcp;
166 	char ***flagp;
167 	int *cntp;
168 {
169 
170 	(*argvp)++;
171 	*flagp = *argvp;
172 	*cntp = 0;
173 	for ((*argcp)--; *argcp > 0 && (*argvp)[0][0] != '-'; (*argcp)--)
174 		(*cntp)++, (*argvp)++;
175 	(*argcp)++;
176 	(*argvp)--;
177 }
178 
179 
180 zerof()
181 {
182 
183 	if (sflag && bflag && mflag)
184 		sflag = bflag = mflag = 0;
185 }
186 int	count;
187 int	print;
188 
189 
190 lookup(cp)
191 	register char *cp;
192 {
193 	register char *dp;
194 
195 	for (dp = cp; *dp; dp++)
196 		continue;
197 	for (; dp > cp; dp--) {
198 		if (*dp == '.') {
199 			*dp = 0;
200 			break;
201 		}
202 	}
203 	for (dp = cp; *dp; dp++)
204 		if (*dp == '/')
205 			cp = dp + 1;
206 	if (uflag) {
207 		print = 0;
208 		count = 0;
209 	} else
210 		print = 1;
211 again:
212 	if (print)
213 		printf("%s:", cp);
214 	if (sflag) {
215 		looksrc(cp);
216 		if (uflag && print == 0 && count != 1) {
217 			print = 1;
218 			goto again;
219 		}
220 	}
221 	count = 0;
222 	if (bflag) {
223 		lookbin(cp);
224 		if (uflag && print == 0 && count != 1) {
225 			print = 1;
226 			goto again;
227 		}
228 	}
229 	count = 0;
230 	if (mflag) {
231 		lookman(cp);
232 		if (uflag && print == 0 && count != 1) {
233 			print = 1;
234 			goto again;
235 		}
236 	}
237 	if (print)
238 		printf("\n");
239 }
240 
241 looksrc(cp)
242 	char *cp;
243 {
244 	if (Sflag == 0) {
245 		find(srcdirs, cp);
246 	} else
247 		findv(Sflag, Scnt, cp);
248 }
249 
250 lookbin(cp)
251 	char *cp;
252 {
253 	if (Bflag == 0)
254 		find(bindirs, cp);
255 	else
256 		findv(Bflag, Bcnt, cp);
257 }
258 
259 lookman(cp)
260 	char *cp;
261 {
262 	if (Mflag == 0) {
263 		find(mandirs, cp);
264 	} else
265 		findv(Mflag, Mcnt, cp);
266 }
267 
268 findv(dirv, dirc, cp)
269 	char **dirv;
270 	int dirc;
271 	char *cp;
272 {
273 
274 	while (dirc > 0)
275 		findin(*dirv++, cp), dirc--;
276 }
277 
278 find(dirs, cp)
279 	char **dirs;
280 	char *cp;
281 {
282 
283 	while (*dirs)
284 		findin(*dirs++, cp);
285 }
286 
287 findin(dir, cp)
288 	char *dir, *cp;
289 {
290 	register FILE *d;
291 	struct direct direct;
292 
293 	d = fopen(dir, "r");
294 	if (d == NULL)
295 		return;
296 	while (fread(&direct, sizeof direct, 1, d) == 1) {
297 		if (direct.d_ino == 0)
298 			continue;
299 		if (itsit(cp, direct.d_name)) {
300 			count++;
301 			if (print)
302 				printf(" %s/%.14s", dir, direct.d_name);
303 		}
304 	}
305 	fclose(d);
306 }
307 
308 itsit(cp, dp)
309 	register char *cp, *dp;
310 {
311 	register int i = 14;
312 
313 	if (dp[0] == 's' && dp[1] == '.' && itsit(cp, dp+2))
314 		return (1);
315 	while (*cp && *dp && *cp == *dp)
316 		cp++, dp++, i--;
317 	if (*cp == 0 && *dp == 0)
318 		return (1);
319 	while (isdigit(*dp))
320 		dp++;
321 	if (*cp == 0 && *dp++ == '.') {
322 		--i;
323 		while (i > 0 && *dp)
324 			if (--i, *dp++ == '.')
325 				return (*dp++ == 'C' && *dp++ == 0);
326 		return (1);
327 	}
328 	return (0);
329 }
330