1 /*
2 * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
3 * Use is subject to license terms.
4 */
5
6 /* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */
7 /* All Rights Reserved */
8
9 /*
10 * Copyright (c) 1980 Regents of the University of California.
11 * All rights reserved. The Berkeley software License Agreement
12 * specifies the terms and conditions for redistribution.
13 */
14
15 #pragma ident "%Z%%M% %I% %E% SMI"
16
17 #include "e.h"
18 #include "e.def"
19 #include <locale.h>
20
21 int csp;
22 int psp;
23 #define CSSIZE 400
24 char cs[420];
25
26 int lf, rf; /* temporary spots for left and right fonts */
27
28 void name4(int, int);
29 void roman(int);
30 void shim(void);
31 int trans(int, char *);
32
33 void
text(int t,char * p1)34 text(int t, char *p1)
35 {
36 int c;
37 char *p;
38 tbl *tp, *lookup();
39 extern tbl *restbl[];
40
41 yyval = oalloc();
42 ebase[yyval] = 0;
43 #ifndef NEQN
44 eht[yyval] = VERT(EM(1.0, EFFPS(ps))); /* ht in machine units */
45 #else /* NEQN */
46 eht[yyval] = VERT(2); /* 2 half-spaces */
47 #endif /* NEQN */
48 lfont[yyval] = rfont[yyval] = ROM;
49 if (t == QTEXT)
50 p = p1;
51 else if (t == SPACE)
52 p = "\\ ";
53 else if (t == THIN)
54 p = "\\|";
55 else if (t == TAB)
56 p = "\\t";
57 else if ((tp = lookup(restbl, p1, NULL)) != NULL)
58 p = tp->defn;
59 else {
60 lf = rf = 0;
61 for (csp = psp = 0; (c = p1[psp++]) != '\0'; ) {
62 rf = trans(c, p1);
63 if (lf == 0)
64 lf = rf; /* save first */
65 if (csp > CSSIZE)
66 error(FATAL, gettext(
67 "converted token %.25s... too long"), p1);
68 }
69 cs[csp] = '\0';
70 p = cs;
71 lfont[yyval] = lf;
72 rfont[yyval] = rf;
73 }
74 if (dbg)
75 printf(".\t%dtext: S%d <- %s; b=%d,h=%d,lf=%c,rf=%c\n",
76 t, yyval, p, ebase[yyval], eht[yyval], lfont[yyval],
77 rfont[yyval]);
78 printf(".ds %d \"%s\n", yyval, p);
79 }
80
81 int
trans(int c,char * p1)82 trans(int c, char *p1)
83 {
84 int f;
85 f = ROM;
86 switch (c) {
87 case '0': case '1': case '2': case '3': case '4':
88 case '5': case '6': case '7': case '8': case '9':
89 case ':': case ';': case '!': case '%':
90 case '(': case '[': case ')': case ']':
91 case ',':
92 if (rf == ITAL)
93 shim();
94 roman(c); break;
95 case '.':
96 if (rf == ROM)
97 roman(c);
98 else
99 cs[csp++] = c;
100 f = rf;
101 break;
102 case '|':
103 if (rf == ITAL)
104 shim();
105 shim(); roman(c); shim(); break;
106 case '=':
107 if (rf == ITAL)
108 shim();
109 name4('e', 'q');
110 break;
111 case '+':
112 if (rf == ITAL)
113 shim();
114 name4('p', 'l');
115 break;
116 case '>': case '<':
117 if (rf == ITAL)
118 shim();
119 if (p1[psp] == '=') { /* look ahead for == <= >= */
120 name4(c, '=');
121 psp++;
122 } else {
123 cs[csp++] = c;
124 }
125 break;
126 case '-':
127 if (rf == ITAL)
128 shim();
129 if (p1[psp] == '>') {
130 name4('-', '>'); psp++;
131 } else {
132 name4('m', 'i');
133 }
134 break;
135 case '/':
136 if (rf == ITAL)
137 shim();
138 name4('s', 'l');
139 break;
140 case '~': case ' ':
141 shim(); shim(); break;
142 case '^':
143 shim(); break;
144 case '\\': /* troff - pass 2 or 3 more chars */
145 if (rf == ITAL)
146 shim();
147 cs[csp++] = c; cs[csp++] = c = p1[psp++]; cs[csp++] = p1[psp++];
148 if (c == '(') cs[csp++] = p1[psp++];
149 if (c == '*' && cs[csp-1] == '(') {
150 cs[csp++] = p1[psp++];
151 cs[csp++] = p1[psp++];
152 }
153 break;
154 case '\'':
155 cs[csp++] = '\\';
156 cs[csp++] = 'f';
157 cs[csp++] = rf == ITAL ? ITAL : ROM;
158 name4('f', 'm');
159 cs[csp++] = '\\'; cs[csp++] = 'f'; cs[csp++] = 'P';
160 f = rf == ITAL ? ITAL : ROM;
161 break;
162
163 case 'f':
164 if (ft == ITAL) {
165 cs[csp++] = '\\'; cs[csp++] = '^';
166 cs[csp++] = 'f';
167
168 /* trying | instead of ^ */
169 cs[csp++] = '\\'; cs[csp++] = '|';
170
171 f = ITAL;
172 }
173 else
174 cs[csp++] = 'f';
175 break;
176 case 'j':
177 if (ft == ITAL) {
178 cs[csp++] = '\\'; cs[csp++] = '^';
179 cs[csp++] = 'j';
180 f = ITAL;
181 }
182 else
183 cs[csp++] = 'j';
184 break;
185 default:
186 cs[csp++] = c;
187 f = ft == ITAL ? ITAL : ROM;
188 break;
189 }
190 return (f);
191 }
192
193 void
shim(void)194 shim(void)
195 {
196 cs[csp++] = '\\'; cs[csp++] = '|';
197 }
198
199 void
roman(int c)200 roman(int c)
201 {
202 cs[csp++] = '\\'; cs[csp++] = 'f'; cs[csp++] = ROM;
203 cs[csp++] = c;
204 cs[csp++] = '\\'; cs[csp++] = 'f'; cs[csp++] = 'P';
205 }
206
207 void
name4(int c1,int c2)208 name4(int c1, int c2)
209 {
210 cs[csp++] = '\\';
211 cs[csp++] = '(';
212 cs[csp++] = c1;
213 cs[csp++] = c2;
214 }
215