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