home *** CD-ROM | disk | FTP | other *** search
- /*T uroff - produce nroff underlining for not-so-smart printers */
- /*S introduction */
- /*H uroff ----------------------------------------------------------- **
- **
- ** uroff - produce underlining for nroff documents for printers that
- ** do not do backspacing.
- **
- ** This program was written to reduce frustration with the use of the
- ** Printronix P-series printers and nroff. It was enough that we
- ** couldn't have bold, italics, or anything resembling correspondence
- ** or word-processing quality print. But NO UNDERLINING either was too
- ** much. This program works with any printer that can handle text
- ** followed by carriage return followed by some spaces and underscores.
- ** Like the P-series with an IGP!
- **
- ** This program is simple-minded, but quick. It uses buffered I/O and
- ** classes characters into very simple categories.
- **
- ** usage: uroff [ file... ]
- **
- ** If no file names are specified, it will filter standard input.
- ** If a file name is dash (-), standard input will be read at that
- ** point.
- **
- ** Permission is granted for use and distribution, as long as you
- ** include the following notice:
- **
- ** (c) 1985 Steven M. List
- ** Benetics Corporation, Mt. View, CA
- ** {cdp,greipa,idi,oliveb,sun,tolerant}!bene!luke!itkin
- **
- ** ------------------------------------------------------------------ */
- /*E*/
- #include <stdio.h>
-
- char *pgm;
-
- #ifdef BSD
- #define strrchr rindex
- #endif
- extern char *strrchr ();
- /*S main - control loop */
- /*Page Eject*/
- main (ac, av)
- int ac;
- char **av;
- {
- register FILE *in; /* input stream */
-
- /* ------------------------------------------------------------ */
- /* set the basename of the program name for logging */
- /* ------------------------------------------------------------ */
-
- if (pgm = strrchr (av[0], '/')) pgm++;
- else pgm = av[0];
-
- ac--; av++;
-
- /* ------------------------------------------------------------ */
- /* arguments are file names - if none, use standard input */
- /* ------------------------------------------------------------ */
-
- if (ac == 0)
- {
- dofile (stdin);
- }
- else while (ac--)
- {
- if (!strcmp (*av, "-"))
- {
- in = stdin;
- }
- else if (!(in = fopen (*av, "r")))
- {
- fprintf (stderr,
- "%s: cannot open %s for read\n", pgm, *(av-1));
- }
-
- av++;
-
- if (in)
- {
- dofile (in);
- if (in != stdin) fclose (in);
- }
- }
-
- exit (0);
- }
- /*S dofile - process an input file */
- /*H dofile ***********************************************************
- *
- * dofile
- *
- * Read each character from the input file. Put it into the buffer
- * appropriate for the type. Flush the buffers on newline or eof.
- *
- *********************************************************************/
- /*E*/
- dofile (stream)
- register FILE *stream;
- {
- /* ------------------------------------------------------------ */
- /* some convenient defines */
- /* ------------------------------------------------------------ */
-
- # define BUFSIZE 256
- # define BACKSPACE '\b'
- # define NEWLINE '\n'
- # define FORMFEED '\f'
- # define RETURN '\r'
- # define UNDERSCORE '_'
- # define TAB '\t'
- # define SPACE ' '
- # define NUL '\0'
-
- register unsigned char anyund = 0;
- register unsigned char backup = 0;
- register char c;
- register int i;
- register char *tp;
- register char *up;
-
- char tbuf[BUFSIZE];
- char ubuf[BUFSIZE];
-
- /* ------------------------------------------------------------ */
- /* initialize BOTH buffers to all spaces */
- /* ------------------------------------------------------------ */
-
- for (i = 0, tp = tbuf, up = ubuf; i < BUFSIZE; i++)
- *(tp++) = *(up++) = SPACE;
- tp = tbuf; up = ubuf;
-
- /* ------------------------------------------------------------ */
- /* process each character in the input file */
- /* ------------------------------------------------------------ */
-
- while ((c = getc (stream)) != EOF)
- {
- switch (c)
- {
- case BACKSPACE:
- backup = 1;
- break;
- case UNDERSCORE:
- if (backup) *(up-1) = c;
- else
- {
- *up = c;
- up++; tp++;
- }
- anyund = 1;
- backup = 0;
- break;
- case NEWLINE:
- *tp = *up = NUL;
- fputs (tbuf, stdout);
- if (anyund)
- {
- putchar (RETURN);
- fputs (ubuf, stdout);
- }
- putchar (NEWLINE);
- anyund = 0;
- for (i = 0, tp = tbuf, up = ubuf; i < BUFSIZE; i++)
- *(tp++) = *(up++) = SPACE;
- tp = tbuf; up = ubuf;
- break;
- case SPACE:
- case TAB:
- case FORMFEED:
- *(up++) = *(tp++) = c;
- break;
- default:
- if (backup) *(tp-1) = c;
- else
- {
- *tp = c;
- up++; tp++;
- }
- backup = 0;
- break;
- }
- }
-
- if (tp != tbuf)
- {
- *tp = *up = NUL;
- fputs (tbuf, stdout);
- if (anyund)
- {
- putchar (RETURN);
- fputs (ubuf, stdout);
- }
- putchar (NEWLINE);
- }
-
- return;
- }
-