Add copyright notice
[unix-history] / usr / src / old / vfilters / vpsf / vpsf.c
CommitLineData
012f1c1f
DF
1/*
2 * Copyright (c) 1983 Regents of the University of California.
3 * All rights reserved. The Berkeley software License Agreement
4 * specifies the terms and conditions for redistribution.
5 */
6
c936af6c 7#ifndef lint
012f1c1f
DF
8static char sccsid[] = "@(#)vpsf.c 5.1 (Berkeley) %G%";
9#endif not lint
c936af6c 10
1d6f0f0d
RC
11/*
12 * Versatec printer filter
13 * make wide listings by placing pages side by side
14 */
15
1d6f0f0d 16#include <stdio.h>
1d6f0f0d
RC
17#include <sys/vcmd.h>
18
19#define LINELN 440
fad99a32
RC
20#define PAGELN 86
21#define LMARG 10
1d6f0f0d 22
2d0289ae
RC
23int pltmode[] = {VPLOT};
24int prtmode[] = {VPRINT};
1d6f0f0d
RC
25
26char screen[PAGELN][LINELN];
27char ul[PAGELN][LINELN];
28char anyul[PAGELN];
fad99a32
RC
29int origin; /* first column of a page */
30int origin_ind; /* origin plus indent */
31int outline; /* current line number */
32int outcol; /* current column number */
1d6f0f0d 33int npages;
fad99a32
RC
34int width = 106; /* default page width */
35int length = 86; /* default page length */
36int indent = 0; /* default indent */
1d6f0f0d
RC
37
38int literal;
39char *name; /* user's login name */
40char *host; /* user's machine name */
41char *acctfile; /* accounting information file */
42
fad99a32 43main(argc, argv)
5af70e5e
RC
44 int argc;
45 char *argv[];
1d6f0f0d
RC
46{
47 register int i;
48
49 while (--argc) {
50 if (*(*++argv) == '-') {
51 switch (argv[0][1]) {
52 case 'n':
53 argc--;
54 name = *++argv;
55 break;
56
57 case 'h':
58 argc--;
59 host = *++argv;
60 break;
61
62 case 'w':
63 if ((i = atoi(&argv[0][2])) > 0 && i <= LINELN)
64 width = i;
65 break;
66
67 case 'l':
68 if ((i = atoi(&argv[0][2])) > 0 && i <= PAGELN)
69 length = i;
70 break;
71
fad99a32
RC
72 case 'i':
73 if ((i = atoi(&argv[0][2])) >= 0 &&
74 i < LINELN - 1)
75 indent = i;
76 break;
77
1d6f0f0d
RC
78 case 'c': /* Print input without throwing away
79 control chars and without putting
80 in page breaks. */
81 literal++;
82 break;
83 }
84 } else
85 acctfile = *argv;
86 }
fad99a32
RC
87 indent += literal ? 1 : LMARG;
88 if (indent >= width)
89 indent = width - 1;
1d6f0f0d
RC
90
91 /*
92 * input file is open on file descriptor 0.
93 * vp should be open on file descriptor 1.
94 * The error log file is open on file descriptor 2.
95 */
96 ioctl(1, VSETSTATE, prtmode);
97 process();
98
99 /*
100 * Put out an extra null to ensure versatec will get an even
101 * number of good characters.
102 */
103 putchar('\0');
104
105 if (ferror(stdout))
106 exit(1);
107 if (name && acctfile && access(acctfile, 02) >= 0 &&
108 freopen(acctfile, "a", stdout) != NULL) {
109 if (host)
110 printf("%7.2f\t%s:%s\n", (float)npages, host, name);
111 else
112 printf("%7.2f\t%s\n", (float)npages, name);
113 }
114 exit(0);
115}
116
fad99a32
RC
117set_up()
118{
119 clear(screen, sizeof(screen));
120 origin = 0;
121 origin_ind = outcol = origin + indent;
122 outline = 0;
123 cutmark(origin);
124}
125
1d6f0f0d
RC
126process()
127{
128 register int c;
129
fad99a32 130 set_up();
1d6f0f0d
RC
131
132 while ((c = getchar()) != EOF)
133 switch (c) {
134 case ' ':
135 outcol++;
136 break;
137
138 case '\t':
fad99a32 139 outcol = ((outcol - origin_ind) | 07) + origin_ind + 1;
1d6f0f0d
RC
140 break;
141
142 case '\b':
fad99a32 143 if (outcol > origin_ind)
1d6f0f0d
RC
144 outcol--;
145 break;
146
147 case '\r':
fad99a32 148 outcol = origin_ind;
1d6f0f0d
RC
149 break;
150
151 case '\f':
152 outline = length;
153 /* fall into ... */
154
155 case '\n':
156 if (++outline >= length) {
fad99a32
RC
157 origin += width + 1;
158 origin_ind += width + 1;
159 cutmark(origin);
160 if (origin + width + 1 >= LINELN) {
1d6f0f0d
RC
161 oflush();
162 break;
163 }
164 outline = 0;
1d6f0f0d 165 }
fad99a32 166 outcol = origin_ind;
1d6f0f0d
RC
167 break;
168
169 default:
170 outchar(c);
171 break;
172 }
173
fad99a32
RC
174 if (outline || origin) {
175 cutmark(origin + width + 1);
1d6f0f0d
RC
176 oflush();
177 }
178 printf("\n\n\n\n\n");
179}
180
181outchar(c)
182 register int c;
183{
184 register char *cp;
185 register int d;
186
187 if (!literal && (c < 040 || c >= 0177))
188 return;
fad99a32 189 if (outcol >= origin + width + 1) {
1d6f0f0d
RC
190 outcol++;
191 return;
192 }
193 cp = &screen[outline][outcol];
194 d = *cp;
195 if (d != ' ') {
196 if (d == '_' || c == '_') {
197 if (c == d) {
198 outcol++;
199 return;
200 }
201 if (anyul[outline] == 0)
202 clear(ul[outline], LINELN);
203 anyul[outline] = 1;
204 ul[outline][outcol] = 0377;
205 if (c == '_')
206 c = d;
207 }
208 }
209 *cp = c;
210 outcol++;
211}
212
213oflush()
214{
215 register char *cp, *dp;
216 register int i, j, oc, dc, c;
217
218 npages++;
219 putchar('\n');
220 for (i = 0; i < length; i++)
221 putline(i);
222 for (i = 0; i < LINELN; i++)
223 putchar('_');
224 putchar('\n');
fad99a32
RC
225
226 set_up();
1d6f0f0d
RC
227}
228
229clear(cp, i)
230 register char *cp;
231 register int i;
232{
233 if (i > 0)
234 do
235 *cp++ = ' ';
236 while (--i);
237}
238
239cutmark(o)
240 register int o;
241{
242 register int i;
243
fad99a32
RC
244 screen[0][o] = '|';
245 screen[1][o] = '|';
246 screen[length - 1][o] = '|';
247 screen[length - 2][o] = '|';
1d6f0f0d
RC
248}
249
250putline(n)
251 register int n;
252{
253 register char *cp;
254 register int j;
255
256 fwrite(screen[n], sizeof(char), sizeof(screen[0]), stdout);
257 if (anyul[n]) {
258 putchar('\n');
259 putchar('\0');
260 fflush(stdout);
261 ioctl(1, VSETSTATE, pltmode);
262 cp = ul[n];
263 j = LINELN;
264 do {
265 putchar(*cp & 0377);
266 putchar(*cp++ & 0377);
267 } while (--j);
268 fflush(stdout);
269 ioctl(1, VSETSTATE, prtmode);
270 } else
271 putchar('\n');
272 if (ferror(stdout))
273 exit(1);
274}