Mail Archives: djgpp/1995/06/19/12:55:19
Xref: | news-dnh.mv.net comp.os.msdos.djgpp:444
|
Path: | news-dnh.mv.net!mv!news.sprintlink.net!cs.utexas.edu!convex!not-for-mail
|
From: | rosenkra AT convex DOT com (William Rosenkranz)
|
Newsgroups: | comp.os.msdos.djgpp
|
Subject: | whatis(1) system (part01/02)
|
Date: | 19 Jun 1995 00:13:10 -0500
|
Organization: | Engineering, Convex Computer Corporation, Richardson, Tx USA
|
Lines: | 3418
|
Nntp-Posting-Host: | convex1.convex.com
|
Summary: | unix whatis system
|
Keywords: | unix manual man whatis apropos
|
To: | djgpp AT sun DOT soe DOT clarkson DOT edu
|
Dj-Gateway: | from newsgroup comp.os.msdos.djgpp
|
whatis (part01/02)
this is a whatis(1) system. it is used in conjunction with man(1) that
i also posted. man is standalone, but without apropos and whatis, the
-k and -f switches in man will not work.
-bill rosenkranz
rosenkra AT convex DOT com
---------------------------- cut here ----------------------------
# This is a shell archive. Remove anything before this line,
# then unpack it by saving it in a file and typing "sh file".
#
# Wrapped by William Rosenkranz <rosenkra AT det_hp> on Mon Jun 19 00:41:03 1995
#
# This archive contains:
# whatis
#
# Error checking via sum(1) will be performed.
LANG=""; export LANG
PATH=/bin:/usr/bin:$PATH; export PATH
if sum -r </dev/null >/dev/null 2>&1
then
sumopt='-r'
else
sumopt=''
fi
echo mkdir - whatis
mkdir whatis
echo x - whatis/README.all
cat >whatis/README.all <<'@EOF'
README (man, whatis, 95/06/18)
------------------------------
someone (stanb AT netcom DOT com) had asked for a man(1) command for reading
manpages. i am posting such a system which includes:
man - read online manpages
apropos - list relevant manpages on a given topic (same as "man -k word")
whatis - give 1-line description of a command (same as "man -f word")
whatisin - list information about what is in sections of the manual
mkwhatis - tool to help build whatis database
note that man does not have its own pager. man calls the pager and
gives it a filename. what man does is find the file (in known places)
and figures out what to run (pager, whatis, apropos, etc.). in this
regard it is really pretty simple minded. the hard part is getting,
organizing, formatting, and maintaining the manpages. for example, i
have hundreds of manpages on my systems. the typical unix system might
have over a thousand manpages.
these programs function more or less the same as the unix (BSD) commands
with some exceptions:
- man does not invoke nroff. your manpages should be preformatted.
- every unix flavor has its own way of doing man so some of the
switches on these commands may not correspond with all unix
(or posix) ways of dealing with this.
- the whatis database itself is different than how unix does it.
but it is similar, and no two unix systems do it the same
anyway.
as it stands, these programs assumes the following directory structure:
c:\usr\man main location of manpages, whatis db, etc
c:\usr\man\man[0-9lno] dirs containing *unformatted* manpages)
c:\usr\man\cat[0-9lno] dirs containing *formatted* manpages)
c:\usr\man\whatis._?_ whatis databases for each section (you
have to build these based on your collection
of manpages)
c:\usr\man\whatisin.___ whatisin database
man will ONLY look in the cat* directories, and does not format the manpages.
you will need nroff for this (cawf, groff, etc). i also have an nroff
that i wrote years ago that is PD. or you can format the manpages on a unix
system and download them to your PC.
everything is configurable, both in the source and via the environment.
for example, the c:\usr\man path can be overridded with:
- setting environment variable MANPATH
- using the commandline switch "-M path" on each command
- changing the executables with a binary editor (i have left
space in the source for such patches)
- changing the source and recompiling
caveats:
- i am providing this free, with no restrictions. it is 100% my
code (does not contain any unix code).
- i will not help in any way to fix anything or add new features.
this system runs fine under both Unix and on my atari ST (with
gcc) so it should port easily, though i have not tried it under
DOS or with djgpp.
- i will not reformat the source to correspond to someone's notion
of style. this is my prefered style, after 10 years of C coding
and 20 years of fortran coding. :-)
- if you don't like it, either a) fix it yourself, or b) don't use
it. it is free, after all.
Install:
- Unpack everything into separate directories (./man, ./whatis).
- The files are all ascii (no binary files). there are no CF-LF
(just LF) so if you need CR-LF, you have to fix this yourself.
- go to each dir (./man and ./whatis) and look at the makefile.
change (at least) the following for your particular setup:
CC how to invoke compiler
LD how to link .o files
MANTOP main location to place manpages (install)
MANDIR specific location for manpage source
CATDIR specific location for formatted manpages
BINDIR location to install executables (man,
whatis, etc)
DEFS in man, you should specify what you have
available (eg, if you have ul(1) and want
the -ul switch to function, define HAS_UL).
you probably want to define MSDOS, __GNUC__,
and possibly undefine unix.
in general, check all the macros in upper case in the
makefile. note that i could have used sed in the makefile
to patch names in the program, but i don't know how good
make is on the PC.
- man invokes the PAGER and other programs via the system(3) call.
on unix (and on my atari), system will search PATH for executables
so you don't need a full path. if this is not the case with djgpp,
then you will have to alter ./man/man.c to build a full path
for executing PAGER, cat, ul, whatis, apropos, etc.
- type:
make all will build the executables
make install will install the execs and manpages
make clobber will clean up after the make all.
you may also consider doing "make dirs" before make install
when building man. this creates the directory structure.
you should do man before whatis.
- if successful, you should be all set. i have provided formatted
manpages (man.1, whatis.1, whatis.5, apropos.1, whatisin.1) from
the manpage sources (man.man, whatis.man, whatis.ma5, etc). these
were piped through "ul -t dumb" to remove any bold/underline
escape sequences. so the formatted manpages are pure ascii. if
you have a PAGER that groks how to handle nroff bold, etc, then
you may want to reformat the manpages.
you should at a minimum build man. it will allow you to read manpages.
if you are up for it, the whatis capability might be desirable. whatis
contains a 1-line description of every manpage you have on your system.
for more information, see the file ./whatis/whatis.5 and whatis.1.
note: i have not included any manpages here other than those for these
programs themselves. don't ask me for a manpage on ls(1).
Environment:
these programs recognize several environment variables:
MANPAGER man if set, this pager is used by man. on my
atari, i have a special pager that resets
fonts, based on what -T does in nroff on
my system. this gives me bold, etc.
PAGER man if MANPAGER is not set, this pager is used.
the default is less.
MANPATH man, location of the manpages, top level. the
whatis default is c:\usr\man. at the moment, MANPATH
apropos is a single path, not a list.
whatisin
for more, grep the sources for "getenv" or read the manpages.
note that man will invoke other programs as follows (using system(3)):
man file PAGER
man -k word apropos
man -f name whatis
you can also invoke apropos and whatis by themselves, of course.
that's about all i have time for. have fun...
-bill rosenkranz
rosenkra AT convex DOT com
@EOF
set `sum $sumopt <whatis/README.all`; if test $1 -ne 9384
then
echo ERROR: whatis/README.all checksum is $1 should be 9384
fi
chmod 644 whatis/README.all
rm -f /tmp/uud$$
(echo "begin 666 /tmp/uud$$\n#;VL*n#6%@x\n \nend" | uudecode) >/dev/null 2>&1
if [ X"`cat /tmp/uud$$ 2>&1`" = Xok ]
then
unpacker=uudecode
else
echo Compiling unpacker for non-ascii files
pwd=`pwd`; cd /tmp
cat >unpack$$.c <<'EOF'
#include <stdio.h>
#define C (*p++ - ' ' & 077)
main()
{
int n;
char buf[128], *p, a,b;
scanf("begin %o ", &n);
gets(buf);
if (freopen(buf, "w", stdout) == NULL) {
perror(buf);
exit(1);
}
while (gets(p=buf) && (n=C)) {
while (n>0) {
a = C;
if (n-- > 0) putchar(a << 2 | (b=C) >> 4);
if (n-- > 0) putchar(b << 4 | (a=C) >> 2);
if (n-- > 0) putchar(a << 6 | C);
}
}
exit(0);
}
EOF
cc -o unpack$$ unpack$$.c
rm unpack$$.c
cd $pwd
unpacker=/tmp/unpack$$
fi
rm -f /tmp/uud$$
echo x - whatis/README '[non-ascii]'
$unpacker <<'@eof'
begin 644 whatis/README
M=VAA=&ES+"!W:&%T:7-I;BP AT 87!R;W!O<R!V,BXP+C$@.3(O.2\Q,PT*+2TMX
M+2TM+2TM+2TM+2TM+2TM+2TM+2TM+2TM+2TM+2TM+2TM+2TM+0T*#0I(97)EX
M(&ES(&%N(&EM<&QE;65N=&%T:6]N(&]F('=H871I<R AT Q*2P@=VAA=&ES:6XHX
M,2DL(&%N9"!A<')O<&]S*#$I+@T*5&AE<V4@=V5R92!A;&P AT 8G5I;'0@=VETX
M:"!G8V,@,2XT,"!W:71H($UI3E0@;&EB<R!A="!03" Q DOT 2X AT 270@:&%S(&)EX
M96X-"G1E<W1E9"!O;B!43U,@,2XR(')U;FYI;F<@36E.5" P+CDT+B!)="!DX
M;V5S(&YO="!U<V4 AT 86YY($UI3E0M<W!E8VEF:6,-"F9U;F-T:6]N<R!S;R!IX
M="!S:&]U;&0@<G5N('5N9&5R(%1/4R!A;&]N92 H=6YT97-T960I+@T*#0I4X
M:&ES('-H;W5L9"!J=7-T(&%B;W5T(&-O;7!L971E(&%N(&]N;&EN92!D;V-UX
M;65N=&%T:6]N('-Y<W1E;2!C;VYS:7-T:6YG#0IO9CH-"@T*"6YR;V9F"0ETX
M97AT(&9O<FUA='1E<B H9F]R(&UA;G!A9V5S*0T*"6UA;@D);6%N=6%L(")FX
M<F]N="!E;F0B#0H);6%N<&%G97()9FEL92!V:65W97(-"@EA<')O<&]S"0EGX
M:79E;B!K97EW;W)D+"!F:6YD(&%P<')O<')I871E(&1O8W5M96YT871I;VX-X
M"@EW:&%T:7-I;@EF:6YD(&]U="!W:&%T(&ES(&EN(&5A8V@@<V5C=&EO;B!OX
M9B!T:&4@;6%N=6%L#0H)=VAA=&ES"0EG970@<W5M;6%R>2!O9B!W:&%T(&$@X
M8V]M;6%N9"P AT 971C+B!I<PT*#0I.;W1E('1H870@=&AE(&YR;V9F($D@:G5SX
M="!P;W-T960@;&%S="!W965K("A^.3(O.2\Q,2D@=&\@871A<FDN87)C:&EVX
M90T*<W5P<&]R=',@=&AE("YT;2!M86-R;R!A;F0@:&5N8V4@=&AE("Y)6"!MX
M86X@;6%C<F\@:7,@:6UP;&5M96YT960N(%1H:7,-"FES('5S969U;"!F;W(@X
M8W)E871I;F<@:6YD97@@96YT<FEE<RX AT 66]U(&-O=6QD+"!I;B!T:&5O<GDLX
M('=R:71E(&$@;6%C<F\-"G1H870@=V]U;&0 AT 9V5N97)A=&4 AT 86X@=VAA=&ESX
M(&1A=&%B87-E(&5N=')Y(&5A8V@@=&EM92!A(&UA;G!A9V4@=V%S#0IF;W)MX
M871T960N("YT;2!W<FET97,@=&\@<W1D97)R('=H:6QE(&YR;V9F(&]T:&5RX
M=VES92!W<FET97,@=&\@<W1D;W5T+@T*#0H-"DUA;FEF97-T#0HM+2TM+2TMX
M+0T*#0H)87!R;W!O<RXQ>@EC;VUP<F5S<V5D+"!F;W)M871T960@;6%N<&%GX
M92 H;6%N<&%G97(@9F]R;6%T*0T*"6%P<F]P;W,N8PES;W5R8V4-"@EA<')OX
M<&]S+FUA;@EN<F]F9B!S;W5R8V4 AT 9F]R(&UA;G!A9V4-"@EA<')O<&]S+G1TX
M< EE>&5C=71A8FQE#0H)8V]M;6]N+F,)8V]M;6]N('-O=7)C92!C;V1E(&9OX
M<B!A;&P@<')O9W)A;7,-"@EM86ME9FEL90EW:&%T('4 AT 97AP96-T#0H);6MWX
M:&%T:7,N.'H)8V]M<')E<W-E9"P AT 9F]R;6%T=&5D(&UA;G!A9V4@*&UA;G!AX
M9V5R(&9O<FUA="D-"@EM:W=H871I<RYC"7-O=7)C92!F;W(@=&]O;"!T;R!HX
M96QP(&)U:6QD(&1A=&%B87-E<PT*"6UK=VAA=&ES+FUA. EN<F]F9B!S;W5RX
M8V4 AT 9F]R(&UA;G!A9V4-"@EM:W=H871I<RYT=' )97AE8W5T86)L90T*"7=HX
M871I<RXQ>@EC;VUP<F5S<V5D+"!F;W)M871T960@;6%N<&%G92 H;6%N<&%GX
M97(@9F]R;6%T*0T*"7=H871I<RXU>@EC;VUP<F5S<V5D+"!F;W)M871T960 AT X
M;6%N<&%G92 H;6%N<&%G97(@9F]R;6%T*0T*"7=H871I<RY?,5\)97AA;7!LX
M92!D871A8F%S97,@*&UA;G5A;"!S96-T:6]N(#$I#0H)=VAA=&ES+E\R7PD AT X
M(" B(" @(" @(" B(" @(" H;6%N=6%L('-E8W1I;VX@,BD-"@EW:&%T:7,NX
M7S1?"2 @("(@(" @(" @("(@(" @("AM86YU86P@<V5C=&EO;B T*0T*"7=HX
M871I<RY?-5\)(" @(B @(" @(" @(B @(" @*&UA;G5A;"!S96-T:6]N(#4IX
M#0H)=VAA=&ES+E\W7PD@(" B(" @(" @(" B(" @(" H;6%N=6%L('-E8W1IX
M;VX AT -RD-"@EW:&%T:7,N7SA?"2 @("(@(" @(" @("(@(" @("AM86YU86P AT X
M<V5C=&EO;B X*0T*"7=H871I<RYC"7-O=7)C90T*"7=H871I<RYH"6-O;6UOX
M;B!H96%D97(@9FEL90T*"7=H871I<RYM834);G)O9F8@<V]U<F-E(&9O<B!MX
M86YP86=E#0H)=VAA=&ES+FUA;@EN<F]F9B!S;W5R8V4 AT 9F]R(&UA;G!A9V4-X
M"@EW:&%T:7,N='1P"65X96-U=&%B;&4-"@EW:&%T:7-I;BXQ>@EC;VUP<F5SX
M<V5D+"!F;W)M871T960@;6%N<&%G92 H;6%N<&%G97(@9F]R;6%T*0T*"7=HX
M871I<VEN+E]?7PED871A(&9I;&4 AT 9F]R('=H871I<VEN#0H)=VAA=&ES:6XNX
M8PES;W5R8V4-"@EW:&%T:7-I;BYM86X);G)O9F8@<V]U<F-E(&9O<B!M86YPX
M86=E#0H)=VAA=&ES:6XN='1P"65X96-U=&%B;&4-"@T*#0I);G-T86QL871IX
M;VX-"BTM+2TM+2TM+2TM+0T*#0I9;W4@=VEL;"!N965D('1O('-E="!A;B!EX
M;G9I<F]N;65N="!V87)I86)L92P AT 34%.4$%42"P@=&\@=&AE(&1I<F5C=&]RX
M>0T*=VAI8V@@=VEL;"!C;VYT86EN('1H92!D871A8F%S97,N(%1H:7,@:7,@X
M=&AE('-A;64 AT 96YV:7)O;FUE;G0@=F%R:6%B;&4-"G5S960 AT 8GD@;6%N*#$IX
M("AM:6YE+"!A="!L96%S="DN($EF('EO=2!D;VXG="!S970@:70@*&%N9"!IX
M9B!Y;W4 AT 9&]N)W0-"F]V97)R:61E('=I=&@@=&AE("U0('-W:71C:"!O;B!TX
M:&5S92!C;VUM86YD<RDL('1H92!D969A=6QT(&1I<F5C=&]R>2!I<PT*9#I<X
M=7-R7&UA;BX-"@T*4V\@<'5T('1H:7,@:6X@>6]U<B!S:&5L;"=S('-T87)TX
M=7 @9FEL93H-"@T*"7-E=&5N=B!-04Y0051(('!A=&@-"@T*=VAE<F4@<&%TX
M:"!I<R!T:&4 AT 9&ER96-T;W)Y+@T*#0I4:&5N(&-O<'D@=VAA=&ES+E\_7R!AX
M;F0@=VAA=&ES:6XN7U]?(&9I;&5S('1H97)E+@T*#0I#;W!Y('1H92!E>&5CX
M=71A8FQE<R!T;R!Y;W5R(&)I;B!D:7)E8W1O<GDN($EF('EO=2!H879E(&]NX
M92P@>6]U('-H;W5L9 T*<')O8F%B;'D AT 8V]P>2!M:W=H871I<RYT=' @=&\@X
M>6]U<B O971C(&1I<F5C=&]R>2!I;G-T96%D+B!)="!I<R!R96%L;'D-"FUOX
M<F4@;V8 AT 86X@861M:6YI<W1R871I;VX AT 8V]M;6%N9"X-"@T*#0I"=6EL9&ENX
M9R!W:&%T:7,@1&%T86)A<V5S#0HM+2TM+2TM+2TM+2TM+2TM+2TM+2TM+2TMX
M#0H-"DD@:&%V92!I;F-L=61E9"!S979E<F%L(&]F(&UY(&]W;B!W:&%T:7,@X
M9&%T86)A<V5S(&AE<F4N(%1H97D@=V5R92!A;&P-"F)U:6QT('5S:6YG('1HX
M92!M:W=H871I<R!P<F]G<F%M("AA;'-O(&EN8VQU9&5D*2!T:&]U9V@@=&AEX
M<F4@=V%S('-O;64-"FAA;F0 AT 961I=&EN9R!I;G9O;'9E9" H:2YE+BP@=&\@X
M861D(&ME>7=O<F0 AT 9FEE;&1S*2X-"@T*;6MW:&%T:7,@:7,@9VEV96X AT 82!LX
M:7-T(&]F(&9I;&4@;F%M97,@=VAI8V@@87)E(&UA;G!A9V4@<V]U<F-E(&9IX
M;&5S#0HH:2YE+BP@;G)O9F8@+6UA;BDN($ET('=I;&P@<W!E=R!O=70 AT 82!PX
M<F5T='D AT 9V]O9"!A='1E;7!T(&%T(&9O<FUA='1I;F<-"F5N=')I97,@9F]RX
M('1H92!D871A8F%S92X AT 1F]R(&1E=&%I;',@;VX@=&AE(&9O<FUA="!O9B!TX
M:&4 AT 9&%T86)A<V4L('-E90T*=&AE(&1O8W5M96YT871I;VX@:6X@=VAA=&ESX
M*#4I+"!M:W=H871I<R AT X*2P AT 86YD(&UK=VAA=&ES+F,N#0H-"DD AT 9&5C:61EX
M9"!T;R!D:79E<F=E(&9R;VT@=6YI>" H0E-$*2!P<F%C=&EC92!A;F0@:6YCX
M;'5D92!A('-E<&%R871E(&9I;&4-"F9O<B!E86-H('-E8W1I;VX@;V8@=&AEX
M(&UA;G5A;"X AT 5&\@<V5E('=H870@=&AE('-E8W1I;VYS(&%R92P@<V5E('1HX
M92!F:6QE#0IW:&%T:7-I;BY?7U\@*'=H:6-H(&ES('1H92!D871A(&9I;&4 AT X
M9F]R('=H871I<VEN*2X-"@T*5'EP:6-A;&QY+"!Y;W4@<VAO=6QD(&)E(&%BX
M;&4@=&\@;6]V92!T;R!T:&4 AT 9&ER96-T;W)Y*&EE<RD AT 8V]N=&%I;FEN9PT*X
M>6]U<B!U;F9O<FUA='1E9"!M86YP86=E<R!A;F0 AT 9&\Z#0H-"@EC9"!M86XQX
M#0H);6MW:&%T:7,@*BYM86X@/B!W:&%T:7,N7S%?#0H)8V0@+BXO;6%N,@T*X
M"6UK=VAA=&ES("HN;6%N(#X@=VAA=&ES+E\R7PT*"6-D("XN+VUA;C,-"@EMX
M:W=H871I<R J+FUA;B ^('=H871I<RY?,U\-"@EE=&,N+BX-"@T*5&AE<F4 AT X
M:7,@;F\@8V]M;6%N9"!L:6YE(&]P=&EO;B!T;R!R96YA;64@=&AE(&1A=&%BX
M87-E(&9I;&4N($EF('EO=2!W86YT#0IT;R!D;R!T:&%T('EO=2!W:6QL(&AAX
M=F4@=&\@<F5C;VUP:6QE+@T*#0IW:&%T:7,L(&%P<F]P;W,L(&%N9"!W:&%TX
M:7-I;B!R96-O9VYI>F4@<V5C=&EO;G,@9G)O;2!T:&ES(&QI<W0Z#0H-"@DPX
M"6=E;F5R86P@:6YF;PT*"3$)8V]M;6%N9',-"@DR"7-Y<W1E;2!C86QL<PT*X
M"3,);&EB<F%R>2!F=6YC=&EO;G,-"@DT"61E=FEC97,L(&AA<F1W87)E+"!DX
M<FEV97)S+"!E=&,N#0H)-0EF:6QE(&9O<FUA=',-"@DV"6=A;65S#0H)-PEMX
M:7-C#0H). ES>7,@861M:6X AT 8V]M;6%N9',-"@DY"75N=7-E9 T*"6P);&]CX
M86P-"@EN"6YE=PT*"6\);VQD#0H-"E1O(&-H86YG92!T:&ES(&QI<W0L(&-HX
M86YG92!314-424].4R!M86-R;R!I;B!W:&%T:7,N:"!A;F0 AT 8VAA;F=E('=HX
M871I<VEN+E]?7PT*9FEL92X AT 5&AE<V4@<V5C=&EO;G,@87)E(&YO<FUA;"!UX
M;FEX(&-O;G9E;G1I;VXL(&)U="!Y;W4 AT 8V%N('5S92!T:&5M(&EN(&%N>0T*X
M;W1H97(@=V%Y('EO=2!W86YT+@T*#0H-"D5N:F]Y+BXN#0H-"D)I;&P AT 4F]SX
@96YK<F%N>@T*<F]S96YK<F% 8V]N=F5X+F-O;0T*#0HN X
X
end
@eof
set `sum $sumopt <whatis/README`; if test $1 -ne 1503
then
echo ERROR: whatis/README checksum is $1 should be 1503
fi
chmod 644 whatis/README
echo x - whatis/apropos.1
cat >whatis/apropos.1 <<'@EOF'
APROPOS(1) APROPOS(1)
NAME
apropos - find pertinent online documentation
SYNOPSIS
apropos [ -P path ] [ -s section ] word...
DESCRIPTION
The apropos command displays a one line synopsis of each online
documentation file whose name or description contains a specified word
or whose keywords listed in the whatis databases matches the specified
word. Once you know what you are looking for, use man(1) to read the
appropriate documentation.
The argument word is considered separately from each other word. The
case of letters is ignored.
OPTIONS
The following switch options are recognized:
-P path
if a valid path is given, apropos searches for the databases
there (see ENVIRONMENT).
-s section
search only for items from the specified section. This should be
a single character representing a section of the manual, i.e.,
from the list:
0123456789lno
EXAMPLE
Try apropos editor and apropos disk to get a feel for what apropos
does.
ENVIRONMENT
Apropos searches for the database file in the directory contained in
the MANPATH environment variable. Note that the -P option overrides
this. If neither MANPATH or -P are specified, a default path of
``d:/usr/man'' is used.
NOTES
Apropos performs a simple string search. For example, apropos man
finds all instances of command, manipulate, mantissa, permanent, and
so forth.
FILES
MANPATH/whatis._?_ online documentation database file
SEE ALSO
man(1), whatis(1), whatisin(1), whereis(1)
- 1 - Formatted: June 18, 1995
APROPOS(1) APROPOS(1)
AUTHOR
Bill Rosenkranz
rosenkra AT convex DOT com
VERSION
apropos 2.0.1 92/9/12 rosenkra
- 2 - Formatted: June 18, 1995
@EOF
set `sum $sumopt <whatis/apropos.1`; if test $1 -ne 22565
then
echo ERROR: whatis/apropos.1 checksum is $1 should be 22565
fi
chmod 644 whatis/apropos.1
echo x - whatis/apropos.c
cat >whatis/apropos.c <<'@EOF'
#undef DEBUG
/*
* apropos - find pertinent on-line documentation
*
* apropos name ...
*/
static char *rcsid_apropos_c = "$Id: apropos.c,v 2.0 1992/09/13 05:02:44 rosenkra Exp $";
static char *version = "apropos 2.0 92/09/11 rosenkra AT convex DOT com";
static char *myname = "apropos";
/*
* $Log: apropos.c,v $
* Revision 2.0 1992/09/13 05:02:44 rosenkra
* total rewrite. this if first rev of this file.
*
*
*/
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <ctype.h>
#include "whatis.h"
/*
* we only need one record here. we read a record and check all the
* command line args against it for a match
*/
struct rec r;
char *libpath = MANPATH; /* path to database files (-P) */
int debugging = 0; /* for -d */
/*
* fcn prototypes
*/
void apropos (int, int, int, char **);
int match_up (char *, char *);
int advance (char *, char *);
int cmp_ign_case (int, int);
void usage (int);
int parse_record (char *, struct rec *);
void print_record (int, struct rec *);
#ifdef CHECK_MAGIC
int check_magic (void);
#endif
/*------------------------------*/
/* main */
/*------------------------------*/
void main (int argc, char *argv[])
{
int sect = -1;
int verbose = 0;
char *lpath;
char *ps;
/*
* see if there is MANPATH in env. use it over default...
*/
if ((lpath = getenv ("MANPATH")) != (char *) NULL)
libpath = lpath;
else if ((lpath = getenv ("MANDIR")) != (char *) NULL)
libpath = lpath;
#ifdef DEBUG
else
fprintf (stderr, "apropos: environment variable MANPATH not set, using default\n");
#endif
/*
* parse args
*/
for (argc--, argv++; argc && **argv == '-'; argc--, argv++)
{
switch (*(*argv+1))
{
case 'P': /* path for db */
case 'M':
argc--, argv++;
if (argc < 1)
usage (1);
libpath = *argv;
break;
case 's': /* specific section */
argc--, argv++;
if (argc < 1)
usage (1);
sect = **argv;
break;
case 'd': /* debug mode */
debugging = 1;
break;
case 'v': /* version */
printf ("%s\n", version);
exit (0);
break;
case 'h': /* help */
usage (0);
break;
case '-':
switch (*(*argv+2))
{
case 'v': /* --version */
printf ("%s\n", version);
exit (0);
break;
case 'h': /* --help */
usage (0);
break;
}
break;
}
}
/*
* apropos what?
*/
if (argc == 0)
{
fprintf (stderr,
"%s: you must specify an argument. consider using whatisin.\n",
myname);
usage (1);
}
/*
* not documented: if first arg is a number, use it for section...
*/
if (isdigit(**argv))
{
sect = **argv;
argc--, argv++;
}
/*
* do it. if specific section, search it only. else search all
* sections
*/
if (sect != -1)
{
apropos (verbose, sect, argc, argv);
}
else
{
for (ps = SECTIONS; *ps; ps++)
{
sect = *ps;
apropos (verbose, sect, argc, argv);
}
}
exit (0);
}
/*------------------------------*/
/* apropos */
/*------------------------------*/
void apropos (int verbose, int sect, int argc, char **argv)
{
#define MAX_ARGS 100
char dbname[256];
char buf[REC_SIZE];
char srch[REC_SIZE];
register char **vp;
int notfound[MAX_ARGS];
int i, j;
/*
* FIXME: we should allocate space for the notfound list.
*/
if (argc > MAX_ARGS)
argc = MAX_ARGS;
/*
* set up db name. section is really a single ascii char, not an
* int. this is so we can have whatis for local, new, etc.
*/
if (sect == -1)
/* orig behavior (just single "whatis" file, never used here) */
sprintf (dbname, "%s%s%s", libpath, SLASH, WHATIS);
else
/* new: whatis._[0-9lno]_ */
sprintf (dbname, "%s%s%s._%c_", libpath, SLASH, WHATIS, sect);
/*
* reopen stdin as this file...
*/
if (debugging)
fprintf (stderr, "checking database file %s...\n", dbname);
if (freopen (dbname, "r", stdin) == (FILE *) NULL)
{
/* if (verbose || debugging)*/
if (debugging)
fprintf (stderr,
"%s: could not access file %s\n",
myname, dbname);
return;
}
#ifdef CHECK_MAGIC
/*
* check file's magic
*/
if (check_magic ())
{
fprintf (stderr,
"%s: magic number is wrong for file %s\n",
myname, dbname);
return;
}
#endif
/*
* read file and compare. first assume we will not find anything
* and flag list...
*/
for (i = 0; i < MAX_ARGS; i++)
notfound[i] = 1;
while (1)
{
/*
* get raw record from file
*/
fgets (buf, REC_SIZE-1, stdin);
if (feof (stdin))
break;
if (debugging)
fprintf (stderr, "%s", buf);
/*
* skip comment or blank lines
*/
if (buf[0] == '#' || buf[0] == '\0' || buf[0] == '\n')
continue;
/*
* parse the record and store in r
*/
parse_record (buf, &r);
if (debugging)
{
fprintf(stderr,"name: %s\n",r.name ? r.name : "(NULL)");
fprintf(stderr,"section: %s\n",r.section ? r.section:"(NULL)");
fprintf(stderr,"subsect: %s\n",r.subsect ? r.subsect:"(NULL)");
fprintf(stderr,"desc: %s\n",r.desc ? r.desc : "(NULL)");
}
/*
* compare record's name field to all args from orig
* command line. if we find one, flag notfound list
*/
for (i = 0, vp = argv; i < argc && *vp; vp++, i++)
{
/*
* make a long list of things to search
*/
srch[0] = '\0';
if (r.name)
{
strcat (srch, r.name);
strcat (srch, " ");
}
if (r.desc)
{
strcat (srch, r.desc);
strcat (srch, " ");
}
for (j = 0; j < MAX_ALIAS; j++)
{
if (r.alias[j] == NULL)
break;
strcat (srch, r.alias[j]);
strcat (srch, " ");
}
for (j = 0; j < MAX_KEYW; j++)
{
if (r.keyw[j] == NULL)
break;
strcat (srch, r.keyw[j]);
strcat (srch, " ");
}
/*
* check for a match...
*/
if (match_up (srch, *vp))
{
print_record (verbose, &r);
notfound[i] = 0;
}
}
}
/*
* print a message if we didn't find anything for the cmdline arg
*/
if (verbose)
{
for (i = 0; i < argc; i++)
{
if (notfound[i])
{
printf ("nothing appropriate in section %c for %s\n",
sect, argv[i]);
}
}
}
return;
}
/*------------------------------*/
/* match_up */
/*------------------------------*/
int match_up (char *buf, char *str)
{
/*
* search for string in str from a list contained in buf. this part
* just advances a ptr to buf and calls a lower level routine. ret 1
* if there is a match, else 0.
*/
register char *pbuf;
for (pbuf = buf; *pbuf; pbuf++)
if (advance (pbuf, str))
return (1);
return (0);
}
/*------------------------------*/
/* advance */
/*------------------------------*/
int advance (char *s1, char *s2)
{
/*
* main matching driver. advances along each string. cmp_ign_case does
* theactual char match. ret 1 if match, else 0. search is finished when
* s2 is at EOS.
*/
while (*s1 && *s2
&& ((*s1 == *s2) || cmp_ign_case ((int) (*s1), (int) (*s2))))
s1++, s2++;
if (*s2 == 0)
return (1);
return (0);
}
/*------------------------------*/
/* cmp_ign_case */
/*------------------------------*/
int cmp_ign_case (int c1, int c2)
{
/*
* char matching part. ignores case. must be alpha chars only! if
* chars match, ret 1, else 0. c1 should probably always be alpha,
* but check anyway. c2 comes from user. check it first for possible
* quick exit. compare in lower case (since that is more probable
* and the tolower could be skipped).
*
* consider inlining this...
*/
if (!isalpha (c2) || !isalpha (c1)) return (0);
if (isupper (c1)) c1 = tolower (c1);
if (isupper (c2)) c2 = tolower (c2);
return (c1 == c2);
}
/*------------------------------*/
/* usage */
/*------------------------------*/
void usage (int excode)
{
#define U fprintf
U(stderr,"usage: %s [-P path] [-s section] name ...\n", myname);
U(stderr," -P path alternative path to databases (MANPATH)\n");
U(stderr," -s section limit search to single section, not all\n");
U(stderr," name name of a keyword (any single word).\n");
exit (excode);
}
@EOF
set `sum $sumopt <whatis/apropos.c`; if test $1 -ne 65023
then
echo ERROR: whatis/apropos.c checksum is $1 should be 65023
fi
chmod 644 whatis/apropos.c
echo x - whatis/apropos.man
sed 's/^@//' >whatis/apropos.man <<'@EOF'
@.\" $Id: apropos.man,v 2.0 1992/09/13 05:09:30 rosenkra Exp $
@.\"
@.\" $Log: apropos.man,v $
@.\" Revision 2.0 1992/09/13 05:09:30 rosenkra
@.\" total rewrite. this is first rev.
@.\"
@.TH APROPOS 1
@.SH NAME
apropos \- find pertinent online documentation
@.SH SYNOPSIS
@.B apropos
[
@.B \-P
@.I path
] [
@.B \-s
@.I section
]
@.IR word ...
@.SH DESCRIPTION
The
@.B apropos
command displays a one line synopsis of each online documentation
file whose name or description contains a specified
@.I word
or whose keywords listed in the
@.I whatis
databases matches the specified
@.IR word .
Once you know what you are looking for, use
@.IR man (1)
to read the appropriate documentation.
@.PP
The argument
@.I word
is considered separately from each other word.
The case of letters is ignored.
@.SH OPTIONS
The following switch options are recognized:
@.IP "\fB\-P \fIpath\fR"
if a valid
@.I path
is given,
@.B apropos
searches for the databases there (see ENVIRONMENT).
@.IP "\fB\-s \fIsection\fR"
search only for items from the specified
@.IR section .
This should be a single character representing a section of the
manual, i.e., from the list:
@.nf
0123456789lno
@.fi
@.SH EXAMPLE
Try \*(lqapropos editor\*(rq and \*(lqapropos disk\*(rq to get a feel
for what
@.B apropos
does.
@.SH ENVIRONMENT
@.B Apropos
searches for the database file in the directory contained
in the
@.B MANPATH
environment variable.
Note that the
@.B \-P
option overrides this.
If neither
@.B MANPATH
or
@.B \-P
are specified, a default path of ``d:/usr/man'' is used.
@.SH NOTES
@.B Apropos
performs a simple string search.
For example, \*(lqapropos man\*(rq finds all instances of command,
manipulate, mantissa, permanent, and so forth.
@.SH FILES
@.nf
MANPATH/whatis._?_ online documentation database file
@.fi
@.SH "SEE ALSO"
man(1), whatis(1), whatisin(1), whereis(1)
@.SH AUTHOR
Bill Rosenkranz
@.br
rosenkra AT convex DOT com
@.SH VERSION
apropos 2.0.1 92/9/12 rosenkra
@EOF
set `sum $sumopt <whatis/apropos.man`; if test $1 -ne 3040
then
echo ERROR: whatis/apropos.man checksum is $1 should be 3040
fi
chmod 644 whatis/apropos.man
echo x - whatis/common.c
cat >whatis/common.c <<'@EOF'
/*
* common.c - stuff used by all programs
*/
static char *rcsid_common_c = "$Id: common.c,v 2.0 1992/09/13 05:02:44 rosenkra Exp $";
/*
* $Log: common.c,v $
* Revision 2.0 1992/09/13 05:02:44 rosenkra
* total rewrite. this if first rev of this file.
*
*
*/
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include "whatis.h"
extern int debugging;
/*------------------------------*/
/* parse_record */
/*------------------------------*/
/*
* macros to make parsing easier
*/
#define EOS '\0'
#define NL '\n'
#define FIELDSEP '%'
#define ITEMSEP ','
#define END_OF_STRING(c) (c==EOS || c==NL)
#define END_OF_FIELD(c) (c==FIELDSEP)
#define END_OF_ITEM(c) (c==ITEMSEP)
#define ADVANCE_FIELD \
while(!END_OF_STRING(*ps) && !END_OF_FIELD(*ps)){ps++;} \
if(END_OF_STRING(*ps)){*ps=EOS;return(lastone?0:1);} \
*ps++ = EOS;
#define ADVANCE_ITEM \
while(!END_OF_STRING(*ps) && !END_OF_ITEM(*ps) && !END_OF_FIELD(*ps)){ps++;} \
if(END_OF_STRING(*ps)){*ps=EOS;return(lastone?0:1);} \
if(END_OF_FIELD(*ps)){*ps++ = EOS;break;} \
*ps++ = EOS;
int parse_record (char *raw, struct rec *r)
{
/*
* parse record. caller provides raw record and space for parsed
* structure. ret 0 if all ok, else 1 (incomplete record, etc).
* raw input is a null terminated string (with/without newline).
*/
char *ps = raw;
int i;
int lastone = 0;
/*
* set up default (empty)
*/
r->name = NULL;
r->alias[0] = NULL; r->alias[1] = NULL;
r->section = NULL;
r->subsect = NULL;
r->desc = NULL;
r->xref[0] = NULL; r->xref[1] = NULL;
r->keyw[0] = NULL; r->keyw[1] = NULL;
/*
* read name (required!)
*/
r->name = ps;
ADVANCE_FIELD;
/*
* read any aliases (optional)
*/
if (ps[0] == '_' && (END_OF_FIELD(ps[1]) || END_OF_STRING(ps[1])))
{
r->alias[0] = NULL;
ADVANCE_FIELD;
}
else
{
for (i = 0; i < MAX_ALIAS-1; i++)
{
if (*ps == EOS)
{
r->alias[i] = NULL;
return (1);
}
r->alias[i] = ps;
r->alias[i+1] = NULL;
ADVANCE_ITEM;
}
}
/*
* read section (required!)
*/
r->section = ps;
ADVANCE_FIELD;
/*
* read subsection (optional)
*/
r->subsect = ps;
ADVANCE_FIELD;
if (r->subsect[0] == '_')
r->subsect = NULL;
/*
* read description (required)
*/
r->desc = ps;
ADVANCE_FIELD;
/*
* read any xrefs (optional)
*/
if (ps[0] == '_' && (END_OF_FIELD(ps[1]) || END_OF_STRING(ps[1])))
{
r->xref[0] = NULL;
ADVANCE_FIELD;
}
else
{
for (i = 0; i < MAX_XREF-1; i++)
{
if (*ps == EOS)
{
r->xref[i] = NULL;
return (1);
}
r->xref[i] = ps;
r->xref[i+1] = NULL;
ADVANCE_ITEM;
}
}
/*
* read any keywords (optional)
*/
lastone = 1;
if (ps[0] == '_' && (END_OF_FIELD(ps[1]) || END_OF_STRING(ps[1])))
{
r->keyw[0] = NULL;
return (1);
}
else
{
for (i = 0; i < MAX_KEYW-1; i++)
{
if (*ps == EOS)
{
r->keyw[i] = NULL;
return (0);
}
r->keyw[i] = ps;
r->keyw[i+1] = NULL;
ADVANCE_ITEM;
}
}
return (0);
}
/*------------------------------*/
/* print_record */
/*------------------------------*/
void print_record (int verbose, struct rec *r)
{
/*
* print record. one line, just:
*
* name(sect[subsect]) - description.
*
* if verbose, add aliases, see also, and keywords, if any
*/
int i;
if (r->name)
printf ("%s", r->name);
if (r->section)
{
printf ("(%s", r->section);
if (r->subsect)
printf ("%s", r->subsect);
printf (") -");
}
else
printf (" -");
if (r->desc)
printf (" %s\n", r->desc);
else
printf (" unknown (no description in database)\n");
if (!verbose)
return;
if (r->alias[0] != NULL)
{
printf ("\tprimary manpage:\n");
for (i = 0; r->alias[i] != NULL; i++)
printf ("\t\t%s\n", r->alias[i]);
}
if (r->xref[0] != NULL)
{
printf ("\tsee also:\n");
for (i = 0; r->xref[i] != NULL; i++)
printf ("\t\t%s\n", r->xref[i]);
}
if (r->keyw[0] != NULL)
{
printf ("\tkeywords:\n");
for (i = 0; r->keyw[i] != NULL; i++)
printf ("\t\t%s\n", r->keyw[i]);
}
printf ("\n");
return;
}
#ifdef CHECK_MAGIC
/*------------------------------*/
/* check_magic */
/*------------------------------*/
int check_magic (void)
{
/*
* check magic "number" of file. if ok, return 0. else 1.
* should be first line of file. check only MAGIC_CHECK_LEN bytes.
*/
char buf[REC_SIZE];
fgets (buf, REC_SIZE-1, stdin);
if (feof (stdin))
return (1);
if (debugging)
fprintf (stderr, "magic: %s", buf);
if (!strncmp (buf, MAGIC, MAGIC_CHECK_LEN))
return (0);
return (1);
}
#endif /*CHECK_MAGIC*/
@EOF
set `sum $sumopt <whatis/common.c`; if test $1 -ne 54566
then
echo ERROR: whatis/common.c checksum is $1 should be 54566
fi
chmod 644 whatis/common.c
echo x - whatis/makefile
cat >whatis/makefile <<'@EOF'
# makefile for whatis,whatisin,apropos
#
# version:
#
# $Id$
#
# $Log$
#
# compiler (use second set for MiNT):
#SYSINC = c:/u/gcc/include
#SYSLIB = c:/u/gcc/lib
#SPECL = -nostdlib $(SYSLIB)/crt0.o
SYSINC =
SYSLIB =
SPECL =
#CC = gcc -z -Wall -v -I$(SYSINC)
#LD = gcc -z -Wall -v -L$(SYSLIB) $(SPECL)
CC = cc -Aa
LD = cc -Aa
#LIBS32 = -liio -lgnu
#LIBS16 = -liio16 -lgnu16
LIBS32 =
LIBS16 =
USRLIBS =
# if -mshort, use LIBS16...
LIBS = $(USRLIBS) $(LIBS32)
# compile/link options:
DEFS = #-DCHECK_MAGIC
OPT = #-O -fomit-frame-pointer
DEBUG = #-DDEBUG
PROF =
# use -mshort for 16-bit version (make sure to change libs)
ARCH =
MISC =
CFLAGS = $(DEBUG) $(PROF) $(ARCH) $(MISC) $(OPT) $(DEFS)
LDFLAGS = $(DEBUG) $(PROF) $(ARCH) $(MISC)
# targets, etc:
EXE =#.exe
SECT = 1
SUBSECT =
TARG1 = whatis$(EXE)
TARG2 = whatisin$(EXE)
TARG3 = apropos$(EXE)
TARGETS = $(TARG1) $(TARG2) $(TARG3)
MANPAG1 = whatis.$(SECT)
MANSRC1 = whatis.man
MANPAG2 = whatisin.$(SECT)
MANSRC2 = whatisin.man
MANPAG3 = apropos.$(SECT)
MANSRC3 = apropos.man
MANPAG4 = whatis.5
MANSRC4 = whatis.ma5
MANPAGES = $(MANPAG1) $(MANPAG2) $(MANPAG3) $(MANPAG4)
# commands used here:
ECHO = echo
CP = cp -p
COMPRESS = compress
RM = rm -f
# headers, sources, and objects:
HEADERS = whatis.h
SRCS1 = whatis.c
SRCS2 = whatisin.c
SRCS3 = apropos.c
COMSRC = common.c
SRCS = $(SRCS1) $(SRCS2) $(SRCS3) $(COMSRC)
OBJS1 = whatis.o
OBJS2 = whatisin.o
OBJS3 = apropos.o
COMOBJ = common.o
OBJS = $(OBJS1) $(OBJS2) $(OBJS3) $(COMOBJ)
DATABASES = whatisin.___ whatis._1_ whatis._2_ whatis._4_ \
whatis._5_ whatis._7_ whatis._8_
#whatis._6_ whatis._3_
# distribution files (add others as needed):
OTHERS = readme makefile $(MANSRC) todo
DISTFILES = $(OTHERS) $(SRCS) $(HEADERS)
LOG = compile.err
# install directories, etc:
#SLASH =\\
#BINDIR = c:\usr\bin
#MANTOP = c:\usr\man
#MANDIR = $(MANDIR)$(SLASH)man$(SECT)
#MANDI5 = $(MANDIR)$(SLASH)man5
#CATDIR = $(MANTOP)$(SLASH)cat$(SECT)
#CATDI5 = $(MANTOP)$(SLASH)cat5
SLASH =/
BINDIR = /mnt/rosenkra/test/bin
MANTOP = /mnt/rosenkra/test/man
MANDIR = $(MANTOP)$(SLASH)man$(SECT)
MANDI5 = $(MANTOP)$(SLASH)man5
CATDIR = $(MANTOP)$(SLASH)cat$(SECT)
CATDI5 = $(MANTOP)$(SLASH)cat5
# install commands
#
INST_BIN = cp -p
INST_MAN = cp -p
# directions...
#
directions:
@$(ECHO) type make all to built $(TARGETS)
@$(ECHO) type make install to build/install $(TARGET)
@$(ECHO) type make clean to remove objects
@$(ECHO) type make clobber to remove objects and $(TARGETS)
@$(ECHO) these should be done in this order
# main target (make all)...
#
all: $(TARGETS) mkwhatis$(EXE)
$(TARG1): $(COMOBJ) $(OBJS1)
$(LD) $(LDFLAGS) -o $(TARG1) $(OBJS1) $(COMOBJ) $(LIBS)
@$(ECHO) done making $(TARG1)
$(TARG2): $(COMOBJ) $(OBJS2)
$(LD) $(LDFLAGS) -o $(TARG2) $(OBJS2) $(COMOBJ) $(LIBS)
@$(ECHO) done making $(TARG2)
$(TARG3): $(COMOBJ) $(OBJS3)
$(LD) $(LDFLAGS) -o $(TARG3) $(OBJS3) $(COMOBJ) $(LIBS)
@$(ECHO) done making $(TARG3)
mkwhatis$(EXE): mkwhatis.o
$(LD) $(LDFLAGS) -o mkwhatis$(EXE) mkwhatis.o $(LIBS)
# manpage (use built-in .man.cat rule)...
#
manpage: $(MANPAGES)
$(MANPAG1): $(MANSRC1)
nroff -man $(MANSRC1)|ul -t dumb|cat -s >$(MANPAG1)
$(MANPAG2): $(MANSRC2)
nroff -man $(MANSRC2)|ul -t dumb|cat -s >$(MANPAG2)
$(MANPAG3): $(MANSRC3)
nroff -man $(MANSRC3)|ul -t dumb|cat -s >$(MANPAG3)
$(MANPAG4): $(MANSRC4)
nroff -man $(MANSRC4)|ul -t dumb|cat -s >$(MANPAG4)
install: install_bin install_man install_mkwhatis install_databases
install_mkwhatis: mkwhatis$(EXE)
$(INST_BIN) mkwhatis$(EXE) $(BINDIR)$(SLASH)mkwhatis$(EXE)
nroff -man mkwhatis.ma8|ul -t dumb|cat -s >mkwhatis.8
$(INST_MAN) mkwhatis.ma8 $(MANDIR)$(SLASH)mkwhatis.8
$(INST_MAN) mkwhatis.8 $(CATDIR)$(SLASH)mkwhatis.8
touch install_mkwhatis
install_bin: $(TARGETS)
$(INST_BIN) $(TARG1) $(BINDIR)$(SLASH)$(TARG1)
$(INST_BIN) $(TARG2) $(BINDIR)$(SLASH)$(TARG2)
$(INST_BIN) $(TARG3) $(BINDIR)$(SLASH)$(TARG3)
touch install_bin
install_man: $(MANPAGES)
$(INST_MAN) $(MANSRC1) $(MANDIR)$(SLASH)$(MANPAG1)
$(INST_MAN) $(MANSRC2) $(MANDIR)$(SLASH)$(MANPAG2)
$(INST_MAN) $(MANSRC3) $(MANDIR)$(SLASH)$(MANPAG3)
$(INST_MAN) $(MANSRC4) $(MANDI5)$(SLASH)$(MANPAG4)
$(INST_MAN) $(MANPAG1) $(CATDIR)$(SLASH)$(MANPAG1)
$(INST_MAN) $(MANPAG2) $(CATDIR)$(SLASH)$(MANPAG2)
$(INST_MAN) $(MANPAG3) $(CATDIR)$(SLASH)$(MANPAG3)
$(INST_MAN) $(MANPAG4) $(CATDI5)$(SLASH)$(MANPAG4)
touch install_man
install_databases:
$(INST_MAN) $(DATABASES) $(MANTOP)
touch install_databases
# others...
#
clean:
$(RM) $(OBJS) $(LOG) core mkwhatis.o
clobber: clean
$(RM) $(TARGETS) mkwhatis
$(RM) install_bin install_man
$(RM) install_mkwhatis install_databases
# dependencies...
#
$(COMOBJ): $(HEADERS)
$(OBJS1): $(HEADERS)
$(OBJS2): $(HEADERS)
$(OBJS3): $(HEADERS)
@EOF
set `sum $sumopt <whatis/makefile`; if test $1 -ne 29206
then
echo ERROR: whatis/makefile checksum is $1 should be 29206
fi
chmod 644 whatis/makefile
echo x - whatis/mkwhatis.8
cat >whatis/mkwhatis.8 <<'@EOF'
MKWHATIS(8) MKWHATIS(8)
NAME
mkwhatis - tool for making entries in whatis(1) databases
SYNOPSIS
mkwhatis manpage...
DESCRIPTION
mkwhatis reads the input files (which should be manpage source files)
and extracts information for the database used by whatis(1). It is
not perfect, but should help substantially in this otherwise tedious
task.
NOTES
For the format of the whatis database, see whatis(5).
whatis assumes manpages that look like this:
.TH FOO 1X <-- section, subsection
.SH NAME
foo \- blah blah blah <-- name, desc
.SH DESCIPTION
.
.
.
.SH "SEE ALSO"
bar(1), foobar(5) <-- cross references
.SH SOMETHING (or eof)
or
.TH FOO 1 LOCAL
.
.
.
It does not handle sourced files (aliases), ie:
.so man1/foo.1
At a minimum, you will have to add keywords yourself.
SEE ALSO
man(1), whatis(1), whatisin(1), apropos(1), whatis(5)
AUTHOR
Bill Rosenkranz
rosenkra AT convex DOT com
VERSION
mkwhatis 2.0.1 92/9/12 rosenkra
- 1 - Formatted: June 18, 1995
@EOF
set `sum $sumopt <whatis/mkwhatis.8`; if test $1 -ne 923
then
echo ERROR: whatis/mkwhatis.8 checksum is $1 should be 923
fi
chmod 644 whatis/mkwhatis.8
echo x - whatis/mkwhatis.c
cat >whatis/mkwhatis.c <<'@EOF'
/*
* mkwhatis - read/print "SEE ALSO" or NAME section of unformatted manpage
*
* finds .SH "SEE ALSO" or .SH NAME line and prints next line(s) until
* either EOF or first char of line is '.'
*
* this is a tool to help build the whatis(1) databases. the idea is
* to feed it a list of manpages (source form). it does a reasonable
* job, but is not perfect. you may have to do some editing...
*
* the format for each line of the whatis databases is:
*
* name%aliases%section%subsection%description%xrefs%keywords
*
* name program/routine/etc name. (required)
* alias if this sources another manpage or refered by another
* name. a comma-separated list. (optional)
* section number [0-9nlo] (required)
* subsection single capital letter (optional)
* description what this is, ascii string (required)
* xref basically "SEE ALSO". a comma-separated list (optional)
* keywords any descriptive keywords. comma-sep list (optional)
*
* optional fields contain only a '_' char.
*
* here is an example:
*
* unixmode%_%5%_%Extended Filename Standard%tcsh(1),sh(1)%TOS,MiNT,file,glob,links,shell,standard
*
* it assumes manpage (src) that look like this:
*
* .TH FOO 1X <-- gives section, subsection
* .SH NAME
* foo \- blah blah blah <-- gives name, desc
* .SH DESCIPTION
* .
* .
* .
* .SH "SEE ALSO"
* bar(1), foobar(5) <-- gives xref
* .SH SOMETHING (or eof)
*
* or
* .TH FOO 1 LOCAL <-- gives section, subsection
* .
* .
* .
*
* it does NOT handle sourced files (aliases), ie:
*
* .so man1/foo.1
*
* at a minimum, you will have to add keywords yourself.
*/
static char *rcsid_mkwhatis_c = "$Id: mkwhatis.c,v 2.0 1992/09/13 05:02:44 rosenkra Exp $";
static char *version = "mkwhatis 2.0 92/09/13 rosenkra AT convex DOT com";
static char *myname = "mkwhatis";
/*
* $Log: mkwhatis.c,v $
* Revision 2.0 1992/09/13 05:02:44 rosenkra
* total rewrite. this if first rev of this file.
*
*
*/
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#define EOS '\0'
#define NL '\n'
#define CR '\r'
#define TAB '\t'
#define SPC ' '
#define DOT '.'
#define DASH '-'
#define NAME "NAME"
#define SEE_ALSO "SEE ALSO"
#define SEE_ALSO_Q "\"SEE ALSO"
#define PR_NULL_FIELD printf("%%_");
#define B_SIZE 1024
char buf[B_SIZE];
FILE *stream;
void read_xref (void);
char *skipwhite (char *);
char *skipword (char *);
char *finddash (char *);
void kill_newline (char *);
void main (int argc, char *argv[])
{
char *ps;
int sec;
int subsec;
int got_xref = 0;
int got_name = 0;
for (argc--, argv++; argc && **argv == '-'; argc--, argv++)
{
switch (*(*argv+1))
{
default:
fprintf (stderr,"%s\n", version);
fprintf (stderr,
"usage: %s [-A | -N | -S | -B] file...\n",
myname);
exit (1);
}
}
/*
* args are manpage source files
*/
for ( ; argc && *argv; argc--, argv++)
{
if ((stream = fopen (*argv, "r")) == (FILE *) NULL)
{
fprintf (stderr,
"%s: could not open %s\n", myname, *argv);
continue;
}
got_xref = 0;
got_name = 0;
while (1)
{
fgets (buf, B_SIZE-1, stream);
if (feof (stream))
{
/* if we exit loop here, things were probably
ok, but there was no SEE ALSO. put out
an appropriate ending... */
if (got_name && !got_xref)
printf ("%%_%%_\n");
else
printf ("\n");
goto next1; /* ERROR? */
}
kill_newline (buf);
/*
* look for .TH or .SH
*/
if (buf[0] != DOT)
continue;
if (buf[1] == 'T' && buf[2] == 'H')
{
ps = buf;
/* skip .TH */
if ((ps = skipword (ps)) && *ps == EOS)
goto next1; /* ERROR */
if ((ps = skipwhite (ps)) && *ps == EOS)
goto next1; /* ERROR */
/* skip FOO */
if ((ps = skipword (ps)) && *ps == EOS)
goto next1; /* ERROR */
if ((ps = skipwhite (ps)) && *ps == EOS)
goto next1; /* ERROR */
if (*ps)
sec = *ps;
else
sec = '1'; /* assume */
subsec = EOS; /* none */
/* skip sect */
if ((ps = skipword (ps)) && *ps == EOS)
continue;
if ((ps = skipwhite (ps)) && *ps == EOS)
continue;
if (*ps)
subsec = *ps;
}
else if (buf[1] == 'S' && buf[2] == 'H')
{
ps = buf;
/* skip .SH */
if ((ps = skipword (ps)) && *ps == EOS)
goto next1; /* ERROR */
if ((ps = skipwhite (ps)) && *ps == EOS)
goto next1; /* ERROR */
if (!strncmp (ps, NAME, 4))
{
char *dsh;
fgets (buf, B_SIZE-1, stream);
if (feof (stream))
{
goto next1; /* ERROR */
}
kill_newline (buf);
ps = buf;
if ((ps = finddash (ps)) && *ps == EOS)
goto next1; /* ERROR */
/* skip past dash to desc */
dsh = ps;
if ((ps = skipword (ps)) && *ps == EOS)
goto next1; /* ERROR */
if ((ps = skipwhite (ps)) && *ps == EOS)
goto next1; /* ERROR */
/* find end of name, going backwards
from dash */
if (dsh[-1] == '\\')
dsh--;
while (dsh > buf
&& (dsh[-1] == SPC || dsh[-1] == TAB))
dsh--;
*dsh = EOS;
/* check for name */
if (buf[0] == EOS)
goto next1; /* ERROR */
printf ("%s", buf); /* name */
PR_NULL_FIELD; /* alias */
printf ("%%%c", sec); /* section */
if (subsec) /* subsect */
printf ("%%%c", subsec);
else
PR_NULL_FIELD;
if (ps && *ps) /* desc */
printf ("%%%s", ps);
else
PR_NULL_FIELD;
got_name = 1;
}
else if (strncmp (ps, SEE_ALSO, 8) == 0
|| strncmp (ps, SEE_ALSO_Q, 9) == 0)
{
got_xref = 1;
printf ("%%"); /* xref */
read_xref ();
break; /* normal exit! */
}
}
}
if (!got_xref)
PR_NULL_FIELD; /* xref */
PR_NULL_FIELD; /* keywords */
printf ("\n");
next1: ;
fclose(stream);
}
exit(0);
}
/*------------------------------*/
/* read_xref */
/*------------------------------*/
void read_xref (void)
{
char *ps;
while (1)
{
fgets (buf, B_SIZE-1, stream);
if (feof (stream) || buf[0] == '.')
return;
kill_newline (buf);
/* fputs (buf, stdout);*/
for (ps = buf; *ps; ps++)
{
if (*ps == SPC)
continue;
putchar (*ps);
}
}
return;
}
/*------------------------------*/
/* skipwhite */
/*------------------------------*/
char *skipwhite (char *ps)
{
while (*ps && (*ps == SPC || *ps == TAB))
ps++;
return (ps);
}
/*------------------------------*/
/* skipword */
/*------------------------------*/
char *skipword (char *ps)
{
while (*ps && (*ps != SPC && *ps != TAB))
ps++;
return (ps);
}
/*------------------------------*/
/* finddash */
/*------------------------------*/
char *finddash (char *ps)
{
while (*ps && *ps != DASH)
ps++;
return (ps);
}
/*------------------------------*/
/* kill_newline */
/*------------------------------*/
void kill_newline (char *ps)
{
while (*ps)
{
if (*ps == NL || *ps == CR)
{
*ps = EOS;
return;
}
ps++;
}
return;
}
@EOF
set `sum $sumopt <whatis/mkwhatis.c`; if test $1 -ne 29942
then
echo ERROR: whatis/mkwhatis.c checksum is $1 should be 29942
fi
chmod 644 whatis/mkwhatis.c
echo x - whatis/mkwhatis.ma8
sed 's/^@//' >whatis/mkwhatis.ma8 <<'@EOF'
@.\" $Id: mkwhatis.ma8,v 2.0 1992/09/13 05:09:30 rosenkra Exp $
@.\"
@.\" $Log: mkwhatis.ma8,v $
@.\" Revision 2.0 1992/09/13 05:09:30 rosenkra
@.\" total rewrite. this is first rev.
@.\"
@.TH MKWHATIS 8
@.SH NAME
mkwhatis \- tool for making entries in whatis(1) databases
@.SH SYNOPSIS
@.B mkwhatis
@.IR manpage ...
@.SH DESCRIPTION
@.B mkwhatis
reads the input files
(which should be manpage source files)
and extracts information for the
database used by
@.IR whatis (1).
It is not perfect, but should help substantially in this
otherwise tedious task.
@.SH NOTES
For the format of the
@.I whatis
database, see
@.IR whatis (5).
@.PP
@.B whatis
assumes manpages that look like this:
@.nf
\&.TH FOO 1X <-- section, subsection
\&.SH NAME
foo \\- blah blah blah <-- name, desc
\&.SH DESCIPTION
\&.
\&.
\&.
\&.SH "SEE ALSO"
bar(1), foobar(5) <-- cross references
\&.SH SOMETHING (or eof)
or
\&.TH FOO 1 LOCAL
\&.
\&.
\&.
@.fi
It does
@.I not
handle sourced files (aliases), ie:
@.nf
\&.so man1/foo.1
@.fi
At a minimum, you will have to add keywords yourself.
@.SH "SEE ALSO"
man(1), whatis(1), whatisin(1), apropos(1), whatis(5)
@.SH AUTHOR
Bill Rosenkranz
@.br
rosenkra AT convex DOT com
@.SH VERSION
mkwhatis 2.0.1 92/9/12 rosenkra
@EOF
set `sum $sumopt <whatis/mkwhatis.ma8`; if test $1 -ne 24514
then
echo ERROR: whatis/mkwhatis.ma8 checksum is $1 should be 24514
fi
chmod 644 whatis/mkwhatis.ma8
echo x - whatis/whatis.1
cat >whatis/whatis.1 <<'@EOF'
WHATIS(1) WHATIS(1)
NAME
whatis - show description of word
SYNOPSIS
whatis [ -l ] [ -P path ] [ -s section ] word...
DESCRIPTION
The whatis command displays a one line synopsis of each online
documentation file whose name matches the specified word. To read the
actual online documentation, use the man(1) command.
Word is considered separately from each other word. The case of
letters is significant.
OPTIONS
The following switch options are recognized:
-l a more verbose (long) output is given containing the one line
description plus a list of keywords, cross references, and the
primary manual page, if any.
-P path
if a valid path is given, whatis searches for the databases there
(see ENVIRONMENT).
-s section
search only for items from the specified section. This should be
a single character representing a section of the manual, i.e.,
from the list:
0123456789lno
ENVIRONMENT
Whatis searches for the database file in the directory contained in
the MANPATH environment variable. Note that the -P option overrides
this. If neither MANPATH or -P are specified, a default path of
``d:/usr/man'' is used.
FILES
MANPATH/whatis._?_ online documentation database file
SEE ALSO
apropos(1), man(1), whatisin(1), whereis(1)
AUTHOR
Bill Rosenkranz
rosenkra AT convex DOT com
VERSION
whatis v2.0.1 92/9/12 rosenkra
- 1 - Formatted: June 18, 1995
@EOF
set `sum $sumopt <whatis/whatis.1`; if test $1 -ne 23217
then
echo ERROR: whatis/whatis.1 checksum is $1 should be 23217
fi
chmod 644 whatis/whatis.1
echo x - whatis/whatis.5
cat >whatis/whatis.5 <<'@EOF'
WHATIS(5) WHATIS(5)
NAME
whatis - format of whatis(1) database
DESCRIPTION
These files are used by whatis(1), apropos(1), and whatisin(1).
The databases are kept in separate file for each section of the
manual, i.e.,
whatis._0_
whatis._1_
whatis._2_
etc.
whatis._l_
whatis._n_
whatis._o_
Each line is either a comment or data. Comments are blank lines or
those whose first character is a `#'.
The format for each data line of the databases is:
name%aliases%section%subsection%description%xrefs%keywords
name program/routine/etc name. (required)
alias if this sources another manpage or refered by another
name. a comma-separated list. (optional)
section manual section number [0-9nlo]. (required)
subsection single capital letter. (optional)
description what this is, ascii string. (required)
xref basically "SEE ALSO". a comma-separated list.
(optional)
keywords any descriptive keywords. comma-separated list.
(optional)
Optional or unspecified fields contain only a `_' char.
Here is an example:
unixmode%_%5%_%Extended Filename Standard%sh(1)%MiNT,file
SEE ALSO
whatis(1), apropos(1), whatisin(1), mkwhatis(8)
- 1 - Formatted: June 18, 1995
WHATIS(5) WHATIS(5)
AUTHOR
Bill Rosenkranz
rosenkra AT convex DOT com
VERSION
whatis.5 v2.0.1 92/9/12 rosenkra
- 2 - Formatted: June 18, 1995
@EOF
set `sum $sumopt <whatis/whatis.5`; if test $1 -ne 33431
then
echo ERROR: whatis/whatis.5 checksum is $1 should be 33431
fi
chmod 644 whatis/whatis.5
echo x - whatis/manifest
cat >whatis/manifest <<'@EOF'
README.all top level readme for man and whatis
README readme for whatis
makefile makefile to build apropos, whatis, and whatisin
apropos.1 formated manpage for apropos program
apropos.c source for apropos program
apropos.man unformatted manpage for apropos (nroff -man)
whatis.1 formated manpage for whatis program
whatis.5 formated manpage for whatis database format
whatis.man unformatted manpage for whatis program (nroff -man)
whatis.ma5 unformatted manpage for whatis database format (nroff -man)
whatis.c source for whatis program
whatis.h ditto
whatisin.1 formated manpage for whatisin program
whatisin.man unformatted manpage for whatisin (nroff -man)
whatisin.c source for whatisin program
common.c common source code for apropos, whatis, etc.
mkwhatis.8 formated manpage for mkwhatis program
mkwhatis.ma8 unformatted manpage for mkwhatis (nroff -man)
mkwhatis.c source for mkwhatis program. this is a tool to help build
the whatis databases from unformatted manpages
whatis._?_ example whatis databases. the number corresponds to the
section of the manual (1=commands, 2=system calls, etc)
whatisin.___ whatisin database
manifest this file
@EOF
set `sum $sumopt <whatis/manifest`; if test $1 -ne 16506
then
echo ERROR: whatis/manifest checksum is $1 should be 16506
fi
chmod 644 whatis/manifest
echo x - whatis/whatis.c
cat >whatis/whatis.c <<'@EOF'
#undef DEBUG
#undef CHECK_MAGIC
/*
* whatis - show description of word from man database
*
* whatis [-l] [-P path] [-s sect] name ...
*
* bugs:
* - need more error checking (of data in database)
* - perhaps a "magic number" for the database? it is
* written, but #ifdef CHECK_MAGIC.
*
* todo:
* - allow "-s n name name -s m name ..."
* - allow continuation lines in database:
*
* name\
* %1\
* %...
*/
static char *rcsid_whatis_c = "$Id: whatis.c,v 2.0 1992/09/13 05:02:44 rosenkra Exp $";
static char *version = "whatis 2.0 92/09/13 rosenkra AT convex DOT com";
static char *myname = "whatis";
/*
* $Log: whatis.c,v $
* Revision 2.0 1992/09/13 05:02:44 rosenkra
* total rewrite. this if first rev of this file.
*
*
*/
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <ctype.h>
#include "whatis.h"
/*
* we only need one record here. we read a record and check all the
* command line args against it for a match
*/
struct rec r;
char *libpath = MANPATH; /* path to database files (-P) */
int debugging = 0; /* for -d */
/*
* fcn prototypes
*/
void whatis (int, int, int, char **);
void usage (int);
int parse_record (char *, struct rec *);
void print_record (int, struct rec *);
#ifdef CHECK_MAGIC
int check_magic (void);
#endif
/*------------------------------*/
/* main */
/*------------------------------*/
void main (int argc, char *argv[])
{
int sect = -1;
int verbose = 0;
char *lpath;
char *ps;
/*
* see if there is MANPATH in env. use it over default...
*/
if ((lpath = getenv ("MANPATH")) != (char *) NULL)
libpath = lpath;
else if ((lpath = getenv ("MANDIR")) != (char *) NULL)
libpath = lpath;
#ifdef DEBUG
else
fprintf (stderr, "whatis: environment variable MANPATH not set, using default\n");
#endif
/*
* parse args
*/
for (argc--, argv++; argc && **argv == '-'; argc--, argv++)
{
switch (*(*argv+1))
{
case 'P': /* path for db */
case 'M':
argc--, argv++;
if (argc < 1)
usage (1);
libpath = *argv;
break;
case 's': /* specific section */
argc--, argv++;
if (argc < 1)
usage (1);
sect = **argv;
break;
case 'l': /* long (verbose) */
verbose = 1;
break;
case 'd': /* debug mode */
debugging = 1;
break;
case 'v': /* version */
printf ("%s\n", version);
exit (0);
break;
case 'h': /* help */
usage (0);
break;
case '-':
switch (*(*argv+2))
{
case 'v': /* --version */
printf ("%s\n", version);
exit (0);
break;
case 'h': /* --help */
usage (0);
break;
}
break;
}
}
/*
* whatis what?
*/
if (argc == 0)
{
fprintf (stderr,
"%s: you must specify an argument. consider using whatisin.\n",
myname);
usage (1);
}
/*
* not documented: if first arg is a number, use it for section...
*/
if (isdigit(**argv))
{
sect = **argv;
argc--, argv++;
}
/*
* do it. if specific section, search it only. else search all
* sections
*/
if (sect != -1)
{
whatis (verbose, sect, argc, argv);
}
else
{
for (ps = SECTIONS; *ps; ps++)
{
sect = *ps;
whatis (verbose, sect, argc, argv);
}
}
exit (0);
}
/*------------------------------*/
/* whatis */
/*------------------------------*/
void whatis (int verbose, int sect, int argc, char **argv)
{
#define MAX_ARGS 100
char dbname[256];
char buf[REC_SIZE];
register char **vp;
int notfound[MAX_ARGS];
int i;
/*
* FIXME: we should allocate space for the notfound list.
*/
if (argc > MAX_ARGS)
argc = MAX_ARGS;
/*
* set up db name. section is really a single ascii char, not an
* int. this is so we can have whatis for local, new, etc.
*/
if (sect == -1)
/* orig behavior (just single "whatis" file, never used here) */
sprintf (dbname, "%s%s%s", libpath, SLASH, WHATIS);
else
/* new: whatis._[0-9lno]_ */
sprintf (dbname, "%s%s%s._%c_", libpath, SLASH, WHATIS, sect);
/*
* reopen stdin as this file...
*/
if (debugging)
fprintf (stderr, "checking database file %s...\n", dbname);
if (freopen (dbname, "r", stdin) == (FILE *) NULL)
{
/* if (verbose || debugging)*/
if (debugging)
fprintf (stderr,
"%s: could not access file %s\n",
myname, dbname);
return;
}
#ifdef CHECK_MAGIC
/*
* check file's magic
*/
if (check_magic ())
{
fprintf (stderr,
"%s: magic number is wrong for file %s\n",
myname, dbname);
return;
}
#endif
/*
* read file and compare. first assume we will not find anything
* and flag list...
*/
for (i = 0; i < MAX_ARGS; i++)
notfound[i] = 1;
while (1)
{
/*
* get raw record from file
*/
fgets (buf, REC_SIZE-1, stdin);
if (feof (stdin))
break;
if (debugging)
fprintf (stderr, "%s", buf);
/*
* skip comment or blank lines
*/
if (buf[0] == '#' || buf[0] == '\0' || buf[0] == '\n')
continue;
/*
* parse the record and store in r
*/
parse_record (buf, &r);
if (debugging)
{
fprintf (stderr, "name: %s\n", r.name ? r.name : "(NULL)");
fprintf (stderr, "section: %s\n", r.section ? r.section : "(NULL)");
fprintf (stderr, "subsect: %s\n", r.subsect ? r.subsect : "(NULL)");
fprintf (stderr, "desc: %s\n", r.desc ? r.desc : "(NULL)");
}
/*
* compare record's name field to all args from orig
* command line. if we find one, flag notfound list
*/
for (i = 0, vp = argv; i < argc && *vp; vp++, i++)
{
if (!strncmp (r.name, *vp, strlen (*vp)))
{
print_record (verbose, &r);
notfound[i] = 0;
}
}
}
/*
* print a message if we didn't find anything for the cmdline arg
*/
if (verbose)
{
for (i = 0; i < argc; i++)
{
if (notfound[i])
{
printf ("nothing found in section %c for %s\n",
sect, argv[i]);
}
}
}
return;
}
/*------------------------------*/
/* usage */
/*------------------------------*/
void usage (int excode)
{
#define U fprintf
U(stderr,"usage: %s [-l] [-P path] [-s section] name ...\n", myname);
U(stderr," -l long list\n");
U(stderr," -P path alternative path to databases (MANPATH)\n");
U(stderr," -s section search single section, not all\n");
U(stderr," name valid name of a command, etc. if name is unknown,\n");
U(stderr," consider using whatisin(1) or apropos(1).\n");
exit (excode);
}
@EOF
set `sum $sumopt <whatis/whatis.c`; if test $1 -ne 22389
then
echo ERROR: whatis/whatis.c checksum is $1 should be 22389
fi
chmod 644 whatis/whatis.c
echo x - whatis/whatis.h
cat >whatis/whatis.h <<'@EOF'
/*
* whatis.h
*/
static char *rcsid_whatis_h = "$Id: whatis.h,v 2.0 1992/09/13 05:02:44 rosenkra Exp $";
/*
* $Log: whatis.h,v $
* Revision 2.0 1992/09/13 05:02:44 rosenkra
* total rewrite. this if first rev of this file.
*
*
*/
#ifdef CHECK_MAGIC
#define MAGIC "WHATIS/ST" /* file's magic */
#define MAGIC_CHECK_LEN 9 /* how much of magic has to match? */
/* rest is comment. this MAGIC is */
/* for whatis._?_ files */
#endif
#if defined(unix) || defined(__unix)
#define MANPATH "/usr/man\0\0<-----------patch space------------->"
/* db is $MANPATH/whatis._?_ */
#else
#define MANPATH "c:\\usr\\man\0\0<-----------patch space------------->"
/* db is $MANPATH/whatis._?_ */
#endif
#define WHATIS "whatis" /* db name (root) */
#define WHATISIN "whatisin" /* list of sections */
#define SECTIONS "0123456789lno\0\0<----------patch space------------->"
/* list of sections */
#if defined(unix) || defined(__unix)
#define SLASH "/" /* use "/" for unix, UNIXMODE */
#else
#define SLASH "\\" /* use "/" for unix, UNIXMODE */
#endif
#define REC_SIZE 1024 /* max line length in database */
#define MAX_ALIAS 10 /* max number of aliases, */
#define MAX_XREF 50 /* cross refs, and */
#define MAX_KEYW 50 /* keywords */
/*
* record structure (after reading from file)
*/
struct rec
{
char *name;
char *alias[MAX_ALIAS];
char *section;
char *subsect;
char *desc;
char *xref[MAX_XREF];
char *keyw[MAX_KEYW];
};
@EOF
set `sum $sumopt <whatis/whatis.h`; if test $1 -ne 38986
then
echo ERROR: whatis/whatis.h checksum is $1 should be 38986
fi
chmod 644 whatis/whatis.h
echo x - whatis/whatis.ma5 '[non-ascii]'
$unpacker <<'@eof'
begin 644 whatis/whatis.ma5
M+EPB("1)9#H@=VAA=&ES+FUA-2QV(#(N," Q.3DR+S Y+S$S(# U.C Y.C,PX
M(')O<V5N:W)A($5X<" D#0HN7"(-"BY<(B D3&]G.B!W:&%T:7,N;6$U+'8 AT X
M) T*+EPB(%)E=FES:6]N(#(N," @,3DY,B\P.2\Q,R @,#4Z,#DZ,S @(')OX
M<V5N:W)A#0HN7"(@=&]T86P@<F5W<FET92X@=&AI<R!I<R!F:7)S="!R978NX
M#0HN7"(@#0HN5$@@5TA!5$E3(#4-"BY32"!.04U%#0IW:&%T:7,@7"T AT 9F]RX
M;6%T(&]F('=H871I<R AT Q*2!D871A8F%S90T*+E-(($1%4T-225!424].#0I4X
M:&5S92!F:6QE<R!A<F4@=7-E9"!B>0T*+DE2('=H871I<R H,2DL#0HN25(@X
M87!R;W!O<R H,2DL#0IA;F0-"BY)4B!W:&%T:7-I;B H,2DN#0HN4% -"E1HX
M92!D871A8F%S97,@87)E(&ME<'0@:6X@<V5P87)A=&4 AT 9FEL92!F;W(@96%CX
M:"!S96-T:6]N(&]F('1H90T*;6%N=6%L+"!I+F4N+ T*+FYF#0H-"@EW:&%TX
M:7,N7S!?#0H)=VAA=&ES+E\Q7PT*"7=H871I<RY?,E\-"@EE=&,N#0H-"@EWX
M:&%T:7,N7VQ?#0H)=VAA=&ES+E]N7PT*"7=H871I<RY?;U\-"BYF:0T*+E!0X
M#0I%86-H(&QI;F4@:7,@96ET:&5R(&$@8V]M;65N="!O<B!D871A+@T*0V]MX
M;65N=',@87)E(&)L86YK(&QI;F5S(&]R('1H;W-E('=H;W-E(&9I<G-T(&-HX
M87)A8W1E<B!I<R!A(& C)RX-"BY04 T*5&AE(&9O<FUA="!F;W(@96%C:"!DX
M871A(&QI;F4@;V8@=&AE#0ID871A8F%S97,@:7,Z#0HN;F8-"@T*"6YA;64EX
M86QI87-E<R5S96-T:6]N)7-U8G-E8W1I;VXE9&5S8W)I<'1I;VXE>')E9G,EX
M:V5Y=V]R9',-"@T*+F9I#0HN25 @;F%M92 Q- AT T*<')O9W)A;2]R;W5T:6YEX
M+V5T8R!N86UE+@T**')E<75I<F5D*0T*+DE0(&%L:6%S(#$V#0II9B!T:&ESX
M('-O=7)C97,@86YO=&AE<B!M86YP86=E(&]R(')E9F5R960-"F)Y(&%N;W1HX
M97(@;F%M92X AT 82!C;VUM82US97!A<F%T960@;&ES="X-"BAO<'1I;VYA;"D-X
M"BY)4"!S96-T:6]N(#$V#0IM86YU86P@<V5C=&EO;B!N=6UB97(@6S M.6YLX
M;UTN#0HH<F5Q=6ER960I#0HN25 @<W5B<V5C=&EO;B Q- AT T*<VEN9VQE(&-AX
M<&ET86P@;&5T=&5R+@T**&]P=&EO;F%L*0T*+DE0(&1E<V-R:7!T:6]N(#$VX
M#0IW:&%T('1H:7,@:7,L(&%S8VEI('-T<FEN9RX-"BAR97%U:7)E9"D-"BY)X
M4"!X<F5F(#$V#0IB87-I8V%L;'D@(E-%12!!3%-/(BX-"F$@8V]M;6$M<V5PX
M87)A=&5D(&QI<W0N#0HH;W!T:6]N86PI#0HN25 @:V5Y=V]R9',@,38-"F%NX
M>2!D97-C<FEP=&EV92!K97EW;W)D<RX-"F-O;6UA+7-E<&%R871E9"!L:7-TX
M+@T**&]P=&EO;F%L*0T*+E!0#0I/<'1I;VYA;"!O<B!U;G-P96-I9FEE9"!FX
M:65L9',@8V]N=&%I;B!O;FQY(&$@8%\G(&-H87(N#0HN4% -"DAE<F4@:7,@X
M86X AT 97AA;7!L93H-"BYN9 AT T*#0H)=6YI>&UO9&4E7R4U)5\E17AT96YD960 AT X
M1FEL96YA;64 AT 4W1A;F1A<F0E<V AT H,2DE36E.5"QF:6QE#0HN9FD-"BY32" BX
M4T5%($%,4T\B#0IW:&%T:7,H,2DL(&%P<F]P;W,H,2DL('=H871I<VEN*#$IX
M+"!M:W=H871I<R AT X*0T*+E-(($%55$A/4 AT T*0FEL;"!2;W-E;FMR86YZ#0HNX
M8G(-"G)O<V5N:W)A0&-O;G9E>"YC;VT-"BY32"!615)324].#0IW:&%T:7,NX
;-2!V,BXP+C$@.3(O.2\Q,B!R;W-E;FMR80T* X
X
end
@eof
set `sum $sumopt <whatis/whatis.ma5`; if test $1 -ne 20319
then
echo ERROR: whatis/whatis.ma5 checksum is $1 should be 20319
fi
chmod 644 whatis/whatis.ma5
echo x - whatis/whatis.man
sed 's/^@//' >whatis/whatis.man <<'@EOF'
@.\" $Id: whatis.man,v 2.0 1992/09/13 05:09:30 rosenkra Exp $
@.\"
@.\" $Log: whatis.man,v $
@.\" Revision 2.0 1992/09/13 05:09:30 rosenkra
@.\" total rewrite. this is first rev.
@.\"
@.TH WHATIS 1
@.SH NAME
whatis \- show description of word
@.SH SYNOPSIS
@.B whatis
[
@.B \-l
] [
@.B \-P
@.I path
] [
@.B \-s
@.I section
]
@.IR word ...
@.SH DESCRIPTION
The
@.B whatis
command displays a one line synopsis of each online
documentation file whose name matches the specified
@.IR word .
To read the actual online documentation, use the
@.IR man (1)
command.
@.PP
@.I Word
is considered separately from each other word.
The case of letters is significant.
@.SH OPTIONS
The following switch options are recognized:
@.IP \fB\-l\fR
a more verbose (long) output is given containing the one line
description plus a list of keywords, cross references, and the
primary manual page, if any.
@.IP "\fB\-P \fIpath\fR"
if a valid
@.I path
is given,
@.B whatis
searches for the databases there (see ENVIRONMENT).
@.IP "\fB\-s \fIsection\fR"
search only for items from the specified
@.IR section .
This should be a single character representing a section of the
manual, i.e., from the list:
@.nf
0123456789lno
@.fi
@.SH ENVIRONMENT
@.B Whatis
searches for the database file in the directory contained in the
@.B MANPATH
environment variable.
Note that the
@.B \-P
option overrides this.
If neither
@.B MANPATH
or
@.B \-P
are specified, a default path of ``d:/usr/man'' is used.
@.SH FILES
@.nf
MANPATH/whatis._?_ online documentation database file
@.fi
@.SH "SEE ALSO"
apropos(1), man(1), whatisin(1), whereis(1)
@.SH AUTHOR
Bill Rosenkranz
@.br
rosenkra AT convex DOT com
@.SH VERSION
whatis v2.0.1 92/9/12 rosenkra
@EOF
set `sum $sumopt <whatis/whatis.man`; if test $1 -ne 44603
then
echo ERROR: whatis/whatis.man checksum is $1 should be 44603
fi
chmod 644 whatis/whatis.man
echo x - whatis/whatisin.1
cat >whatis/whatisin.1 <<'@EOF'
WHATISIN(1) WHATISIN(1)
NAME
whatisin - show contents of online documentation section
SYNOPSIS
whatisin [ -P path ] [ section ]
DESCRIPTION
The whatisin command displays a one line synopsis of each file in a
specified online documentation section. To read the actual online
documentation, use the man(1) command.
The argument section specifies a section similar to those in the 4.2
BSD UNIX Programmer's Manual (as explained below). In this case, the
description of that section is printed along with a full list of all
documentation in that section.
If no section is specified, whatisin displays a list of sections.
OPTIONS
The following switch options are recognized:
-P path
if a valid path is given, whatisin searches for the databases
there (see ENVIRONMENT).
SECTION NAMES
The sections of the manual are based on the Unix Programmer's Manual:
Sect UNIX Manual Description
---- ----------- -----------
0 General overview of features and documentation
1 Commands commands (like those in
n
)2 System calls low-level library calls (C)
3 Subroutines standard user calls (C)
4 Special files things like emacs .CMD files
5 File formats things like arc file formats
6 Games games manual
7 Miscellaneous miscellaneous information
8 Maintenance system administration commands
In addition, whatisin recognizes the following section names:
l local files specific to local system
n new files added since current software release
o old files from previous software release
ENVIRONMENT
Whatisin searches for the database file in the directory contained in
the MANPATH environment variable. Note that the -P option overrides
this. If neither MANPATH or -P are specified, a default path of
``d:/usr/man'' is used.
- 1 - Formatted: June 18, 1995
WHATISIN(1) WHATISIN(1)
FILES
MANPATH/whatisin.___ manual section list (contents)
MANPATH/whatis._?_ online documentation database files
SEE ALSO
apropos(1), man(1), whatis(1), whereis(1)
AUTHOR
Bill Rosenkranz
rosenkra AT convex DOT com
VERSION
whatisin 2.0.1 92/9/12 rosenkra
- 2 - Formatted: June 18, 1995
@EOF
set `sum $sumopt <whatis/whatisin.1`; if test $1 -ne 58137
then
echo ERROR: whatis/whatisin.1 checksum is $1 should be 58137
fi
chmod 644 whatis/whatisin.1
echo x - whatis/whatisin.c
cat >whatis/whatisin.c <<'@EOF'
#undef DEBUG
#undef CHECK_MAGIC
/*
* whatisin - show list of documentation sections
*
* whatisin [-P path] [section]
*
* reads both $MANPATH/whatisin and $MANPATH/whatis._?_ files
*
* bugs:
* - need more error checking (of data in database)
* - perhaps a "magic number" for the whatis database? it is
* written, but #ifdef CHECK_MAGIC.
*
* todo:
* - invoke PAGER (or MANPAGER) on list if sections specified
* - allow continuation lines in whatis database:
*
* name\
* %1\
* %...
*/
static char *rcsid_whatisin_c = "$Id: whatisin.c,v 2.0 1992/09/13 05:02:44 rosenkra Exp $";
static char *version = "whatisin 2.0 92/09/13 rosenkra AT convex DOT com";
static char *myname = "whatisin";
/*
* $Log: whatisin.c,v $
* Revision 2.0 1992/09/13 05:02:44 rosenkra
* total rewrite. this if first rev of this file.
*
*
*/
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include "whatis.h"
/*
* we only need one record here. we read a record and check all the
* command line args against it for a match
*/
struct rec r;
char *libpath = MANPATH;
int debugging = 0; /* for -d */
/*
* fcn prototypes
*/
void whatisin (int, char **);
void contents (int);
int parse_record (char *, struct rec *);
void print_record (int, struct rec *);
void usage (int);
#ifdef CHECK_MAGIC
int check_magic (void);
#endif
/*------------------------------*/
/* main */
/*------------------------------*/
void main (int argc, char *argv[])
{
char *lpath;
/*
* see if there is MANPATH in env. use it over default...
*/
if ((lpath = getenv ("MANPATH")) != (char *) NULL)
libpath = lpath;
else if ((lpath = getenv ("MANDIR")) != (char *) NULL)
libpath = lpath;
#ifdef DEBUG
else
fprintf (stderr, "whatisin: environment variable MANPATH not set, using default\n");
#endif
/*
* parse args
*/
for (argc--, argv++; argc && **argv == '-'; argc--, argv++)
{
switch (*(*argv+1))
{
case 'P': /* path for db */
case 'M':
argc--, argv++;
if (argc < 1)
usage (1);
libpath = *argv;
break;
case 'd': /* debug mode */
debugging = 1;
break;
case 'v': /* version */
printf ("%s\n", version);
exit (0);
break;
case 'h': /* help */
usage (0);
break;
case '-':
switch (*(*argv+2))
{
case 'v': /* --version */
printf ("%s\n", version);
exit (0);
break;
case 'h': /* --help */
usage (0);
break;
}
break;
}
}
/*
* do it. if no args, print file containing description of sections.
* else print contents of sections in argv list
*/
if (argc < 1)
whatisin (argc, argv);
else
while (argc)
whatisin (argc--, argv++);
exit (0);
}
/*------------------------------*/
/* whatisin */
/*------------------------------*/
void whatisin (int argc, char **argv)
{
char dbname[256];
char buf[REC_SIZE];
int doall = 0;
int sect;
int foundit = 0;
/*
* if no args specified, we only want a description of each section.
* otherwise, set sect to that specified in argv. should be single
* char (0-9,l,n,o, etc).
*/
if (argc == 0)
doall++;
else
{
doall = 0;
sect = **argv;
}
/*
* set up name of whatisin database and open it
*/
sprintf (dbname, "%s%s%s.___", libpath, SLASH, WHATISIN);
if (freopen (dbname, "r", stdin) == (FILE *) NULL)
{
fprintf (stderr,
"%s: could not access file %s\n",
myname, dbname);
exit (1);
}
if (doall)
{
/*
* just copy whatisin file. skip lines starting with #
*/
while (1)
{
fgets (buf, REC_SIZE-1, stdin);
if (feof (stdin))
break;
if (buf[0] == '#')
continue;
fputs (buf, stdout);
}
}
else
{
/*
* look for line describing section
*/
while (1)
{
fgets (buf, REC_SIZE-1, stdin);
if (feof (stdin))
break;
if (buf[0] == sect)
{
foundit++;
break;
}
}
if (foundit)
{
/*
* print header info then get print all the
* things in that section. contents will reopen
* stdin as the particular whatis database.
*/
printf ("Section Description\n");
printf ("------- -----------\n");
printf ("%s\n\n", buf);
printf ("Contents\n");
printf ("--------\n");
contents (sect);
printf ("\n");
}
else
{
fprintf (stderr, "%s: no section %c\n",
myname, sect);
exit (1);
}
}
return;
}
/*------------------------------*/
/* contents */
/*------------------------------*/
void contents (int sect)
{
char dbname[256];
char buf[REC_SIZE];
/*
* set up db name. section is really a single ascii char, not an
* int. this is so we can have whatis for local, new, etc.
*/
if (sect == -1)
/* orig behavior (just single "whatis" file, never used here) */
sprintf (dbname, "%s%s%s", libpath, SLASH, WHATIS);
else
/* new: whatis._[0-9lno]_ */
sprintf (dbname, "%s%s%s._%c_", libpath, SLASH, WHATIS, sect);
/*
* reopen stdin as this file...
*/
if (debugging)
fprintf (stderr, "checking database file %s...\n", dbname);
if (freopen (dbname, "r", stdin) == (FILE *) NULL)
{
fprintf (stderr,
"%s: could not access file %s\n",
myname, dbname);
exit (1);
}
#ifdef CHECK_MAGIC
/*
* check file's magic
*/
if (check_magic ())
{
fprintf (stderr,
"%s: magic number is wrong for file %s\n",
myname, dbname);
exit (1);
}
#endif
/*
* read file and print lines
*/
while (1)
{
/*
* get raw record from file
*/
fgets (buf, REC_SIZE-1, stdin);
if (feof (stdin))
break;
if (debugging)
fprintf (stderr, "%s", buf);
/*
* skip comment or blank lines
*/
if (buf[0] == '#' || buf[0] == '\0' || buf[0] == '\n')
continue;
/*
* parse the record and store in r
*/
parse_record (buf, &r);
if (debugging)
{
fprintf (stderr, "name: %s\n", r.name ? r.name : "(NULL)");
fprintf (stderr, "section: %s\n", r.section ? r.section : "(NULL)");
fprintf (stderr, "subsect: %s\n", r.subsect ? r.subsect : "(NULL)");
fprintf (stderr, "desc: %s\n", r.desc ? r.desc : "(NULL)");
}
/*
* print record (short form)
*/
print_record (0, &r);
}
return;
}
/*------------------------------*/
/* usage */
/*------------------------------*/
void usage (int excode)
{
#define U fprintf
U(stderr,"usage: %s [-P path] [section ...]\n", myname);
U(stderr," -P path alternative path to databases (MANPATH)\n");
U(stderr," section valid name of a manual section (single char). to get a\n");
U(stderr," list, invoke whatisin with no args.\n");
exit (excode);
#undef U
}
@EOF
set `sum $sumopt <whatis/whatisin.c`; if test $1 -ne 11169
then
echo ERROR: whatis/whatisin.c checksum is $1 should be 11169
fi
chmod 644 whatis/whatisin.c
echo x - whatis/whatisin.man
sed 's/^@//' >whatis/whatisin.man <<'@EOF'
@.\" $Id: whatisin.man,v 2.0 1992/09/13 05:09:30 rosenkra Exp $
@.\"
@.\" $Log: whatisin.man,v $
@.\" Revision 2.0 1992/09/13 05:09:30 rosenkra
@.\" total rewrite. this is first rev.
@.\"
@.TH WHATISIN 1
@.SH NAME
whatisin \- show contents of online documentation section
@.SH SYNOPSIS
@.B whatisin
[
@.B \-P
@.I path
] [
@.I section
]
@.SH DESCRIPTION
The
@.B whatisin
command displays a one line synopsis of each file in a specified
online documentation section.
To read the actual online documentation, use the
@.IR man (1)
command.
@.PP
The argument
@.I section
specifies a \*(lqsection\*(rq similar to those in the 4.2 BSD UNIX
Programmer's Manual (as explained below).
In this case, the description of that section is printed along with
a full list of all documentation in that section.
@.PP
If no section is specified,
@.B whatisin
displays a list of sections.
@.SH OPTIONS
The following switch options are recognized:
@.IP "\fB\-P \fIpath\fR"
if a valid
@.I path
is given,
@.B whatisin
searches for the databases there (see ENVIRONMENT).
@.SH "SECTION NAMES"
The sections of the manual are based on the Unix Programmer's Manual:
@.sp
@.nf
Sect UNIX Manual Description
---- ----------- -----------
0 General overview of features and documentation
1 Commands commands (like those in \bin)
2 System calls low-level library calls (C)
3 Subroutines standard user calls (C)
4 Special files things like emacs .CMD files
5 File formats things like arc file formats
6 Games games manual
7 Miscellaneous miscellaneous information
8 Maintenance system administration commands
@.fi
@.sp
In addition,
@.B whatisin
recognizes the following section names:
@.sp
@.nf
l local files specific to local system
n new files added since current software release
o old files from previous software release
@.fi
@.SH ENVIRONMENT
@.B Whatisin
searches for the database file in the directory contained in the
@.B MANPATH
environment variable.
Note that the
@.B \-P
option overrides this.
If neither
@.B MANPATH
or
@.B \-P
are specified, a default path of ``d:/usr/man'' is used.
@.SH FILES
@.nf
MANPATH/whatisin.___ manual section list (contents)
MANPATH/whatis._?_ online documentation database files
@.fi
@.SH "SEE ALSO"
apropos(1), man(1), whatis(1), whereis(1)
@.SH AUTHOR
Bill Rosenkranz
@.br
rosenkra AT convex DOT com
@.SH VERSION
whatisin 2.0.1 92/9/12 rosenkra
@EOF
set `sum $sumopt <whatis/whatisin.man`; if test $1 -ne 47789
then
echo ERROR: whatis/whatisin.man checksum is $1 should be 47789
fi
chmod 644 whatis/whatisin.man
chmod 755 whatis
rm -f /tmp/unpack$$
exit 0
--
Bill Rosenkranz |UUCP: {uunet,texsun}!convex!rosenkra
Convex Computer Corp. |ARPA: rosenkra AT convex DOT com
- Raw text -