#!/bin/sh
# makewhatis: create the whatis database
# Created: Sun Jun 14 10:49:37 1992
# Revised: Wed Dec 23 14:22:44 1992 by root
# Copyright 1992 Rickard E. Faith (faith@cs.unc.edu)
# May be freely distributed and modified as long as copyright is retained.

# Wed Dec 23 13:27:50 1992: Rik Faith (faith@cs.unc.edu) applied changes
# based on Mitchum DSouza (mitchum.dsouza@mrc-apu.cam.ac.uk) cat patches.
# Also, cleaned up code and make it work with NET-2 doc pages.

# Thu Sep 23 03:42:49 GMT 1993
# Modified to work better with .gz, .z, and more garbage resistant
# by: Mark Lord (mlord@bnr.ca)

# Sun Apr 24 21:05:08 CDT 1994
# Modified to look for preformatted cat pages in /usr/man/preformat,
# and to update an existing database correctly by Patrick Volkerding
# (volkerdi@ftp.cdrom.com)

PATH=/usr/bin:/bin

for name in $*
do
case $name in
    -a) if echo $* | grep '\-u' 1> /dev/null 2> /dev/null ; then
        # a little recursion never hurt anybody... :^)
	    touch --file=/usr/man/whatis /tmp/timeref$$
	    $0 -u
	    # and there's nothing wrong with an occasional kludge. ;^)
	    # If you plan to build the whatis database in a different place
	    # than /usr/man, you'll have to change the 3 'touch' lines to
	    # make the kludge for '-a' work correctly. Maybe someday I'll
	    # fix it, but for now it's a big improvement from the way it 
            # was before, so I'm gonna be lazy.
	    touch --file=/tmp/timeref$$ /usr/man/whatis
	    rm -f /tmp/timeref$$
	    $0 -c -u
	else
	    $0
	    touch -t 010100001970 /usr/man/whatis
	    $0 -c -u
	fi
	exit;;
    -u) update="-anewer /usr/man/whatis";
        continue;;
    -c) pages=cat;
        filter="col -bx";
	mandir=/usr/man/preformat
        continue;;
    -*) echo "Usage: makewhatis -a -c -u [manpath]";
	echo "       -a: Builds a database of all pages in /usr/man/man* and"
	echo "           /usr/man/preformat (do not mix with -c)"
        echo "       -c: build database from cat pages in /usr/man/preformat/cat*";
	echo "           (otherwise database will be extracted from groff source"
	echo "           pages found in /usr/man/man*)"
        echo "       -u: update database with man/cat pages that are newer than the";
	echo "           existing /usr/man/whatis"
        echo "       [manpath]: man directory (default: /usr/man)";
        exit;;
     *) if [ -d ${name} ]
        then
            mandir=$name
        else
            echo "No such directory $name"
            exit
        fi;;
esac
done

pages=${pages-man}
export pages
mandir=${mandir-/usr/man}
filter=${filter-cat}

cd $mandir

for i in 0 1 2 3 4 5 6 7 8 9 n l
do
    if [ -d ${pages}$i ]
    then
        cd ${pages}$i
        section=$i
        export section
        for j in `find . -name '*' ${update} -print`
        do
	    Cat=cat
	    if [ `basename $j .gz` != `basename $j` -o \
		`basename $j .z` != `basename $j` -o \
		`basename $j .Z` != `basename $j` ]; then
                Cat=zcat
            fi
            ${Cat} ${j} | ${filter} |\
            gawk 'BEGIN {after = 0; insh = 0; wordjoin = 1;
                        pages = ENVIRON["pages"];
                        section = ENVIRON["section"]} {
                if (($1 ~ /^\.[Ss][Hh]/ && $2 ~ /[Nn][Aa][Mm][Ee]/) ||
                    (pages == "cat" && $1 ~ /^NAME/)) {
                    if (!insh)
                        insh = 1
                    else {
                        printf "\n"
                        exit
                    }
                } else if (insh) {
                    if ($1 ~ /^\.[Ss][HhYS]/ ||
                        (pages == "cat" && $1 ~ /^[DS][yYeE]/)) {
                        printf "\n"
                        exit
                    } else { # Substitutions after Tom Christiansen perl script
			if (!wordjoin)
				printf " "
                        gsub(/	/, " ")			# tabs to spaces
                        sub(/^ +/, "")			# Kill initial spaces
			if (!after && $0 ~ /^[^ ]+-/)
				sub(/-/, " - ")
                        sub(/  *,/,",")			# Fix comma spacings
                        sub(/,/,", ")			# Fix comma spacings
                        sub(/--/," - ")			# Handle Double dash
                        gsub(/  */, " ")		# Collapse spaces
                        sub(/  *$/, "")			# Kill trailing spaces
			if ($0 ~ /[^ ]-$/) {
                        	sub(/-$/, "")		# Hypenation
				wordjoin = 1
			} else
				wordjoin = 0
                        sub(/^.[IB] /, "")		# Kill bold and italics
                        gsub(/\\f[PRIB0123]/, "")	# Kill font changes
                        gsub(/\\s[-+0-9]*/, "")		# Kill size changes
                        gsub(/\\&/, "")			# Kill \&
                        gsub(/\\\((ru|ul)/, "_")	# Translate
                        gsub(/\\\((mi|hy|em)/, "-")	# Translate
                        gsub(/\\\*\(../, "")		# Kill troff strings
                        sub(/^\.\\\"/, "")		# Kill comments
                        gsub(/\\/, "")			# Kill all backslashes
			if (after) {
                                if ($1 !~ /^\.../ && $1 != "")
                                    printf "%s", $0
                                else {
                                    printf "\n"
                                    after = 0
                                }
			} else if ($0 !~ / - / && $0 !~ / -$/ && $0 !~ /^- /) {
                                if ($1 !~ /^\.../ && $1 != "")
                                    printf "%s", $0
                                else
                                    printf "\n"
                        } else {
                            after = 1
                            if ($0 ~ / - /) {
                                printf "%-20s", sprintf( "%s (%s)",
                                    substr( $0, 0, match( $0, / - / )-1 ), section )
                                printf " - %s", toupper(substr( $0, 3 + match( $0, / - / ),1 ))
                                printf "%s", substr( $0, 4 + match( $0, / - / ) )
                            } else if ($0 ~ / -$/) {
                                printf "%-20s", sprintf( "%s (%s) -",
                                    substr( $0, 0, match( $0, / -$/ )-1 ), section )
                            } else {
                                printf "(%s) %s", section, $0
                            }
                        }
                    }
                }
            }'
            done
        cd ..
    fi
done > /tmp/whatis$$
if [ "$mandir" = "/usr/man/preformat" ]; then
    # Another cheap hack to deal with /usr/man/preformat:
    mandir=/usr/man
fi
if [ ! "$update" = "" ]; then
    touch /usr/man/whatis
    cp /usr/man/whatis /tmp/oldwhatis$$
    cat /tmp/whatis$$ /tmp/oldwhatis$$ | sed '/^$/d' | sort | uniq > ${mandir}/whatis
    rm -f /tmp/oldwhatis$$
else
    sed '/^$/d' < /tmp/whatis$$ | sort | uniq > ${mandir}/whatis
fi
chmod 644 ${mandir}/whatis
rm /tmp/whatis$$
