|
|
1.1 root 1: /*
2: * fwtable.c
3: * 6/7/91
4: * Usage: fwtable [ -cptv ] [ -ssymset ] [ infile [ outfile ] ]
5: * Read HP PCL bitmap font, PostScript AFM file, or HP TFM file
6: * from infile or stdin, write font width table to outfile or stdout.
7: *
8: * Requires floating point output, PostScript routines in fwt_PS.c,
9: * TFM routines in fwt_TFM.c:
10: * cc fwtable.c fwt_PS.c fwt_TFM.c -f
11: *
12: * Options:
13: * -c Write C instead of binary
14: * -p Input is PostScript AFM file
15: * -ssymset Specify desired symbol set with -t option
16: * -t Input is HP TFM file
17: * -v Write one-line font description to stderr
18: *
19: * Understands PCL bitmap fonts, PostScript AFM files, HP TFM files.
20: * Does not understand Intellifont scalable fonts.
21: *
22: * The following had better agree about the binary FWT format:
23: * troff/fwtable.c/dump_chartab() writes binary FWT from HP PCL
24: * troff/fwt_PS.c/outputPS() writes binary FWT from PostScript AFM
25: * troff/fwt_TFM.c/outputTFM() writes binary FWT from HP TFM
26: * troff/fonts.c/loadfont() reads binary FWT for troff
27: *
28: * Modified 12/12/90-12/28/90 by steve from dag's original hptable.c source;
29: * the coding could definitely be cleaner.
30: */
31:
32: #include <stdio.h>
33: #include <canon.h>
34: #include "fwtable.h"
35:
36: /* PCL bitmap font descriptor format. Cf. "HP LJ III Tech Ref Man", p. 10-7. */
37: typedef struct fnt_hdr {
38: short f_hsize;
39: uchar f_desc_format;
40: uchar f_font_type;
41: uchar f_style_msb;
42: uchar f_reserved1;
43: short f_baseline;
44: short f_cell_width;
45: short f_cell_height;
46: uchar f_orientation;
47: uchar f_spacing;
48: short f_symbol_set;
49: short f_pitch;
50: short f_height;
51: short f_xheight;
52: uchar f_width_type;
53: uchar f_style;
54: char f_weight; /* specifically signed! */
55: uchar f_face;
56: uchar f_comment[0]; /* remainder in add_info */
57: } font_header;
58:
59: typedef struct add_info {
60: char a_slant; /* Slant information */
61: uchar a_serif; /* Serif style (see serif table) */
62: uchar a_quality; /* Quality level */
63: uchar a_placement; /* Placement */
64: char a_underline; /* Underline position */
65: uchar a_uheight; /* Underline height in dots */
66: short a_lspacing; /* Optimum line spacing in dots * 4 */
67: short a_nwidth; /* Average lower-case char width * 4 */
68: short a_firstc; /* First code */
69: short a_lastc; /* Last code */
70: uchar a_piextend; /* Extend for pitch */
71: uchar a_poextend; /* Extend for height */
72: short a_cap_height; /* Cap height */
73: long a_fontnum; /* Font Number */
74: char a_fontname[16]; /* Font name */
75: } font_extra;
76:
77: typedef struct chr_hdr {
78: uchar c_format; /* Character format (4) */
79: uchar c_continuation; /* Continuation flag */
80: uchar c_size; /* Header size to follow*/
81: uchar c_class; /* Format class 1=raster*/
82: uchar c_orientation; /* Orientation */
83: uchar c_empty2; /* more padding... */
84: short c_left_offset; /* left offset */
85: short c_top_offset; /* top offset */
86: short c_char_width; /* character width */
87: short c_char_height; /* character height */
88: short c_delta_x; /* delta X */
89: uchar c_data[0]; /* character data */
90: } character_header;
91: character_header *char_def();
92:
93: /* Global arrays. */
94: /*
95: * Typefaces.
96: * Cf. "HP LJ III Tech Ref Man", pp. 10-27ff.
97: * The list given there gives all values 0-84 and some values 87-168.
98: * This list is truncated in the name of sanity.
99: */
100: char *faces[] = {
101: "LinePrinter", /* 0 */
102: "Pica", /* 1 */
103: "Elite", /* 2 */
104: "Courier", /* 3 */
105: "Helvetica", /* 4 */
106: "Times", /* 5 */
107: "LetterGothic", /* 6 */
108: "Script", /* 7 */
109: "Prestige", /* 8 */
110: "Caslon", /* 9 */
111: "Orator", /* 10 */
112: "Presentation", /* 11 */
113: "HelveticaCondensed", /* 12 */
114: "Serifa", /* 13 */
115: "Futura", /* 14 */
116: "Palatino", /* 15 */
117: "ITCSouvenir", /* 16 */
118: "Optima", /* 17 */
119: "ITCGaramond", /* 18 */
120: "CooperBlack", /* 19 */
121: "Coronet", /* 20 */
122: "Broadway", /* 21 */
123: "BauerBodoniBlack", /* 22 */
124: "NewCenturySchlbk", /* 23 */
125: " " /* >23 */
126: };
127: #define NFACES ((sizeof faces / sizeof faces[0]) - 1)
128:
129: /* f_serif values */
130: char *serif_tab[] = {
131: "sans serif square", /* 0 */
132: "sans serif round", /* 1 */
133: "serif line", /* 2 */
134: "serif triangle", /* 3 */
135: "serif swath", /* 4 */
136: "serif block", /* 5 */
137: "serif bracket", /* 6 */
138: "rounded bracket", /* 7 */
139: "flair serif", /* 8 */
140: "script nonconnecting", /* 9 */
141: "script joining", /* 10 */
142: "script calligraphic", /* 11 */
143: "script broken letter", /* 12 */
144: "serif value out-of-range" /* >12 */
145: };
146: #define NSERIFS ((sizeof serif_tab / sizeof serif_tab[0]) - 1)
147:
148: /* Style posture values. The width and structure info is ignored for now. */
149: char *posture_tab[] = {
150: "upright", /* 0 */
151: "italic", /* 1 */
152: "alternate italic", /* 2 */
153: "reserved" /* 3 */
154: };
155:
156: /* Orientation. */
157: char *orient_tab[] = {
158: "portrait", /* 0 */
159: "landscape", /* 1 */
160: "reverse portrait", /* 2 */
161: "reverse landscape" /* 3 */
162: };
163:
164: /* Globals. */
165: char buf[NBUF]; /* String conversion */
166: int cflag; /* Write C not binary */
167: int char_datasize[NWIDTH]; /* Character size */
168: int char_movement[NWIDTH]; /* Character movement */
169: font_header *fhp; /* Font header pointer */
170: FILE *ifp = stdin; /* The input FILE */
171: int ipointsz; /* Integer point size */
172: FILE *ofp = stdout; /* The output FILE */
173: int pflag; /* PostScript input */
174: char *symset; /* Desired symbol set */
175: int tflag; /* TFM input */
176: int this_char; /* Current character */
177: int vflag; /* Verbose */
178:
179: main(argc, argv) int argc; char *argv[];
180: {
181: register char *s;
182:
183: /* Process command-line options. */
184: while (argc > 1 && argv[1][0] == '-') {
185: for (s = &argv[1][1]; *s; s++) {
186: switch(*s) {
187: case 'c':
188: ++cflag;
189: break;
190: case 'p':
191: ++pflag;
192: break;
193: case 's':
194: symset = ++s;
195: while (*s)
196: ++s;
197: --s;
198: break;
199: case 't':
200: ++tflag;
201: break;
202: case 'v':
203: ++vflag;
204: break;
205: case 'V':
206: fprintf(stderr, "fwtable: V%s\n", VERSION);
207: break;
208: default:
209: usage();
210: }
211: }
212: --argc;
213: ++argv;
214: }
215: if (pflag && tflag)
216: fatal("options -p and -t are mutually exclusive");
217: if (symset != NULL && !tflag)
218: fatal("-s option requires -t option");
219:
220: /* Set up input and output FILEs. */
221: if (argc > 1 && (ifp = fopen(argv[1], "rb")) == NULL)
222: fatal("cannot open input file \"%s\"", argv[1]);
223: else if (argc > 2 && (ofp = fopen(argv[2], "w")) == NULL)
224: fatal("cannot open output file \"%s\"", argv[2]);
225: else if (argc > 3)
226: usage();
227:
228: /* Do the work. */
229: if (pflag) {
230: /* PostScript. */
231: inputPS();
232: outputPS();
233: } else if (tflag) {
234: /* TFM. */
235: inputTFM();
236: outputTFM();
237: } else {
238: /* PCL. */
239: if (argc > 1 && cflag)
240: fprintf(ofp,"/* File %s */\n", argv[1]);
241: base();
242: }
243:
244: /* Close FILEs and exit. */
245: if (ifp != stdin && fclose(ifp) == EOF)
246: fatal("cannot close input file \"%s\"", argv[1]);
247: else if (ofp != stdout && fclose(ofp) == EOF)
248: fatal("cannot close output file \"%s\"", argv[2]);
249: exit(0);
250: }
251:
252: /*
253: * Allocate size bytes.
254: */
255: char *
256: alloc(size) register unsigned int size;
257: {
258: register char *s;
259:
260: if ((s = malloc(size)) == NULL)
261: fatal("out of space");
262: return s;
263: }
264:
265: void
266: base()
267: {
268: register int c;
269:
270: /* Initialize. */
271: for (c = 0 ; c < NWIDTH; c++) {
272: char_movement[c] = -1;
273: char_datasize[c] = 0;
274: }
275:
276: /* Read the font description. */
277: while ((c = fgetc(ifp)) != EOF) {
278: if (c == '\033')
279: escape();
280: else
281: if (c)
282: nonfatal("unexpected char (0x%02x)", c);
283: }
284:
285: /* Dump character table. */
286: dump_chartab();
287: if (fhp != NULL)
288: free(fhp);
289: }
290:
291: int
292: char_code(code) int code;
293: {
294: #ifdef VERBOSE
295: if (cflag)
296: fprintf(ofp,"Character Code 0x%02x\n", code);
297: #endif
298: this_char = code;
299: return code;
300: }
301:
302: character_header *
303: char_def(size) int size;
304: {
305: register character_header *ch;
306:
307: ch = alloc(size);
308: ch->c_format = getuchar();
309: ch->c_continuation = getuchar();
310: ch->c_size = getuchar();
311: ch->c_class = getuchar();
312: ch->c_orientation = getuchar();
313: ch->c_empty2 = getuchar();
314: ch->c_left_offset = getshort();
315: ch->c_top_offset = getshort();
316: ch->c_char_width = getshort();
317: ch->c_char_height = getshort();
318: ch->c_delta_x = getshort();
319: if (size > 16)
320: getextra(ch->c_data, size-16);
321: return ch;
322: }
323:
324: /*
325: * Dump the character width table.
326: */
327: void
328: dump_chartab()
329: {
330: register int c, first, last, max, w;
331: register long dsize;
332: int mult, div, scale;
333:
334: /* Find first, last, max values in char_movement[]. */
335: for (c = first = last = max = 0; c < NWIDTH; c++) {
336: if (char_movement[c] >= 0) {
337: if (first == 0)
338: first = c;
339: if (max < char_movement[c])
340: max = char_movement[c];
341: last = c;
342: } else
343: char_movement[c] = 0;
344: }
345:
346: /*
347: * Calculate multiplier and divisor to convert entries to troff units.
348: * Character deltax is in quarter dots, so movement in troff units is
349: * deltax * 720 / 1200.
350: * and 720/1200 == 3/5.
351: * troff multiplies by pointsize, this predivides accordingly;
352: * this simplifies scaling.
353: */
354: mult = 3;
355: div = ipointsz * 5;
356: if (max > 255) {
357: /* Max deltax is too big to fit in char, scale accordingly. */
358: scale = (max / 256) + 1;
359: mult *= scale;
360: for (c = 0; c < NWIDTH; c++)
361: if (char_movement[c] > 0)
362: char_movement[c] /= scale;
363: }
364: /* Reduce if possible. */
365: for (w = mult; w > 1; w--) {
366: if ((mult % w) == 0 && (div % w) == 0) {
367: div /= w;
368: mult /= w;
369: }
370: }
371: putshort(mult); /* short f_num */
372: putshort(div); /* short f_den */
373:
374: /* Dump the movement table. */
375: if (cflag) {
376: fprintf(ofp,"\t\t/* Movement table: first = %d, last = %d */\n",
377: first, last);
378: fprintf(ofp,"\t\t{\n");
379: }
380: dsize = 0L;
381: for (w = c = 0; c < NWIDTH; c++) {
382: dsize += char_datasize[c];
383: if (cflag) {
384: if (w == 0)
385: fprintf(ofp,"\t\t\t");
386: fprintf(ofp,"%3d", char_movement[c]);
387: fputc((c < NWIDTH-1) ? ',' : ' ', ofp);
388: if (++w > 7) {
389: w = 0;
390: fprintf(ofp,"\t/* 0x%02x-0x%02x */\n", c-7, c);
391: }
392: } else
393: fputc(char_movement[c], ofp);
394: }
395: if (cflag) {
396: fprintf(ofp,"\t\t}\n");
397: fprintf(ofp,"\t/* Size of font data (in bytes): %ld */\n", dsize);
398: fprintf(ofp,"\t}\n");
399: }
400: }
401:
402: #ifdef VERBOSE
403: #ifdef GLYPH
404: void
405: dump_glyph(width, height, data) register uchar *data;
406: {
407: register int c, d, f, g;
408:
409: width += 7;
410: width >>= 3;
411: fprintf(ofp,"-----------------------------------\n");
412: for (c=0; c<height; c++) {
413: for (d=0; d<width; d++) {
414: f = *data++;
415: for (g = 0; g < 8; g++) {
416: if (f & 0x80)
417: fprintf(ofp,"*");
418: else
419: fprintf(ofp,".");
420: f <<= 1;
421: }
422: }
423: fprintf(ofp,"\n");
424: }
425: fprintf(ofp,"-----------------------------------\n");
426: }
427: #endif
428: #endif
429:
430: /*
431: * Process an escape sequence.
432: * The <Esc> has already been read.
433: */
434: void
435: escape()
436: {
437: register int c;
438:
439: c = getuchar();
440: switch (c) {
441: case '*': escape_star();
442: break;
443: case '(': escape_oparen();
444: break;
445: case ')': escape_cparen();
446: break;
447: default: nonfatal("unknown escape sequence (0x1B 0x%02x ...)", c);
448: break;
449: }
450: }
451:
452: /*
453: * Process a font defintition:
454: * <Esc> ) s <#> W <font header>
455: */
456: void
457: escape_cparen()
458: {
459: register int c, q;
460: register font_extra *fe;
461: char *cp;
462: double pointsz;
463:
464: if ((c = getuchar()) != 's') {
465: nonfatal("unknown sequence \\033)%c", c);
466: return;
467: }
468: q = getparm();
469: if ((c = getuchar()) != 'W') {
470: nonfatal("unknown sequence \\033)s%d%c", q, c);
471: return;
472: }
473: read_header(q);
474: /* pointsz is height*72/1200, 72/1200 == 3/50 */
475: pointsz = ((double)(3.0*fhp->f_height))/50.0;
476: if (cflag) {
477: fprintf(ofp, "/*\n * Font Definition:\n");
478: fprintf(ofp, " * Header size: %d\n", fhp->f_hsize);
479: fprintf(ofp, " * %s bits\n", ((fhp->f_font_type) ? "Eight" : "Seven"));
480: fprintf(ofp, " * Orientation: %s\n", orient_tab[fhp->f_orientation]);
481: fprintf(ofp, " * Spacing: %s\n", ((fhp->f_spacing) ? "variable" : "fixed"));
482: fprintf(ofp, " * Baseline: %d\n", fhp->f_baseline);
483: fprintf(ofp, " * Cell width: %d\n", fhp->f_cell_width);
484: fprintf(ofp, " * Cell height: %d\n", fhp->f_cell_height);
485: fprintf(ofp, " * Pitch: %d\n", fhp->f_pitch);
486: fprintf(ofp, " * Height: %d\n", fhp->f_height);
487: fprintf(ofp, " * Weight: %d\n", fhp->f_weight);
488: fprintf(ofp, " * Style: %s\n", posture_tab[(fhp->f_style)%4]);
489: fprintf(ofp, " * Typeface: %s\n", faces[fhp->f_face]);
490: fprintf(ofp, " * Designator: %d%c\n",
491: fhp->f_symbol_set / 32,
492: fhp->f_symbol_set % 32 + 64);
493: }
494: if (fhp->f_hsize > 26) {
495: fe = fhp->f_comment;
496: pointsz += ((double) fe->a_poextend)/4275.0;
497: if (fe->a_serif > NSERIFS)
498: fe->a_serif = NSERIFS;
499: if (cflag) {
500: fprintf(ofp, " * Slant: %d\n", fe->a_slant);
501: fprintf(ofp, " * %s\n", serif_tab[fe->a_serif]);
502: fprintf(ofp, " * Quality: %d\n", fe->a_quality);
503: fprintf(ofp, " * First: 0x%02x\n", fe->a_firstc);
504: fprintf(ofp, " * Last: 0x%02x\n", fe->a_lastc);
505: fprintf(ofp, " * Underline pos: %d\n", fe->a_underline);
506: fprintf(ofp, " * Height: %d\n", fe->a_uheight);
507: fprintf(ofp, " * Line spacing: %u\n", fe->a_lspacing);
508: fprintf(ofp, " * Nominal width: %u\n", fe->a_nwidth);
509: fprintf(ofp, " * Pitch extend: %d\n", fe->a_piextend);
510: fprintf(ofp, " * Height extend: %d\n", fe->a_poextend);
511: fprintf(ofp, " * Font number: %ld\n", fe->a_fontnum);
512: fprintf(ofp, " * Font name: %16s\n", fe->a_fontname);
513: }
514: }
515: if (cflag && q > fhp->f_hsize) {
516: register uchar *sp, *ep;
517: register int c;
518:
519: c = 0;
520: sp = (char *)fhp;
521: ep = sp + q;
522: sp += fhp->f_hsize;
523: while (sp < ep) {
524: if (c == 0)
525: fprintf(ofp," # ");
526: if (*sp >= 0x20 && *sp < 0x7F)
527: fprintf(ofp,"%c", *sp++);
528: else {
529: fprintf(ofp,"\\x%02x", *sp++);
530: c += 3;
531: }
532: if (++c > 72) {
533: c = 0;
534: fprintf(ofp," #\n");
535: }
536: }
537: }
538: ipointsz = (int)(pointsz*10+.5); /* integer pointsize */
539: if (cflag)
540: fprintf(ofp,"\n */\n");
541:
542: /* Build a descriptive name. */
543: sprintf(buf, "%s %.2f point ", faces[fhp->f_face], pointsz);
544: cp = &buf[strlen(buf)];
545: if (fhp->f_weight == 3)
546: strcpy(cp, "bold ");
547: else if (fhp->f_weight != 0)
548: sprintf(cp, "%d weight ", fhp->f_weight);
549: cp = &buf[strlen(buf)];
550: if (fhp->f_style%4 != 0)
551: sprintf(cp, "%s ", posture_tab[(fhp->f_style)%4]);
552: if (fhp->f_orientation != 0)
553: strcat(cp, orient_tab[fhp->f_orientation]);
554: if (vflag)
555: fprintf(stderr,"\t%s\n", buf);
556: if (cflag)
557: fprintf(ofp, "\t{\n\t\t\"%s\",\n", buf);
558: else
559: putstring(buf); /* char *f_descr */
560:
561: if (cflag)
562: fprintf(ofp, "\t\t\"\",\t/* PostScript name */\n");
563: else
564: putstring(""); /* char *f_PSname */
565:
566: /* Font parameters. */
567: putshort(FLAG_PCL); /* flags */
568: putshort(fhp->f_font_type);
569: putshort(fhp->f_orientation);
570: putshort(fhp->f_spacing);
571: putshort(fhp->f_symbol_set);
572: putshort(fhp->f_pitch);
573: putshort(ipointsz);
574: putshort(fhp->f_style);
575: putshort(fhp->f_weight);
576: putshort(fhp->f_face);
577: }
578:
579: /*
580: * Process a character definition:
581: * <Esc> ( s <#> W <char data>
582: */
583: void
584: escape_oparen()
585: {
586: register int c;
587: register int q;
588: register character_header *ch;
589:
590: if ((c = getuchar()) != 's') {
591: nonfatal("unknown sequence \\033(%c", c);
592: return;
593: }
594: q = getparm();
595: if ((c = getuchar()) != 'W') {
596: nonfatal("unknown sequence \\033(s%d%c", q, c);
597: return;
598: }
599: ch = char_def(q);
600:
601: #ifdef VERBOSE
602: fprintf(ofp,"** %s, left off=%d, top off=%d char width=%d, char height=%d\n",
603: orient_tab[ch->c_orientation],
604: ch->c_left_offset, ch->c_top_offset,
605: ch->c_char_width, ch->c_char_height);
606: fprintf(ofp,"** movement=%d (%d), data length = %d\n",
607: ch->c_delta_x, ch->c_delta_x/4, q-16);
608: #ifdef GLYPH
609: dump_glyph(ch->c_char_width, ch->c_char_height, ch->c_data);
610: #endif
611: #endif
612: char_movement[this_char] = ch->c_delta_x;
613: char_datasize[this_char] = q-16;
614:
615: free(ch);
616: }
617:
618: /*
619: * Process a font id:
620: * <Esc> * c <#> D
621: * or a character code:
622: * <Esc> * c <#> E
623: */
624: void
625: escape_star()
626: {
627: register int c, q;
628:
629: c = getuchar();
630: if (c != 'c') {
631: nonfatal("unknown escape sequence (0x1B 0x%02x 0x%02x ...)",
632: '*', c);
633: return;
634: }
635: q = getparm();
636: c = getuchar();
637: if (c == 'D')
638: nonfatal("Font ID %d", q);
639: else if (c == 'E')
640: char_code(q);
641: else
642: nonfatal("unknown sequence \\033*c%d%c", q, c);
643: }
644:
645: /* VARARGS */
646: void
647: fatal(args) char *args;
648: {
649: fprintf(stderr, "fwtable: ");
650: if (lineno != 0)
651: fprintf(stderr, "%d: ", lineno);
652: fprintf(stderr, "%r\n", &args);
653: exit(1);
654: }
655:
656: /*
657: * Read size bytes into the supplied buffer.
658: */
659: void
660: getextra(bp, size) register uchar *bp; register int size;
661: {
662: while (size-- > 0)
663: *bp++ = getuchar();
664: }
665:
666: /*
667: * Read a numeric parameter and return it.
668: */
669: int
670: getparm()
671: {
672: register int a, c;
673:
674: for (a = 0; (c = getuchar()) >= '0' && c <= '9'; ) {
675: a *= 10;
676: a += c - '0';
677: }
678: ungetc(c, ifp);
679: return a;
680: }
681:
682: /*
683: * Read a short and return it.
684: * The byte order is the opposite of the in-memory i8086 order.
685: */
686: short
687: getshort()
688: {
689: register int s;
690:
691: s = getuchar() << 8;
692: return s | getuchar();
693: }
694:
695: /*
696: * Read an unsigned char and return it.
697: */
698: unsigned int
699: getuchar()
700: {
701: register int c;
702:
703: if ((c = fgetc(ifp)) == EOF)
704: fatal("unexpected end of file");
705: return (c & 0xFF);
706: }
707:
708: /* VARARGS */
709: void
710: nonfatal(args) char *args;
711: {
712: fprintf(stderr, "fwtable: %ld: %r\n", ftell(ifp), &args);
713: }
714:
715: /*
716: * Write count bytes from buf.
717: */
718: void
719: ofpwrite(buf, count) register char *buf; register unsigned int count;
720: {
721: if (fwrite(buf, count, 1, ofp) != 1)
722: fatal("write error");
723: }
724:
725: /*
726: * Write a canonical short.
727: */
728: void
729: putshort(i) int i;
730: {
731: short s;
732:
733: if (cflag)
734: fprintf(ofp, "\t\t%d,\n", i);
735: else {
736: s = (short)i;
737: canshort(s);
738: ofpwrite(&s, sizeof s);
739: }
740: }
741:
742: /*
743: * Write a NUL-terminated string.
744: */
745: void
746: putstring(s) register char *s;
747: {
748: fputs(s, ofp);
749: fputc('\0', ofp);
750: }
751:
752: /*
753: * Read a PCL font header.
754: */
755: void
756: read_header(size) register int size;
757: {
758: register int c;
759:
760: if (fhp != NULL)
761: fatal("multiple font headers");
762: fhp = alloc(size);
763: fhp->f_hsize = getshort();
764: fhp->f_desc_format = getuchar();
765: if (fhp->f_desc_format == 10)
766: fatal("Intellifont scalable fonts not yet supported");
767: fhp->f_font_type = getuchar();
768: fhp->f_style_msb = getuchar();
769: fhp->f_reserved1 = getuchar();
770: fhp->f_baseline = getshort();
771: fhp->f_cell_width = getshort();
772: fhp->f_cell_height = getshort();
773: fhp->f_orientation = getuchar();
774: fhp->f_spacing = getuchar();
775: fhp->f_symbol_set = getshort();
776: fhp->f_pitch = getshort();
777: fhp->f_height = getshort();
778: fhp->f_xheight = getshort();
779: fhp->f_width_type = getuchar();
780: fhp->f_style = getuchar();
781: fhp->f_weight = getuchar();
782: fhp->f_face = getuchar();
783: if (fhp->f_face > NFACES) {
784: /* Use extra entry at end of table. */
785: sprintf(faces[NFACES], "[Typeface %3d]", fhp->f_face);
786: fhp->f_face = NFACES;
787: }
788: if (size > 26)
789: getextra(fhp->f_comment, size-26);
790: /*
791: * Many of the fonts at MWC have a bogus extra ' ' after the font header.
792: * Eat the space silently rather than complaining about unexpected char.
793: */
794: if ((c = fgetc(ifp)) != ' ')
795: ungetc(c, ifp);
796: }
797:
798: void
799: usage()
800: {
801: fprintf(stderr,
802: "Usage: fwtable [ -cptv ] [ -ssymset ] [ infile [ outfile ] ]\n"
803: "Options:\n"
804: "\t-c\t\tWrite C instead of binary\n"
805: "\t-p\t\tInput is PostScript AFM file\n"
806: "\t-ssymset\tSpecify desired symbol set with -t option\n"
807: "\t-t\t\tInput is HP TFM file\n"
808: "\t-v\t\tWrite one-line font description to stderr\n"
809: );
810: exit(1);
811: }
812:
813: /* end of fwtable.c */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.