11590Srgrimes/*
21590Srgrimes * Copyright (c) 1980, 1988, 1993
31590Srgrimes *	The Regents of the University of California.  All rights reserved.
41590Srgrimes *
51590Srgrimes * Redistribution and use in source and binary forms, with or without
61590Srgrimes * modification, are permitted provided that the following conditions
71590Srgrimes * are met:
81590Srgrimes * 1. Redistributions of source code must retain the above copyright
91590Srgrimes *    notice, this list of conditions and the following disclaimer.
101590Srgrimes * 2. Redistributions in binary form must reproduce the above copyright
111590Srgrimes *    notice, this list of conditions and the following disclaimer in the
121590Srgrimes *    documentation and/or other materials provided with the distribution.
131590Srgrimes * 4. Neither the name of the University nor the names of its contributors
141590Srgrimes *    may be used to endorse or promote products derived from this software
151590Srgrimes *    without specific prior written permission.
161590Srgrimes *
171590Srgrimes * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
181590Srgrimes * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
191590Srgrimes * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
201590Srgrimes * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
211590Srgrimes * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
221590Srgrimes * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
231590Srgrimes * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
241590Srgrimes * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
251590Srgrimes * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
261590Srgrimes * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
271590Srgrimes * SUCH DAMAGE.
281590Srgrimes */
291590Srgrimes
3087677Smarkm#include <sys/cdefs.h>
3187677Smarkm
3287677Smarkm__FBSDID("$FreeBSD$");
3387677Smarkm
341590Srgrimes#ifndef lint
3528697Scharnierstatic const char copyright[] =
361590Srgrimes"@(#) Copyright (c) 1980, 1988, 1993\n\
371590Srgrimes	The Regents of the University of California.  All rights reserved.\n";
3887677Smarkm#endif
391590Srgrimes
401590Srgrimes#ifndef lint
4187677Smarkmstatic const char sccsid[] = "@(#)what.c	8.1 (Berkeley) 6/6/93";
4228697Scharnier#endif
431590Srgrimes
4428697Scharnier#include <err.h>
45146163Sjmallett#include <stdbool.h>
461590Srgrimes#include <stdio.h>
4735725Srnordier#include <stdlib.h>
4835725Srnordier#include <unistd.h>
491590Srgrimes
5092922Simpstatic void usage(void);
51146163Sjmallettstatic bool search(bool, bool, FILE *);
5228697Scharnier
5328697Scharnierint
54146163Sjmallettmain(int argc, char *argv[])
551590Srgrimes{
56146163Sjmallett	const char *file;
57146163Sjmallett	FILE *in;
58146163Sjmallett	bool found, qflag, sflag;
5935725Srnordier	int c;
6035725Srnordier
61146163Sjmallett	qflag = sflag = false;
62146163Sjmallett
63146163Sjmallett	while ((c = getopt(argc, argv, "qs")) != -1) {
6435725Srnordier		switch (c) {
65146163Sjmallett		case 'q':
66146163Sjmallett			qflag = true;
67146163Sjmallett			break;
6835725Srnordier		case 's':
69146163Sjmallett			sflag = true;
7035725Srnordier			break;
7135725Srnordier		default:
7258626Scharnier			usage();
7335725Srnordier		}
74146163Sjmallett	}
75146163Sjmallett	argc -= optind;
7635725Srnordier	argv += optind;
7735725Srnordier
78146163Sjmallett	found = false;
79146163Sjmallett
80146163Sjmallett	if (argc == 0) {
81146163Sjmallett		if (search(sflag, qflag, stdin))
82146163Sjmallett			found = true;
83146163Sjmallett	} else {
84146163Sjmallett		while (argc--) {
85146163Sjmallett			file = *argv++;
86146163Sjmallett			in = fopen(file, "r");
87146163Sjmallett			if (in == NULL) {
88146163Sjmallett				if (!qflag)
89146163Sjmallett					warn("%s", file);
90146163Sjmallett				continue;
91146163Sjmallett			}
92146163Sjmallett			if (!qflag)
93146163Sjmallett				printf("%s:\n", file);
94146163Sjmallett			if (search(sflag, qflag, in))
95146163Sjmallett				found = true;
96146163Sjmallett			fclose(in);
9735725Srnordier		}
98146163Sjmallett	}
99146163Sjmallett	exit(found ? 0 : 1);
1001590Srgrimes}
1011590Srgrimes
10258626Scharnierstatic void
103102944Sdwmaloneusage(void)
10458626Scharnier{
105146163Sjmallett	fprintf(stderr, "usage: what [-qs] [file ...]\n");
10658626Scharnier	exit(1);
10758626Scharnier}
10858626Scharnier
109146163Sjmallettbool
110146163Sjmallettsearch(bool one, bool quiet, FILE *in)
1111590Srgrimes{
112146163Sjmallett	bool found;
113102944Sdwmalone	int c;
1141590Srgrimes
115146163Sjmallett	found = false;
116146163Sjmallett
117146163Sjmallett	while ((c = getc(in)) != EOF) {
1181590Srgrimesloop:		if (c != '@')
1191590Srgrimes			continue;
120146163Sjmallett		if ((c = getc(in)) != '(')
1211590Srgrimes			goto loop;
122146163Sjmallett		if ((c = getc(in)) != '#')
1231590Srgrimes			goto loop;
124146163Sjmallett		if ((c = getc(in)) != ')')
1251590Srgrimes			goto loop;
126146163Sjmallett		if (!quiet)
127146163Sjmallett			putchar('\t');
128146163Sjmallett		while ((c = getc(in)) != EOF && c && c != '"' &&
12935725Srnordier		    c != '>' && c != '\\' && c != '\n')
1301590Srgrimes			putchar(c);
1311590Srgrimes		putchar('\n');
132146163Sjmallett		found = true;
133146163Sjmallett		if (one)
134146163Sjmallett			break;
1351590Srgrimes	}
136146163Sjmallett	return (found);
1371590Srgrimes}
138