|
|
1.1 root 1: static char *sccsid = "@(#)pr.c 4.7 (Berkeley) 10/22/87";
2:
3: /*
4: * print file with headings
5: * 2+head+2+page[56]+5
6: */
7:
8: #include <stdio.h>
9: #include <signal.h>
10: #include <sys/types.h>
11: #include <sys/stat.h>
12:
13: /* Making putcp a macro sped things up by 14%. */
14: #define putcp(c) if (page >= fpage) putchar(c)
15:
16: int ncol = 1;
17: char *header;
18: int col;
19: int icol;
20: FILE *file;
21: char *bufp;
22: #define BUFS 9000 /* at least 66 * 132 */
23: char buffer[BUFS]; /* for multi-column output */
24: char obuf[BUFSIZ];
25: #define FF 014
26: int line;
27: char *colp[72];
28: int nofile;
29: char isclosed[10];
30: FILE *ifile[10];
31: char **lastarg;
32: int peekc;
33: int fpage;
34: int page;
35: int colw;
36: int nspace;
37: int width = 72;
38: int length = 66;
39: int plength = 61;
40: int margin = 10;
41: int ntflg;
42: int fflg;
43: int mflg;
44: int tabc;
45: char *tty;
46: int mode;
47: char *ttyname();
48: char *ctime();
49:
50: main(argc, argv)
51: char **argv;
52: {
53: int nfdone;
54: int onintr();
55:
56: setbuf(stdout, obuf);
57: if (signal(SIGINT, SIG_IGN) != SIG_IGN)
58: signal(SIGINT, onintr);
59: lastarg = &argv[argc-1];
60: fixtty();
61: for (nfdone=0; argc>1; argc--) {
62: argv++;
63: if (**argv == '-') {
64: switch (*++*argv) {
65: case 'h': /* define page header */
66: if (argc>=2) {
67: header = *++argv;
68: argc--;
69: }
70: continue;
71:
72: case 't': /* don't print page headers */
73: ntflg++;
74: continue;
75:
76: case 'f': /* use form feeds */
77: fflg++;
78: plength = 60;
79: continue;
80:
81: case 'l': /* length of page */
82: length = atoi(++*argv);
83: continue;
84:
85: case 'w': /* width of page */
86: width = atoi(++*argv);
87: continue;
88:
89: case 's': /* col separator */
90: if (*++*argv)
91: tabc = **argv;
92: else
93: tabc = '\t';
94: continue;
95:
96: case 'm': /* all files at once */
97: mflg++;
98: continue;
99:
100: default:
101: if (numeric(*argv)) { /* # of cols */
102: if ((ncol = atoi(*argv)) == 0) {
103: fprintf(stderr, "can't print 0 cols, using 1 instead.\n");
104: ncol = 1;
105: }
106: } else {
107: fprintf(stderr, "pr: bad key %s\n", *argv);
108: exit(1);
109: }
110: continue;
111: }
112: } else if (**argv == '+') { /* start at page ++*argv */
113: fpage = atoi(++*argv);
114: } else {
115: print(*argv, argv);
116: nfdone++;
117: if (mflg)
118: break;
119: }
120: }
121: if (nfdone==0)
122: print((char *)0, (char **)0);
123: done();
124: }
125:
126: done()
127: {
128:
129: if (tty)
130: chmod(tty, mode);
131: exit(0);
132: }
133:
134: /* numeric -- returns 1 if str is numeric, elsewise 0 */
135: numeric(str)
136: char *str;
137: {
138: for (; *str ; str++) {
139: if (*str > '9' || *str < '0') {
140: return(0);
141: }
142: }
143: return(1);
144: }
145:
146: onintr()
147: {
148:
149: if (tty)
150: chmod(tty, mode);
151: _exit(1);
152: }
153:
154: fixtty()
155: {
156: struct stat sbuf;
157:
158: tty = ttyname(1);
159: if (tty == 0)
160: return;
161: stat(tty, &sbuf);
162: mode = sbuf.st_mode&0777;
163: chmod(tty, 0600);
164: }
165:
166: /* print -- print file */
167: print(fp, argp)
168: char *fp;
169: char **argp;
170: {
171: struct stat sbuf;
172: register sncol;
173: register char *sheader;
174: register char *cbuf;
175: char linebuf[150], *cp;
176:
177: if (ntflg)
178: margin = 0;
179: else
180: margin = 10;
181: if (length <= margin)
182: length = 66;
183: if (width <= 0)
184: width = 72;
185: if (ncol>72 || ncol>width) {
186: fprintf(stderr, "pr: No room for columns.\n");
187: done();
188: }
189: if (mflg) {
190: mopen(argp);
191: ncol = nofile;
192: }
193: colw = width/(ncol==0? 1 : ncol);
194: sncol = ncol;
195: sheader = header;
196: plength = length-5;
197: if (ntflg)
198: plength = length;
199: if (--ncol<0)
200: ncol = 0;
201: if (mflg)
202: fp = 0;
203: if (fp) {
204: if((file=fopen(fp, "r"))==NULL) {
205: if (tty==NULL)
206: perror(fp);
207: ncol = sncol;
208: header = sheader;
209: return;
210: }
211: stat(fp, &sbuf);
212: } else {
213: file = stdin;
214: time(&sbuf.st_mtime);
215: }
216: if (header == 0)
217: header = fp?fp:"";
218: cbuf = ctime(&sbuf.st_mtime);
219: cbuf[16] = '\0';
220: cbuf[24] = '\0';
221: page = 1;
222: icol = 0;
223: colp[ncol] = bufp = buffer;
224: if (mflg==0)
225: nexbuf();
226: while (mflg&&nofile || (!mflg)&&tpgetc(ncol)>0) {
227: if (mflg==0) {
228: colp[ncol]--;
229: if (colp[ncol] < buffer)
230: colp[ncol] = &buffer[BUFS - 1];
231: }
232: line = 0;
233: if (ntflg==0) {
234: if (fflg) {
235: /* Assume a ff takes two blank lines at the
236: top of the page. */
237: line = 2;
238: (void)sprintf(linebuf, "%s %s %s Page %d\n\n\n",
239: cbuf+4, cbuf+20, header, page);
240: } else
241: (void)sprintf(linebuf, "\n\n%s %s %s Page %d\n\n\n",
242: cbuf+4, cbuf+20, header, page);
243: for(cp=linebuf;*cp;) put(*cp++);
244: }
245: putpage();
246: if (ntflg==0) {
247: if (fflg)
248: put('\f');
249: else
250: while(line<length)
251: put('\n');
252: }
253: page++;
254: }
255: fclose(file);
256: ncol = sncol;
257: header = sheader;
258: }
259:
260: mopen(ap)
261: char **ap;
262: {
263: register char **p, *p1;
264:
265: p = ap;
266: while((p1 = *p) && p++ <= lastarg) {
267: if((ifile[nofile]=fopen(p1, "r")) == NULL){
268: isclosed[nofile] = 1;
269: nofile--;
270: }
271: else
272: isclosed[nofile] = 0;
273: if(++nofile>=10) {
274: fprintf(stderr, "pr: Too many args\n");
275: done();
276: }
277: }
278: }
279:
280: putpage()
281: {
282: register int lastcol, i, c;
283: int j;
284:
285: if (ncol==0) {
286: while (line<plength) {
287: while((c = tpgetc(0)) && c!='\n' && c!=FF)
288: putcp(c);
289: if (c==0) break;
290: putcp('\n');
291: line++;
292: if (c==FF)
293: break;
294: }
295: return;
296: }
297: colp[0] = colp[ncol];
298: if (mflg==0) for (i=1; i<=ncol; i++) {
299: colp[i] = colp[i-1];
300: for (j = margin; j<length; j++)
301: while((c=tpgetc(i))!='\n')
302: if (c==0)
303: break;
304: }
305: while (line<plength) {
306: lastcol = colw;
307: for (i=0; i<ncol; i++) {
308: while ((c=pgetc(i)) && c!='\n')
309: if (col<lastcol || tabc!=0)
310: put(c);
311: if (c==0)
312: continue;
313: if (tabc)
314: put(tabc);
315: else while (col<lastcol)
316: put(' ');
317: lastcol += colw;
318: }
319: while ((c = pgetc(ncol)) && c!='\n')
320: put(c);
321: put('\n');
322: }
323: }
324:
325: nexbuf()
326: {
327: register int n;
328: register char *rbufp;
329:
330: rbufp = bufp;
331: n = &buffer[BUFS] - rbufp;
332: if (n>512)
333: n = 512;
334: if((n=fread(rbufp,1,n,file)) <= 0){
335: fclose(file);
336: *rbufp = 0376;
337: }
338: else {
339: rbufp += n;
340: if (rbufp >= &buffer[BUFS])
341: rbufp = buffer;
342: *rbufp = 0375;
343: }
344: bufp = rbufp;
345: }
346:
347: tpgetc(ai)
348: {
349: register char **p;
350: register int c, i;
351:
352: i = ai;
353: if (mflg) {
354: if((c=getc(ifile[i])) == EOF) {
355: if (isclosed[i]==0) {
356: isclosed[i] = 1;
357: if (--nofile <= 0)
358: return(0);
359: }
360: return('\n');
361: }
362: if (c==FF && ncol>0)
363: c = '\n';
364: return(c);
365: }
366: loop:
367: c = **(p = &colp[i]) & 0377;
368: if (c == 0375) {
369: nexbuf();
370: c = **p & 0377;
371: }
372: if (c == 0376)
373: return(0);
374: (*p)++;
375: if (*p >= &buffer[BUFS])
376: *p = buffer;
377: if (c==0)
378: goto loop;
379: return(c);
380: }
381:
382: pgetc(i)
383: {
384: register int c;
385:
386: if (peekc) {
387: c = peekc;
388: peekc = 0;
389: } else
390: c = tpgetc(i);
391: if (tabc)
392: return(c);
393: switch (c) {
394:
395: case '\t':
396: icol++;
397: if ((icol&07) != 0)
398: peekc = '\t';
399: return(' ');
400:
401: case '\n':
402: icol = 0;
403: break;
404:
405: case 010:
406: case 033:
407: icol--;
408: break;
409: }
410: if (c >= ' ')
411: icol++;
412: return(c);
413: }
414: put(ac)
415: {
416: register int ns, c;
417:
418: c = ac;
419: if (tabc) {
420: putcp(c);
421: if (c=='\n')
422: line++;
423: return;
424: }
425: switch (c) {
426:
427: case ' ':
428: nspace++;
429: col++;
430: return;
431:
432: case '\n':
433: col = 0;
434: nspace = 0;
435: line++;
436: break;
437:
438: case 010:
439: case 033:
440: if (--col<0)
441: col = 0;
442: if (--nspace<0)
443: nspace = 0;
444:
445: }
446: while(nspace) {
447: if (nspace>2 && col > (ns=((col-nspace)|07))) {
448: nspace = col-ns-1;
449: putcp('\t');
450: } else {
451: nspace--;
452: putcp(' ');
453: }
454: }
455: if (c >= ' ')
456: col++;
457: putcp(c);
458: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.