xref: /csrg-svn/old/vfilters/vpf/vpf.c (revision 42810)
120203Sdist /*
220203Sdist  * Copyright (c) 1983 Regents of the University of California.
333682Sbostic  * All rights reserved.
433682Sbostic  *
5*42810Sbostic  * %sccs.include.redist.c%
620203Sdist  */
720203Sdist 
813948Ssam #ifndef lint
933682Sbostic char copyright[] =
1033682Sbostic "@(#) Copyright (c) 1983 Regents of the University of California.\n\
1133682Sbostic  All rights reserved.\n";
1233682Sbostic #endif /* not lint */
1313948Ssam 
1433682Sbostic #ifndef lint
15*42810Sbostic static char sccsid[] = "@(#)vpf.c	5.4 (Berkeley) 06/01/90";
1633682Sbostic #endif /* not lint */
1733682Sbostic 
181851Sroot /*
191851Sroot  * Varian/Versatec printer filter
201851Sroot  */
211851Sroot 
221851Sroot #include <signal.h>
231851Sroot #include <stdio.h>
241851Sroot #include <sys/vcmd.h>
251851Sroot 
261851Sroot #define LINELN 440
271851Sroot 
2812471Sralph int	pltmode[] = {VPLOT};
2912471Sralph int	prtmode[] = {VPRINT};
301851Sroot char	linebuf[LINELN+1];
311851Sroot char	ovbuf[LINELN];
321851Sroot int	ov;
331851Sroot int	lineno;
341851Sroot int	varian = 1;	/* default is the varian */
351851Sroot int	width = 132;	/* default line length */
3614667Sralph int	indent = 0;	/* default indent length */
371851Sroot int	length = 58;	/* 80 for 11" long paper */
381851Sroot int	npages = 1;
391851Sroot int	literal;
401851Sroot char	*name;		/* user's login name */
411851Sroot char	*host;		/* user's machine name */
421851Sroot char	*acctfile;	/* accounting information file */
431851Sroot 
main(argc,argv)4414667Sralph main(argc, argv)
4511582Sralph 	int argc;
4611582Sralph 	char *argv[];
4711582Sralph {
481851Sroot 	register int i;
491851Sroot 
501851Sroot 	if (argv[0][strlen(argv[0])-1] == 'W') { /* Wide: the versatec. */
511851Sroot 		varian = 0;
521851Sroot 		width = 440;
531851Sroot 		length = 66;
541851Sroot 	}
551851Sroot 
561851Sroot 	while (--argc) {
571851Sroot 		if (*(*++argv) == '-') {
581851Sroot 			switch (argv[0][1]) {
591851Sroot 			case 'n':
601851Sroot 				argc--;
611851Sroot 				name = *++argv;
621851Sroot 				break;
631851Sroot 
641851Sroot 			case 'h':
651851Sroot 				argc--;
661851Sroot 				host = *++argv;
671851Sroot 				break;
681851Sroot 
691851Sroot 			case 'w':
701851Sroot 				if ((i = atoi(&argv[0][2])) > 0 && i < LINELN)
711851Sroot 					width = i;
721851Sroot 				break;
731851Sroot 
741851Sroot 			case 'l':
751851Sroot 				length = atoi(&argv[0][2]);
761851Sroot 				break;
771851Sroot 
7814667Sralph 			case 'i':
7914667Sralph 				if ((i = atoi(&argv[0][2])) >= 0 &&
8014667Sralph 				    i < LINELN - 1)
8114667Sralph 					indent = i;
8214667Sralph 				break;
8314667Sralph 
841851Sroot 			case 'c':	/* Print input without throwing away
851851Sroot 					   control chars and without putting
861851Sroot 					   in page breaks. */
871851Sroot 				literal++;
881851Sroot 				break;
891851Sroot 			}
901851Sroot 		} else
911851Sroot 			acctfile = *argv;
921851Sroot 	}
931851Sroot 	/*
941851Sroot 	 * device should be open on file descriptor 1.
951851Sroot 	 */
961851Sroot 	ioctl(1, VSETSTATE, prtmode);
971851Sroot 	send();
981851Sroot 	if (name && acctfile && access(acctfile, 02) >= 0 &&
991851Sroot 	    freopen(acctfile, "a", stdout) != NULL) {
1001851Sroot 		printf("%7.2f\t%s:%s\n", (float)npages, host, name);
1011851Sroot 	}
1021851Sroot 	exit(0);
1031851Sroot }
1041851Sroot 
send()1051851Sroot send()
1061851Sroot {
1071851Sroot 	lineno = 0;
1081851Sroot 	while (getline()) {
10911843Sralph 		if (varian && !literal && lineno >= length) {
1101851Sroot 			putline(1);
1111851Sroot 			lineno = 0;
11211843Sralph 		} else
1131851Sroot 			putline(0);
1141851Sroot 	}
11511843Sralph 	if (varian && lineno) {
1161851Sroot 		putchar('\f');	/* be sure to end on a page boundary */
11711843Sralph 		npages++;
11811843Sralph 	}
1191851Sroot 	/*
1201851Sroot 	 * Put out an extra null to ensure varian will get an even
1211851Sroot 	 * number of good characters.
1221851Sroot 	 */
1231851Sroot 	putchar('\0');
1241851Sroot }
1251851Sroot 
getline()1261851Sroot getline()
1271851Sroot {
1281851Sroot 	register col, maxcol, c;
1291851Sroot 
1301851Sroot 	ov = 0;
1311851Sroot 	for (col = 0; col < width; col++) {
1321851Sroot 		linebuf[col] = ' ';
1331851Sroot 		ovbuf[col] = 0;
1341851Sroot 	}
13514667Sralph 	col = indent;
1361851Sroot 	maxcol = 0;
1371851Sroot 	for (;;) switch (c = getchar()) {
1381851Sroot 
1391851Sroot 	case EOF:
1401851Sroot 		return(0);
1411851Sroot 
1421851Sroot 	case '\031':
1431851Sroot 		/*
1441851Sroot 		 * lpd needs to use a different filter to print data so
1451851Sroot 		 * stop what we are doing and wait for lpd to restart us.
1461851Sroot 		 */
1471851Sroot 		if ((c = getchar()) == '\1') {
1481851Sroot 			putchar('\0');		/* make sure even # sent */
1491851Sroot 			fflush(stdout);
1501851Sroot 			kill(getpid(), SIGSTOP);
1511851Sroot 			ioctl(1, VSETSTATE, prtmode);
1521851Sroot 			continue;
1531851Sroot 		}
1541851Sroot 		ungetc(c, stdin);
1551851Sroot 		c = '\031';
1561851Sroot 		/* fall through if not stop sequence */
1571851Sroot 	default:
1581851Sroot 		if (c >= ' ' || literal) {
1591851Sroot 			if (col < width) {
1601851Sroot 				if (linebuf[col] == '_') {
1611851Sroot 					ovbuf[col] = 0377;
1621851Sroot 					ov++;
1631851Sroot 				}
1641851Sroot 				linebuf[col++] = c;
1651851Sroot 				if (col > maxcol)
1661851Sroot 					maxcol = col;
1671851Sroot 			} else
1681851Sroot 				col++;
1691851Sroot 		}
1701851Sroot 		continue;
1711851Sroot 
1721851Sroot 	case ' ':
1731851Sroot 		col++;
1741851Sroot 		continue;
1751851Sroot 
1761851Sroot 	case '\t':
1771851Sroot 		col = (col|07) + 1;
1781851Sroot 		continue;
1791851Sroot 
1801851Sroot 	case '\r':
1811851Sroot 		col = 0;
1821851Sroot 		continue;
1831851Sroot 
1841851Sroot 	case '_':
1851851Sroot 		if (col < width) {
1861851Sroot 			if (linebuf[col] != ' ') {
1871851Sroot 				ovbuf[col] = 0377;
1881851Sroot 				ov++;
1891851Sroot 			} else
1901851Sroot 				linebuf[col] = c;
1911851Sroot 			col++;
1921851Sroot 			if (col > maxcol)
1931851Sroot 				maxcol = col;
1941851Sroot 		} else
1951851Sroot 			col++;
1961851Sroot 		continue;
1971851Sroot 
1981851Sroot 	case '\f':
1991851Sroot 		/* Fall through, treating a ff as a line break, too... */
20011843Sralph 		lineno = length - 1;
2011851Sroot 	case '\n':
2021851Sroot 		if (maxcol > width)
2031851Sroot 			maxcol = width;
2041851Sroot 		linebuf[maxcol] = '\0';
20511843Sralph 		if (++lineno % length == 0)
20611843Sralph 			npages++;
2071851Sroot 		return(1);
2081851Sroot 
2091851Sroot 	case '\b':
2101851Sroot 		if (col > 0)
2111851Sroot 			col--;
2121851Sroot 		continue;
2131851Sroot 	}
2141851Sroot }
2151851Sroot 
putline(ff)2161851Sroot putline(ff)
2171851Sroot int ff;
2181851Sroot {
2191851Sroot 	register char *lp;
2201851Sroot 	register c, i;
2211851Sroot 
2221851Sroot 	lp = linebuf;
2231851Sroot 	while (c = *lp++)
2241851Sroot 		putchar(c);
2251851Sroot 	if (ov) {
2261851Sroot 		putchar('\n');
2271851Sroot 		putchar('\0');
2281851Sroot 		fflush(stdout);
2291851Sroot 		ioctl(1, VSETSTATE, pltmode);
2301851Sroot 		for (lp = ovbuf, i = ov; ov--; ) {
2311851Sroot 			putchar(*lp & 0377);
2321851Sroot 			putchar(*lp++ & 0377);
2331851Sroot 		}
2341851Sroot 		if (ov & 1)
2351851Sroot 			putchar('\0');
2361851Sroot 		fflush(stdout);
2371851Sroot 		ioctl(1, VSETSTATE, prtmode);
2381851Sroot 	}
23911843Sralph 	if (ff)
2401851Sroot 		putchar('\f');
24111843Sralph 	else if (ov == 0)
2421851Sroot 		putchar('\n');
2431851Sroot 	if (ferror(stdout))
2441851Sroot 		exit(1);
2451851Sroot }
246