Blame


1 5cedca1b 2004-05-15 devnull #include "e.h"
2 5cedca1b 2004-05-15 devnull #include "y.tab.h"
3 5cedca1b 2004-05-15 devnull #include <ctype.h>
4 5cedca1b 2004-05-15 devnull
5 5cedca1b 2004-05-15 devnull #define CSSIZE 1000
6 5cedca1b 2004-05-15 devnull char cs[CSSIZE+20]; /* text string converted into this */
7 5cedca1b 2004-05-15 devnull char *csp; /* next spot in cs[] */
8 5cedca1b 2004-05-15 devnull char *psp; /* next character in input token */
9 5cedca1b 2004-05-15 devnull
10 5cedca1b 2004-05-15 devnull int lf, rf; /* temporary spots for left and right fonts */
11 5cedca1b 2004-05-15 devnull int lastft; /* last \f added */
12 5cedca1b 2004-05-15 devnull int nextft; /* next \f to be added */
13 5cedca1b 2004-05-15 devnull
14 5cedca1b 2004-05-15 devnull int pclass; /* class of previous character */
15 5cedca1b 2004-05-15 devnull int nclass; /* class of next character */
16 5cedca1b 2004-05-15 devnull
17 5cedca1b 2004-05-15 devnull int class[LAST][LAST] ={ /* guesswork, tuned to times roman postscript */
18 5cedca1b 2004-05-15 devnull
19 5cedca1b 2004-05-15 devnull /*OT OL IL DG LP RP SL PL IF IJ VB */
20 5cedca1b 2004-05-15 devnull /*OT*/ { 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 0 }, /* OTHER */
21 5cedca1b 2004-05-15 devnull /*OL*/ { 1, 0, 1, 1, 1, 1, 1, 2, 2, 2, 0 }, /* OLET */
22 5cedca1b 2004-05-15 devnull /*IL*/ { 1, 1, 0, 1, 1, 1, 1, 3, 2, 1, 0 }, /* ILET */
23 5cedca1b 2004-05-15 devnull /*DG*/ { 1, 1, 1, 0, 1, 1, 1, 2, 2, 2, 0 }, /* DIG */
24 5cedca1b 2004-05-15 devnull /*LP*/ { 1, 1, 1, 1, 1, 2, 1, 2, 3, 3, 0 }, /* LPAR */
25 5cedca1b 2004-05-15 devnull /*RP*/ { 2, 2, 2, 1, 1, 1, 1, 2, 3, 3, 0 }, /* RPAR */
26 5cedca1b 2004-05-15 devnull /*SL*/ { 1, 1, 1, 1, 1, 1, 1, 2, 2, 1, 0 }, /* SLASH */
27 5cedca1b 2004-05-15 devnull /*PL*/ { 2, 2, 2, 2, 2, 2, 3, 2, 3, 2, 0 }, /* PLUS */
28 5cedca1b 2004-05-15 devnull /*IF*/ { 3, 3, 1, 2, 2, 3, 2, 3, 0, 1, 1 }, /* ILETF */
29 5cedca1b 2004-05-15 devnull /*IJ*/ { 1, 1, 1, 1, 1, 1, 1, 2, 2, 0, 0 }, /* ILETJ */
30 5cedca1b 2004-05-15 devnull /*VB*/ { 4, 4, 4, 4, 4, 4, 4, 4, 5, 4, 1 }, /* VBAR */
31 5cedca1b 2004-05-15 devnull
32 5cedca1b 2004-05-15 devnull };
33 5cedca1b 2004-05-15 devnull
34 5cedca1b 2004-05-15 devnull extern void shim(int, int);
35 5cedca1b 2004-05-15 devnull extern void roman(int);
36 5cedca1b 2004-05-15 devnull extern void sadd(char *);
37 5cedca1b 2004-05-15 devnull extern void cadd(int);
38 5cedca1b 2004-05-15 devnull extern int trans(int, char *);
39 5cedca1b 2004-05-15 devnull
40 5cedca1b 2004-05-15 devnull int textc(void) /* read next UTF rune from psp */
41 5cedca1b 2004-05-15 devnull {
42 5cedca1b 2004-05-15 devnull wchar_t r;
43 5cedca1b 2004-05-15 devnull int w;
44 5cedca1b 2004-05-15 devnull
45 5cedca1b 2004-05-15 devnull w = mbtowc(&r, psp, 3);
46 5cedca1b 2004-05-15 devnull if(w == 0){
47 5cedca1b 2004-05-15 devnull psp++;
48 5cedca1b 2004-05-15 devnull return 0;
49 5cedca1b 2004-05-15 devnull }
50 5cedca1b 2004-05-15 devnull if(w < 0){
51 5cedca1b 2004-05-15 devnull psp += 1;
52 5cedca1b 2004-05-15 devnull return 0x80; /* Plan 9-ism */
53 5cedca1b 2004-05-15 devnull }
54 5cedca1b 2004-05-15 devnull psp += w;
55 5cedca1b 2004-05-15 devnull return r;
56 5cedca1b 2004-05-15 devnull }
57 5cedca1b 2004-05-15 devnull
58 5cedca1b 2004-05-15 devnull void text(int t, char *p1) /* convert text string p1 of type t */
59 5cedca1b 2004-05-15 devnull {
60 5cedca1b 2004-05-15 devnull int c;
61 5cedca1b 2004-05-15 devnull char *p;
62 5cedca1b 2004-05-15 devnull tbl *tp;
63 5cedca1b 2004-05-15 devnull
64 5cedca1b 2004-05-15 devnull yyval = salloc();
65 5cedca1b 2004-05-15 devnull ebase[yyval] = 0;
66 5cedca1b 2004-05-15 devnull eht[yyval] = EM(1.0, ps); /* ht in ems of orig size */
67 5cedca1b 2004-05-15 devnull lfont[yyval] = rfont[yyval] = ROM;
68 5cedca1b 2004-05-15 devnull lclass[yyval] = rclass[yyval] = OTHER;
69 5cedca1b 2004-05-15 devnull if (t == QTEXT) {
70 5cedca1b 2004-05-15 devnull for (p = p1; *p; p++) /* scan for embedded \f's */
71 5cedca1b 2004-05-15 devnull if (*p == '\\' && *(p+1) == 'f')
72 5cedca1b 2004-05-15 devnull break;
73 5cedca1b 2004-05-15 devnull if (*p) /* if found \f, leave it alone and hope */
74 5cedca1b 2004-05-15 devnull p = p1;
75 5cedca1b 2004-05-15 devnull else {
76 5cedca1b 2004-05-15 devnull sprintf(cs, "\\f%s%s\\fP", ftp->name, p1);
77 5cedca1b 2004-05-15 devnull p = cs;
78 5cedca1b 2004-05-15 devnull }
79 5cedca1b 2004-05-15 devnull } else if (t == SPACE)
80 5cedca1b 2004-05-15 devnull p = "\\ ";
81 5cedca1b 2004-05-15 devnull else if (t == THIN)
82 5cedca1b 2004-05-15 devnull p = "\\|";
83 5cedca1b 2004-05-15 devnull else if (t == TAB)
84 5cedca1b 2004-05-15 devnull p = "\\t";
85 5cedca1b 2004-05-15 devnull else if ((tp = lookup(restbl, p1)) != NULL) {
86 5cedca1b 2004-05-15 devnull p = tp->cval;
87 5cedca1b 2004-05-15 devnull } else {
88 5cedca1b 2004-05-15 devnull lf = rf = 0;
89 5cedca1b 2004-05-15 devnull lastft = 0;
90 5cedca1b 2004-05-15 devnull nclass = NONE; /* get started with no class == no pad */
91 5cedca1b 2004-05-15 devnull csp = cs;
92 5cedca1b 2004-05-15 devnull for (psp = p1; (c = textc()) != '\0'; ) {
93 5cedca1b 2004-05-15 devnull nextft = ft;
94 5cedca1b 2004-05-15 devnull pclass = nclass;
95 5cedca1b 2004-05-15 devnull rf = trans(c, p1);
96 5cedca1b 2004-05-15 devnull if (lf == 0) {
97 5cedca1b 2004-05-15 devnull lf = rf; /* left stuff is first found */
98 5cedca1b 2004-05-15 devnull lclass[yyval] = nclass;
99 5cedca1b 2004-05-15 devnull }
100 5cedca1b 2004-05-15 devnull if (csp-cs > CSSIZE)
101 5cedca1b 2004-05-15 devnull ERROR "converted token %.25s... too long", p1 FATAL ;
102 5cedca1b 2004-05-15 devnull }
103 5cedca1b 2004-05-15 devnull sadd("\\fP");
104 5cedca1b 2004-05-15 devnull *csp = '\0';
105 5cedca1b 2004-05-15 devnull p = cs;
106 5cedca1b 2004-05-15 devnull lfont[yyval] = lf;
107 5cedca1b 2004-05-15 devnull rfont[yyval] = rf;
108 5cedca1b 2004-05-15 devnull rclass[yyval] = nclass;
109 5cedca1b 2004-05-15 devnull }
110 5cedca1b 2004-05-15 devnull dprintf(".\t%dtext: S%d <- %s; b=%g,h=%g,lf=%c,rf=%c,ps=%d\n",
111 eb9be703 2006-02-04 devnull t, (int)yyval, p, ebase[yyval], eht[yyval], lfont[yyval], rfont[yyval], ps);
112 eb9be703 2006-02-04 devnull printf(".ds %d \"%s\n", (int)yyval, p);
113 5cedca1b 2004-05-15 devnull }
114 5cedca1b 2004-05-15 devnull
115 5cedca1b 2004-05-15 devnull int isalpharune(int c)
116 5cedca1b 2004-05-15 devnull {
117 5cedca1b 2004-05-15 devnull return ('a'<=c && c<='z') || ('A'<=c && c<='Z');
118 5cedca1b 2004-05-15 devnull }
119 5cedca1b 2004-05-15 devnull
120 5cedca1b 2004-05-15 devnull int isdigitrune(int c)
121 5cedca1b 2004-05-15 devnull {
122 5cedca1b 2004-05-15 devnull return ('0'<=c && c<='9');
123 5cedca1b 2004-05-15 devnull }
124 5cedca1b 2004-05-15 devnull
125 b237df90 2004-05-16 devnull int
126 5cedca1b 2004-05-15 devnull trans(int c, char *p1)
127 5cedca1b 2004-05-15 devnull {
128 5cedca1b 2004-05-15 devnull int f;
129 5cedca1b 2004-05-15 devnull
130 5cedca1b 2004-05-15 devnull if (isalpharune(c) && ft == ITAL && c != 'f' && c != 'j') { /* italic letter */
131 5cedca1b 2004-05-15 devnull shim(pclass, nclass = ILET);
132 5cedca1b 2004-05-15 devnull cadd(c);
133 5cedca1b 2004-05-15 devnull return ITAL;
134 5cedca1b 2004-05-15 devnull }
135 5cedca1b 2004-05-15 devnull if (isalpharune(c) && ft != ITAL) { /* other letter */
136 5cedca1b 2004-05-15 devnull shim(pclass, nclass = OLET);
137 5cedca1b 2004-05-15 devnull cadd(c);
138 5cedca1b 2004-05-15 devnull return ROM;
139 5cedca1b 2004-05-15 devnull }
140 5cedca1b 2004-05-15 devnull if (isdigitrune(c)) {
141 5cedca1b 2004-05-15 devnull shim(pclass, nclass = DIG);
142 5cedca1b 2004-05-15 devnull roman(c);
143 5cedca1b 2004-05-15 devnull return ROM; /* this is the right side font of this object */
144 5cedca1b 2004-05-15 devnull }
145 5cedca1b 2004-05-15 devnull f = ROM;
146 5cedca1b 2004-05-15 devnull nclass = OTHER;
147 5cedca1b 2004-05-15 devnull switch (c) {
148 5cedca1b 2004-05-15 devnull case ':': case ';': case '!': case '%': case '?':
149 5cedca1b 2004-05-15 devnull shim(pclass, nclass);
150 5cedca1b 2004-05-15 devnull roman(c);
151 5cedca1b 2004-05-15 devnull return f;
152 5cedca1b 2004-05-15 devnull case '(': case '[':
153 5cedca1b 2004-05-15 devnull shim(pclass, nclass = LPAR);
154 5cedca1b 2004-05-15 devnull roman(c);
155 5cedca1b 2004-05-15 devnull return f;
156 5cedca1b 2004-05-15 devnull case ')': case ']':
157 5cedca1b 2004-05-15 devnull shim(pclass, nclass = RPAR);
158 5cedca1b 2004-05-15 devnull roman(c);
159 5cedca1b 2004-05-15 devnull return f;
160 5cedca1b 2004-05-15 devnull case ',':
161 5cedca1b 2004-05-15 devnull shim(pclass, nclass = OTHER);
162 5cedca1b 2004-05-15 devnull roman(c);
163 5cedca1b 2004-05-15 devnull return f;
164 5cedca1b 2004-05-15 devnull case '.':
165 5cedca1b 2004-05-15 devnull if (rf == ROM)
166 5cedca1b 2004-05-15 devnull roman(c);
167 5cedca1b 2004-05-15 devnull else
168 5cedca1b 2004-05-15 devnull cadd(c);
169 5cedca1b 2004-05-15 devnull return f;
170 5cedca1b 2004-05-15 devnull case '|': /* postscript needs help with default width! */
171 5cedca1b 2004-05-15 devnull shim(pclass, nclass = VBAR);
172 5cedca1b 2004-05-15 devnull sadd("\\v'.17m'\\z|\\v'-.17m'\\|"); /* and height */
173 5cedca1b 2004-05-15 devnull return f;
174 5cedca1b 2004-05-15 devnull case '=':
175 5cedca1b 2004-05-15 devnull shim(pclass, nclass = PLUS);
176 5cedca1b 2004-05-15 devnull sadd("\\(eq");
177 5cedca1b 2004-05-15 devnull return f;
178 5cedca1b 2004-05-15 devnull case '+':
179 5cedca1b 2004-05-15 devnull shim(pclass, nclass = PLUS);
180 5cedca1b 2004-05-15 devnull sadd("\\(pl");
181 5cedca1b 2004-05-15 devnull return f;
182 5cedca1b 2004-05-15 devnull case '>':
183 5cedca1b 2004-05-15 devnull case '<': /* >, >=, >>, <, <-, <=, << */
184 5cedca1b 2004-05-15 devnull shim(pclass, nclass = PLUS);
185 5cedca1b 2004-05-15 devnull if (*psp == '=') {
186 5cedca1b 2004-05-15 devnull sadd(c == '<' ? "\\(<=" : "\\(>=");
187 5cedca1b 2004-05-15 devnull psp++;
188 5cedca1b 2004-05-15 devnull } else if (c == '<' && *psp == '-') { /* <- only */
189 5cedca1b 2004-05-15 devnull sadd("\\(<-");
190 5cedca1b 2004-05-15 devnull psp++;
191 5cedca1b 2004-05-15 devnull } else if (*psp == c) { /* << or >> */
192 5cedca1b 2004-05-15 devnull cadd(c);
193 5cedca1b 2004-05-15 devnull cadd(c);
194 5cedca1b 2004-05-15 devnull psp++;
195 5cedca1b 2004-05-15 devnull } else {
196 5cedca1b 2004-05-15 devnull cadd(c);
197 5cedca1b 2004-05-15 devnull }
198 5cedca1b 2004-05-15 devnull return f;
199 5cedca1b 2004-05-15 devnull case '-':
200 5cedca1b 2004-05-15 devnull shim(pclass, nclass = PLUS); /* probably too big for ->'s */
201 5cedca1b 2004-05-15 devnull if (*psp == '>') {
202 5cedca1b 2004-05-15 devnull sadd("\\(->");
203 5cedca1b 2004-05-15 devnull psp++;
204 5cedca1b 2004-05-15 devnull } else {
205 5cedca1b 2004-05-15 devnull sadd("\\(mi");
206 5cedca1b 2004-05-15 devnull }
207 5cedca1b 2004-05-15 devnull return f;
208 5cedca1b 2004-05-15 devnull case '/':
209 5cedca1b 2004-05-15 devnull shim(pclass, nclass = SLASH);
210 5cedca1b 2004-05-15 devnull cadd('/');
211 5cedca1b 2004-05-15 devnull return f;
212 5cedca1b 2004-05-15 devnull case '~':
213 5cedca1b 2004-05-15 devnull case ' ':
214 5cedca1b 2004-05-15 devnull sadd("\\|\\|");
215 5cedca1b 2004-05-15 devnull return f;
216 5cedca1b 2004-05-15 devnull case '^':
217 5cedca1b 2004-05-15 devnull sadd("\\|");
218 5cedca1b 2004-05-15 devnull return f;
219 5cedca1b 2004-05-15 devnull case '\\': /* troff - pass only \(xx without comment */
220 5cedca1b 2004-05-15 devnull shim(pclass, nclass);
221 5cedca1b 2004-05-15 devnull cadd('\\');
222 5cedca1b 2004-05-15 devnull cadd(c = *psp++);
223 5cedca1b 2004-05-15 devnull if (c == '(' && *psp && *(psp+1)) {
224 5cedca1b 2004-05-15 devnull cadd(*psp++);
225 5cedca1b 2004-05-15 devnull cadd(*psp++);
226 5cedca1b 2004-05-15 devnull } else
227 5cedca1b 2004-05-15 devnull fprintf(stderr, "eqn warning: unquoted troff command \\%c, file %s:%d\n",
228 5cedca1b 2004-05-15 devnull c, curfile->fname, curfile->lineno);
229 5cedca1b 2004-05-15 devnull return f;
230 5cedca1b 2004-05-15 devnull case '\'':
231 5cedca1b 2004-05-15 devnull shim(pclass, nclass);
232 5cedca1b 2004-05-15 devnull sadd("\\(fm");
233 5cedca1b 2004-05-15 devnull return f;
234 5cedca1b 2004-05-15 devnull
235 5cedca1b 2004-05-15 devnull case 'f':
236 5cedca1b 2004-05-15 devnull if (ft == ITAL) {
237 5cedca1b 2004-05-15 devnull shim(pclass, nclass = ILETF);
238 5cedca1b 2004-05-15 devnull cadd('f');
239 5cedca1b 2004-05-15 devnull f = ITAL;
240 5cedca1b 2004-05-15 devnull } else
241 5cedca1b 2004-05-15 devnull cadd('f');
242 5cedca1b 2004-05-15 devnull return f;
243 5cedca1b 2004-05-15 devnull case 'j':
244 5cedca1b 2004-05-15 devnull if (ft == ITAL) {
245 5cedca1b 2004-05-15 devnull shim(pclass, nclass = ILETJ);
246 5cedca1b 2004-05-15 devnull cadd('j');
247 5cedca1b 2004-05-15 devnull f = ITAL;
248 5cedca1b 2004-05-15 devnull } else
249 5cedca1b 2004-05-15 devnull cadd('j');
250 5cedca1b 2004-05-15 devnull return f;
251 5cedca1b 2004-05-15 devnull default:
252 5cedca1b 2004-05-15 devnull shim(pclass, nclass);
253 5cedca1b 2004-05-15 devnull cadd(c);
254 5cedca1b 2004-05-15 devnull return ft==ITAL ? ITAL : ROM;
255 5cedca1b 2004-05-15 devnull }
256 5cedca1b 2004-05-15 devnull }
257 5cedca1b 2004-05-15 devnull
258 5cedca1b 2004-05-15 devnull char *pad(int n) /* return the padding as a string */
259 5cedca1b 2004-05-15 devnull {
260 5cedca1b 2004-05-15 devnull static char buf[20];
261 5cedca1b 2004-05-15 devnull
262 5cedca1b 2004-05-15 devnull buf[0] = 0;
263 5cedca1b 2004-05-15 devnull if (n < 0) {
264 5cedca1b 2004-05-15 devnull sprintf(buf, "\\h'-%du*\\w'\\^'u'", -n);
265 5cedca1b 2004-05-15 devnull return buf;
266 5cedca1b 2004-05-15 devnull }
267 5cedca1b 2004-05-15 devnull for ( ; n > 1; n -= 2)
268 5cedca1b 2004-05-15 devnull strcat(buf, "\\|");
269 5cedca1b 2004-05-15 devnull if (n > 0)
270 5cedca1b 2004-05-15 devnull strcat(buf, "\\^");
271 5cedca1b 2004-05-15 devnull return buf;
272 5cedca1b 2004-05-15 devnull }
273 5cedca1b 2004-05-15 devnull
274 5cedca1b 2004-05-15 devnull void shim(int lc, int rc) /* add padding space suitable to left and right classes */
275 5cedca1b 2004-05-15 devnull {
276 5cedca1b 2004-05-15 devnull sadd(pad(class[lc][rc]));
277 5cedca1b 2004-05-15 devnull }
278 5cedca1b 2004-05-15 devnull
279 5cedca1b 2004-05-15 devnull void roman(int c) /* add char c in "roman" font */
280 5cedca1b 2004-05-15 devnull {
281 5cedca1b 2004-05-15 devnull nextft = ROM;
282 5cedca1b 2004-05-15 devnull cadd(c);
283 5cedca1b 2004-05-15 devnull }
284 5cedca1b 2004-05-15 devnull
285 5cedca1b 2004-05-15 devnull void sadd(char *s) /* add string s to cs */
286 5cedca1b 2004-05-15 devnull {
287 5cedca1b 2004-05-15 devnull while (*s)
288 5cedca1b 2004-05-15 devnull cadd(*s++);
289 5cedca1b 2004-05-15 devnull }
290 5cedca1b 2004-05-15 devnull
291 5cedca1b 2004-05-15 devnull void cadd(int c) /* add character c to end of cs */
292 5cedca1b 2004-05-15 devnull {
293 5cedca1b 2004-05-15 devnull char *p;
294 5cedca1b 2004-05-15 devnull int w;
295 5cedca1b 2004-05-15 devnull
296 5cedca1b 2004-05-15 devnull if (lastft != nextft) {
297 5cedca1b 2004-05-15 devnull if (lastft != 0) {
298 5cedca1b 2004-05-15 devnull *csp++ = '\\';
299 5cedca1b 2004-05-15 devnull *csp++ = 'f';
300 5cedca1b 2004-05-15 devnull *csp++ = 'P';
301 5cedca1b 2004-05-15 devnull }
302 5cedca1b 2004-05-15 devnull *csp++ = '\\';
303 5cedca1b 2004-05-15 devnull *csp++ = 'f';
304 5cedca1b 2004-05-15 devnull if (ftp == ftstack) { /* bottom level */
305 5cedca1b 2004-05-15 devnull if (ftp->ft == ITAL) /* usual case */
306 5cedca1b 2004-05-15 devnull *csp++ = nextft;
307 5cedca1b 2004-05-15 devnull else /* gfont set, use it */
308 b237df90 2004-05-16 devnull for (p = ftp->name; (*csp = *p++); )
309 5cedca1b 2004-05-15 devnull csp++;
310 5cedca1b 2004-05-15 devnull } else { /* inside some kind of font ... */
311 b237df90 2004-05-16 devnull for (p = ftp->name; (*csp = *p++); )
312 5cedca1b 2004-05-15 devnull csp++;
313 5cedca1b 2004-05-15 devnull }
314 5cedca1b 2004-05-15 devnull lastft = nextft;
315 5cedca1b 2004-05-15 devnull }
316 5cedca1b 2004-05-15 devnull w = wctomb(csp, c);
317 5cedca1b 2004-05-15 devnull if(w > 0) /* ignore bad characters */
318 5cedca1b 2004-05-15 devnull csp += w;
319 5cedca1b 2004-05-15 devnull }