Remove building with NOCRYPTO option
[minix.git] / usr.bin / fpr / fpr.c
blobed7081153e858410125335c62a76105bf448aa4a
1 /* $NetBSD: fpr.c,v 1.9 2011/09/04 20:26:17 joerg Exp $ */
3 /*
4 * Copyright (c) 1989, 1993
5 * The Regents of the University of California. All rights reserved.
7 * This code is derived from software contributed to Berkeley by
8 * Robert Corbett.
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 * 3. Neither the name of the University nor the names of its contributors
19 * may be used to endorse or promote products derived from this software
20 * without specific prior written permission.
22 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
23 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
26 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
27 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
28 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
29 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
31 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32 * SUCH DAMAGE.
35 #include <sys/cdefs.h>
36 #ifndef lint
37 __COPYRIGHT("@(#) Copyright (c) 1989, 1993\
38 The Regents of the University of California. All rights reserved.");
39 #endif /* not lint */
41 #ifndef lint
42 #if 0
43 static char sccsid[] = "@(#)fpr.c 8.1 (Berkeley) 6/6/93";
44 #endif
45 __RCSID("$NetBSD: fpr.c,v 1.9 2011/09/04 20:26:17 joerg Exp $");
46 #endif /* not lint */
48 #include <err.h>
49 #include <stdio.h>
50 #include <stdlib.h>
52 #define BLANK ' '
53 #define TAB '\t'
54 #define NUL '\000'
55 #define FF '\f'
56 #define BS '\b'
57 #define CR '\r'
58 #define VTAB '\013'
59 #define EOL '\n'
61 #define TRUE 1
62 #define FALSE 0
64 #define MAXCOL 170
65 #define TABSIZE 8
66 #define INITWIDTH 8
68 typedef
69 struct column {
70 int count;
71 int width;
72 char *str;
74 COLUMN;
76 static char cc;
77 static char saved;
78 static int length;
79 static char *text;
80 static int highcol;
81 static COLUMN *line;
82 static int maxpos;
83 static int maxcol;
85 static void flush(void);
86 static void get_text(void);
87 static void init(void);
88 __dead static void nospace(void);
89 static void savech(int);
91 int
92 main(int argc, char **argv)
94 int ch;
95 char ateof;
96 int i;
97 int errorcount;
99 init();
100 errorcount = 0;
101 ateof = FALSE;
103 switch (ch = getchar()) {
104 case EOF:
105 exit(0);
106 case EOL:
107 cc = NUL;
108 ungetc((int) EOL, stdin);
109 break;
110 case BLANK:
111 cc = NUL;
112 break;
113 case '1':
114 cc = FF;
115 break;
116 case '0':
117 cc = EOL;
118 break;
119 case '+':
120 cc = CR;
121 break;
122 default:
123 errorcount = 1;
124 cc = NUL;
125 ungetc(ch, stdin);
126 break;
129 while (!ateof) {
130 get_text();
131 switch (ch = getchar()) {
132 case EOF:
133 flush();
134 ateof = TRUE;
135 break;
136 case EOL:
137 flush();
138 cc = NUL;
139 ungetc((int) EOL, stdin);
140 break;
141 case BLANK:
142 flush();
143 cc = NUL;
144 break;
145 case '1':
146 flush();
147 cc = FF;
148 break;
149 case '0':
150 flush();
151 cc = EOL;
152 break;
153 case '+':
154 for (i = 0; i < length; i++)
155 savech(i);
156 break;
157 default:
158 errorcount++;
159 flush();
160 cc = NUL;
161 ungetc(ch, stdin);
162 break;
166 if (errorcount)
167 fprintf(stderr, "Illegal carriage control - %d line%s.\n",
168 errorcount, errorcount == 1 ? "" : "s");
170 exit(0);
173 static void
174 init(void)
176 COLUMN *cp;
177 COLUMN *cend;
178 char *sp;
180 length = 0;
181 maxpos = MAXCOL;
182 sp = malloc((unsigned) maxpos);
183 if (sp == NULL)
184 nospace();
185 text = sp;
187 highcol = -1;
188 maxcol = MAXCOL;
189 line = calloc(maxcol, sizeof(COLUMN));
190 if (line == NULL)
191 nospace();
192 cp = line;
193 cend = line + (maxcol - 1);
194 while (cp <= cend) {
195 cp->width = INITWIDTH;
196 sp = calloc(INITWIDTH, sizeof(char));
197 if (sp == NULL)
198 nospace();
199 cp->str = sp;
200 cp++;
204 static void
205 get_text(void)
207 int i;
208 char ateol;
209 int ch;
210 int pos;
211 char *n;
213 i = 0;
214 ateol = FALSE;
216 while (!ateol) {
217 switch (ch = getchar()) {
218 case EOL:
219 case EOF:
220 ateol = TRUE;
221 break;
222 case TAB:
223 pos = (1 + i / TABSIZE) * TABSIZE;
224 if (pos > maxpos) {
225 n = realloc(text, (unsigned)(pos + 10));
226 if (n == NULL)
227 nospace();
228 text = n;
229 maxpos = pos + 10;
231 while (i < pos) {
232 text[i] = BLANK;
233 i++;
235 break;
236 case BS:
237 if (i > 0) {
238 i--;
239 savech(i);
241 break;
242 case CR:
243 while (i > 0) {
244 i--;
245 savech(i);
247 break;
248 case FF:
249 case VTAB:
250 flush();
251 cc = ch;
252 i = 0;
253 break;
254 default:
255 if (i >= maxpos) {
256 n = realloc(text, (unsigned)(i + 10));
257 if (n == NULL)
258 nospace();
259 maxpos = i + 10;
261 text[i] = ch;
262 i++;
263 break;
267 length = i;
270 static void
271 savech(int col)
273 char ch;
274 int oldmax;
275 COLUMN *cp;
276 COLUMN *cend;
277 char *sp;
278 int newcount;
279 COLUMN *newline;
281 ch = text[col];
282 if (ch == BLANK)
283 return;
285 saved = TRUE;
287 if (col >= highcol)
288 highcol = col;
290 if (col >= maxcol) {
291 newline = realloc(line, (unsigned) (col + 10) * sizeof(COLUMN));
292 if (newline == NULL)
293 nospace();
294 line = newline;
295 oldmax = maxcol;
296 maxcol = col + 10;
297 cp = line + oldmax;
298 cend = line + (maxcol - 1);
299 while (cp <= cend) {
300 cp->width = INITWIDTH;
301 cp->count = 0;
302 sp = calloc(INITWIDTH, sizeof(char));
303 if (sp == NULL)
304 nospace();
305 cp->str = sp;
306 cp++;
309 cp = line + col;
310 newcount = cp->count + 1;
311 if (newcount > cp->width) {
312 cp->width = newcount;
313 sp = realloc(cp->str, (unsigned) newcount * sizeof(char));
314 if (sp == NULL)
315 nospace();
316 cp->str = sp;
318 cp->count = newcount;
319 cp->str[newcount - 1] = ch;
322 static void
323 flush(void)
325 int i;
326 int anchor;
327 int height;
328 int j;
330 if (cc != NUL)
331 putchar(cc);
333 if (!saved) {
334 i = length;
335 while (i > 0 && text[i - 1] == BLANK)
336 i--;
337 length = i;
338 for (i = 0; i < length; i++)
339 putchar(text[i]);
340 putchar(EOL);
341 return;
343 for (i = 0; i < length; i++)
344 savech(i);
346 anchor = 0;
347 while (anchor <= highcol) {
348 height = line[anchor].count;
349 if (height == 0) {
350 putchar(BLANK);
351 anchor++;
352 } else if (height == 1) {
353 putchar(*(line[anchor].str));
354 line[anchor].count = 0;
355 anchor++;
356 } else {
357 i = anchor;
358 while (i < highcol && line[i + 1].count > 1)
359 i++;
360 for (j = anchor; j <= i; j++) {
361 height = line[j].count - 1;
362 putchar(line[j].str[height]);
363 line[j].count = height;
365 for (j = anchor; j <= i; j++)
366 putchar(BS);
370 putchar(EOL);
371 highcol = -1;
374 static void
375 nospace(void)
377 errx(1, "Storage limit exceeded.");