From bd3ae6f76744d30c943652c998b72309b5a0f6a9 Mon Sep 17 00:00:00 2001 From: gdr Date: Sat, 27 Jan 1996 22:38:42 +0000 Subject: [PATCH] Whereis version 1.1 for GNO. --- usr.bin/whereis/README | 62 +++++ usr.bin/whereis/makefile.mk | 23 ++ usr.bin/whereis/whereis.1 | 133 ++++++++++ usr.bin/whereis/whereis.c | 507 ++++++++++++++++++++++++++++++++++++ 4 files changed, 725 insertions(+) create mode 100644 usr.bin/whereis/README create mode 100644 usr.bin/whereis/makefile.mk create mode 100644 usr.bin/whereis/whereis.1 create mode 100644 usr.bin/whereis/whereis.c diff --git a/usr.bin/whereis/README b/usr.bin/whereis/README new file mode 100644 index 0000000..49b1091 --- /dev/null +++ b/usr.bin/whereis/README @@ -0,0 +1,62 @@ +whereis v1.1 (Gno) + +============ +INSTALLATION +============ + +If you have Gno and dmake, type "dmake install". Otherwise: + + FILE: COPY TO: + + Gno: Orca/whereis 17/whereis [if desired] + Gno/whereis /usr/bin/whereis + whereis.1 $(USRMAN)/man1/whereis.1 + + Orca: Orca/whereis 17/whereis + whereis.cat 17/help/whereis + +===== +NOTES +===== + +Whereis is VERY dependant on pathnames. + +This archive consist of both Orca shell and Gno versions. Both versions +will work with both shells, the difference being that in the Gno version +the leading "31" has been stripped from pathnames. (It is no longer needed +because of namespace.) + +I strongly recommend _not_ using the Gno version with the Orca shell unless +you have actual partitions named "/usr", "/bin", "/etc", and so on, as you +will get _many_ accesses to all online devices in this case. + +A -V flag and rVersion resource have been added to show version information. + +A -c flag has been added to provide case-insensitive searches. + +The source is released because it is small, and you can change the pathnames +if you wish. + +======= +HISTORY +======= + +v1.1: Rewritten to take advantage of Gno 2.x's namespace feature. + Separate Gno and Orca versions created. + Prototyped. + Disabled references to the /man volume (both versions). + Fixed up man page. + Added -V flag to show version information. + Added -c flag to force case-insensitive searches. + Added "17" to list of directories to search for binaries. + Added "17/help" to list of directories to search for man pages. + +v1.0: Initial release. + +======= +AUTHORS +======= + +Author of the original original port from BSD to Gno is unknown. (Jawaid?) + +v1.1 updated by G. Devin Reade diff --git a/usr.bin/whereis/makefile.mk b/usr.bin/whereis/makefile.mk new file mode 100644 index 0000000..206af58 --- /dev/null +++ b/usr.bin/whereis/makefile.mk @@ -0,0 +1,23 @@ +# makefile.mk generated by makedmake v0.22 (Gno v1.1) + +# development flags: Undefine __GNO__ to get a more Orca compatible version. +# CFLAGS = -i -w -s1023 -G25 -DDEBUG -DCASEFLAG -D__GNO__ +# LDLIBS = /usr/lib/stack.a +# LDFLAGS = + +# distribution flags: Undefine __GNO__ to get a more Orca compatible version. +CFLAGS = -i -w -s1023 -O -DCASEFLAG -D__GNO__ +LDLIBS = +LDFLAGS = + + +whereis : whereis.o + $(CC) $(LDFLAGS) -o whereis whereis.o $(LDLIBS) + +whereis.o : whereis.c + $(CC) $(CFLAGS) -c whereis.c + +install : + /bin/cp -f Gno/whereis /usr/bin + /bin/cp -f Orca/whereis 17 + /bin/cp -f whereis.1 /usr/man/man1 diff --git a/usr.bin/whereis/whereis.1 b/usr.bin/whereis/whereis.1 new file mode 100644 index 0000000..ca9898b --- /dev/null +++ b/usr.bin/whereis/whereis.1 @@ -0,0 +1,133 @@ +.\" @(#)whereis.1 1.17 90/02/15 SMI; from UCB 4.2 +.TH WHEREIS 1 "Commands and Applications" "2 January 1994" "Orca/Gno Version 1.1" +.SH NAME +whereis \- locate the binary, source, and manual page files for a command +.SH SYNOPSIS +.B whereis +[ +.B \-bcmsuV +] [ +.B \-BMS +.IR directory .\|.\|. +.B \-f +] +\fIfilename\fP\| +.SH DESCRIPTION +.B whereis +locates source/binary and manuals sections for specified +files. +The supplied names are first stripped of leading pathname components +and any (single) trailing extension of the form +.BR .ext , +for example, +.BR .c . +Prefixes of +.B s. +resulting from use of source code control are also dealt with. +.B whereis +then attempts to locate the desired program in +a list of standard places: +.RS +.nf +/bin +/usr/bin +/usr/sbin +/usr/games +/usr/include +/usr/hosts +/usr/local +/usr/local/bin +/etc +/man (disabled) +/usr/man +/usr/src/bin +/usr/src/etc +17/ +17/help +.fi +.RE +.SH OPTIONS +.B \-b +Search only for binaries. +.LP +.B \-c +Make the search case\-insensitive. +.LP +.B \-f +Terminate the last directory list and signals the start of file names, +and +.I must +be used when any of the +.BR \-B , +.BR \-M , +or +.B \-S +options are used. +.LP +.B \-m +Search only for manual sections. +.LP +.B \-s +Search only for sources. +.LP +.B \-u +Search for unusual entries. A file is said to be unusual if it does +not have one entry of each requested type. Therefore +.B "whereis -m -u *" +asks for those files in the current +directory which have no documentation. +.LP +.B \-B +Change or otherwise limit the places where +.B whereis +searches for binaries. +.LP +.B \-M +Change or otherwise limit the places where +.B whereis +searches for +manual sections. +.LP +.B \-S +Change or otherwise limit the places where +.B whereis +searches for sources. +.LP +.B \-V +Print version information. +.SH EXAMPLE +Find all files in +.B /usr/bin +which are not documented +in +.B /usr/share/man/man1 +with source in +.BR /usr/src/cmd : +.RS +.nf + +example% cd /usr/ucb +example% whereis \-u \-M /usr/share/man/man1 \-S /usr/src/cmd \-f * +.fi +.RE +.SH FILES +.nf +/usr/src/* +/usr/{doc,man}/* +/usr/{lib,bin,ucb,old,new,local} +/etc +.fi +.SH SEE ALSO +.BR chdir (2V) +.SH BUGS +Since +.B whereis +uses +.BR chdir (2V) +to run faster, pathnames given with the +.BR \-M , +.BR \-S , +or +.B \-B +must be full; that is, they must begin with a +.BR / . diff --git a/usr.bin/whereis/whereis.c b/usr.bin/whereis/whereis.c new file mode 100644 index 0000000..dc07f1b --- /dev/null +++ b/usr.bin/whereis/whereis.c @@ -0,0 +1,507 @@ +#ifdef __CCFRONT__ +#include <14:pragma.h> +#endif +/*- + * Copyright (c) 1980 The Regents of the University of California. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by the University of + * California, Berkeley and its contributors. + * 4. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#ifndef lint +char copyright[] = +"@(#) Copyright (c) 1980 The Regents of the University of California.\n\ + All rights reserved.\n"; +#endif /* not lint */ + +#ifndef lint +static char sccsid[] = "@(#)whereis.c 5.5 (Berkeley) 4/18/91"; +#endif /* not lint */ + +#include +#include +#include +#include +#include +#include +#include +#include + +#ifdef __GNO__ /* define this to use pathnames _without_ the leading 31/ */ +static char *bindirs[] = { + "/bin", + "/usr/bin", + "/usr/sbin", + "/usr/games", + "/usr/include", + "/usr/hosts", + "/usr/local", + "/usr/local/bin", + "17", + "/etc", + 0 +}; +/* This needs to be redone - man pages live with sources */ +static char *mandirs[] = { + +/* + These are disabled since /man is not usually present; this eliminates + a long series of accesses to the 3.5" drive. + + "/man/man1", + "/man/man2", + "/man/man3", + "/man/man4", + "/man/man5", + "/man/man6", + "/man/man7", + "/man/man8", + "/man/cat1", + "/man/cat2", + "/man/cat3", + "/man/cat4", + "/man/cat5", + "/man/cat6", + "/man/cat7", + "/man/cat8", +*/ + + "/usr/man/cat1", + "/usr/man/cat2", + "/usr/man/cat3", + "/usr/man/cat4", + "/usr/man/cat5", + "/usr/man/cat6", + "/usr/man/cat7", + "/usr/man/cat8", + "/usr/man/man1", + "/usr/man/man2", + "/usr/man/man3", + "/usr/man/man4", + "/usr/man/man5", + "/usr/man/man6", + "/usr/man/man7", + "/usr/man/man8", + "17/help", + 0 +}; +static char *srcdirs[] = { + "/usr/src/bin", + "/usr/src/etc", + /* still need libs */ + 0 +}; + +#else /* not __GNO__ */ + +static char *bindirs[] = { + "31/bin", + "31/usr/bin", + "31/usr/sbin", + "31/usr/games", + "31/usr/include", + "31/usr/hosts", + "31/usr/local", + "31/usr/local/bin", + "17", + "31/etc", + 0 +}; +/* This needs to be redone - man pages live with sources */ +static char *mandirs[] = { + +/* + These are disabled since /man is not usually present; this eliminates + a long series of accesses to the 3.5" drive. + + "31/man/man1", + "31/man/man2", + "31/man/man3", + "31/man/man4", + "31/man/man5", + "31/man/man6", + "31/man/man7", + "31/man/man8", + "31/man/cat1", + "31/man/cat2", + "31/man/cat3", + "31/man/cat4", + "31/man/cat5", + "31/man/cat6", + "31/man/cat7", + "31/man/cat8", +*/ + + "31/usr/man/cat1", + "31/usr/man/cat2", + "31/usr/man/cat3", + "31/usr/man/cat4", + "31/usr/man/cat5", + "31/usr/man/cat6", + "31/usr/man/cat7", + "31/usr/man/cat8", + "31/usr/man/man1", + "31/usr/man/man2", + "31/usr/man/man3", + "31/usr/man/man4", + "31/usr/man/man5", + "31/usr/man/man6", + "31/usr/man/man7", + "31/usr/man/man8", + "17/help", + 0 +}; +static char *srcdirs[] = { + "31/usr/src/bin", + "31/usr/src/etc", + /* still need libs */ + 0 +}; + +#endif /* not __GNO__ */ + +#ifdef CASEFLAG +int cflag = 0; +#endif + +char sflag = 1; +char bflag = 1; +char mflag = 1; +char **Sflag; +int Scnt; +char **Bflag; +int Bcnt; +char **Mflag; +int Mcnt; +char uflag; + +#ifdef __GNO__ +char *verstring = "whereis -- Gno/ME Version 1.1"; +#else +char *verstring = "whereis -- Orca Version 1.1"; +#endif + +void getlist (int *argcp, char ***argvp, char ***flagp, int *cntp); +void zerof(void); +void lookup (register char *cp); +void looksrc (char *cp); +void lookbin (char *cp); +void lookman (char *cp); +void findv (char **dirv, int dirc, char *cp); +void find (char **dirs, char *cp); +void findin (char *dir, char *cp); +int itsit (register char *cp, register char *dp); + +#ifdef DEBUG +void begin_stack_check(void); +int end_stack_check(void); +#endif + +/* + * whereis name + * look for source, documentation and binaries + */ +int main(int argc, char **argv) +{ + +#ifdef DEBUG + begin_stack_check(); +#endif + + argc--, argv++; + if (argc == 0) { +usage: + +#ifdef CASEFLAG + fprintf(stderr, "whereis [ -sbmucV ] [ -SBM dir ... -f ] name...\n"); +#else /* not CASEFLAG */ + fprintf(stderr, "whereis [ -sbmuV ] [ -SBM dir ... -f ] name...\n"); +#endif + +#ifdef DEBUG + if (getenv("CHECKSTACK")) + printf("Stack Usage: %d\n",end_stack_check()); +#endif + + exit(1); + } + do + if (argv[0][0] == '-') { + register char *cp = argv[0] + 1; + while (*cp) switch (*cp++) { + + case 'f': + break; + + case 'S': + getlist(&argc, &argv, &Sflag, &Scnt); + break; + + case 'B': + getlist(&argc, &argv, &Bflag, &Bcnt); + break; + + case 'M': + getlist(&argc, &argv, &Mflag, &Mcnt); + break; + + case 's': + zerof(); + sflag++; + continue; + + case 'u': + uflag++; + continue; + + case 'b': + zerof(); + bflag++; + continue; + + case 'm': + zerof(); + mflag++; + continue; + +#ifdef CASEFLAG + case 'c': + cflag++; + continue; +#endif /* not CASEFLAG */ + + case 'V': + printf("%s\n",verstring); + continue; + + default: + goto usage; + } + argv++; + } else + lookup(*argv++); + while (--argc > 0); + +#ifdef DEBUG + if (getenv("CHECKSTACK")) + printf("Stack Usage: %d\n",end_stack_check()); +#endif + + exit(0); +} + +void getlist (int *argcp, char ***argvp, char ***flagp, int *cntp) { + (*argvp)++; + *flagp = *argvp; + *cntp = 0; + for ((*argcp)--; *argcp > 0 && (*argvp)[0][0] != '-'; (*argcp)--) + (*cntp)++, (*argvp)++; + (*argcp)++; + (*argvp)--; +} + + +void zerof (void) { + + if (sflag && bflag && mflag) + sflag = bflag = mflag = 0; +} + +int count; +int print; + + +void lookup (register char *cp) { + register char *dp; + + for (dp = cp; *dp; dp++) + continue; + for (; dp > cp; dp--) { + if (*dp == '.') { + *dp = 0; + break; + } + } + for (dp = cp; *dp; dp++) + if (*dp == '/') + cp = dp + 1; + if (uflag) { + print = 0; + count = 0; + } else + print = 1; +again: + if (print) + printf("%s:", cp); + if (sflag) { + looksrc(cp); + if (uflag && print == 0 && count != 1) { + print = 1; + goto again; + } + } + count = 0; + if (bflag) { + lookbin(cp); + if (uflag && print == 0 && count != 1) { + print = 1; + goto again; + } + } + count = 0; + if (mflag) { + lookman(cp); + if (uflag && print == 0 && count != 1) { + print = 1; + goto again; + } + } + if (print) + printf("\n"); +} + +void looksrc (char *cp) { + if (Sflag == 0) { + find(srcdirs, cp); + } else + findv(Sflag, Scnt, cp); +} + +void lookbin (char *cp) { + if (Bflag == 0) + find(bindirs, cp); + else + findv(Bflag, Bcnt, cp); +} + +void lookman (char *cp) { + if (Mflag == 0) { + find(mandirs, cp); + } else + findv(Mflag, Mcnt, cp); +} + +void findv (char **dirv, int dirc, char *cp) { + while (dirc > 0) + findin(*dirv++, cp), dirc--; +} + +void find (char **dirs, char *cp) { + while (*dirs) + findin(*dirs++, cp); +} + +void findin (char *dir, char *cp) { + DIR *dirp; + struct dirent *dp; + + dirp = opendir(dir); + if (dirp == NULL) + return; + while ((dp = readdir(dirp)) != NULL) { + if (itsit(cp, dp->d_name)) { + count++; + if (print) + printf(" %s/%s", dir, dp->d_name); + } + } + closedir(dirp); +} + + +#ifdef CASEFLAG + +int itsit (register char *cp, register char *dp) { + register int i = strlen(dp); + + if (cflag) { + if ( (dp[0] == 's' || dp[0] == 'S') && dp[1] == '.' && itsit(cp, dp+2)) + return (1); + while (*cp && *dp && (tolower(*cp) == tolower(*dp))) + cp++, dp++, i--; + if (*cp == 0 && *dp == 0) + return (1); + while (isdigit(*dp)) + dp++; + if (*cp == 0 && *dp++ == '.') { + --i; +/* removed for GNO/ME, cause we want to look up compressed files also. */ +/* while (i > 0 && *dp) + if (--i, *dp++ == '.') + return (*dp++ == 'C' && *dp++ == 0); + */ + return (1); + } + } else { + if (dp[0] == 's' && dp[1] == '.' && itsit(cp, dp+2)) + return (1); + while (*cp && *dp && *cp == *dp) + cp++, dp++, i--; + if (*cp == 0 && *dp == 0) + return (1); + while (isdigit(*dp)) + dp++; + if (*cp == 0 && *dp++ == '.') { + --i; +/* removed for GNO/ME, cause we want to look up compressed files also. */ +/* while (i > 0 && *dp) + if (--i, *dp++ == '.') + return (*dp++ == 'C' && *dp++ == 0); + */ + return (1); + } + } + return (0); +} + +#else /* not CASEFLAG */ + +int itsit (register char *cp, register char *dp) { + register int i = strlen(dp); + + if (dp[0] == 's' && dp[1] == '.' && itsit(cp, dp+2)) + return (1); + while (*cp && *dp && *cp == *dp) + cp++, dp++, i--; + if (*cp == 0 && *dp == 0) + return (1); + while (isdigit(*dp)) + dp++; + if (*cp == 0 && *dp++ == '.') { + --i; +/* removed for GNO/ME, cause we want to look up compressed files also. */ +/* while (i > 0 && *dp) + if (--i, *dp++ == '.') + return (*dp++ == 'C' && *dp++ == 0);*/ + return (1); + } + return (0); +} + +#endif