1 /*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21 /*
22 * Copyright (c) 2014 Gary Mills
23 *
24 * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
25 * Use is subject to license terms.
26 */
27
28 /* Copyright (c) 1988 AT&T */
29 /* All Rights Reserved */
30
31 /* Copyright 1976, Bell Telephone Laboratories, Inc. */
32
33 #include <string.h>
34 #include "once.h"
35 #include "sgs.h"
36 #include <locale.h>
37 #include <limits.h>
38
39 static wchar_t L_INITIAL[] = {'I', 'N', 'I', 'T', 'I', 'A', 'L', 0};
40 static void get1core(void);
41 static void free1core(void);
42 static void get2core(void);
43 static void free2core(void);
44 static void get3core(void);
45 #ifdef DEBUG
46 static void free3core(void);
47 #endif
48
49 int
main(int argc,char ** argv)50 main(int argc, char **argv)
51 {
52 int i;
53 int c;
54 char *apath = NULL;
55 char *ypath;
56 Boolean eoption = 0, woption = 0;
57
58 sargv = argv;
59 sargc = argc;
60 (void) setlocale(LC_ALL, "");
61 #ifdef DEBUG
62 while ((c = getopt(argc, argv, "dyctvnewVQ:Y:")) != EOF) {
63 #else
64 while ((c = getopt(argc, argv, "ctvnewVQ:Y:")) != EOF) {
65 #endif
66 switch (c) {
67 #ifdef DEBUG
68 case 'd':
69 debug++;
70 break;
71 case 'y':
72 yydebug = TRUE;
73 break;
74 #endif
75 case 'V':
76 (void) fprintf(stderr, "lex: %s %s\n",
77 (const char *)SGU_PKG,
78 (const char *)SGU_REL);
79 break;
80 case 'Q':
81 v_stmp = optarg;
82 if (*v_stmp != 'y' && *v_stmp != 'n')
83 error(
84 "lex: -Q should be followed by [y/n]");
85 break;
86 case 'Y':
87 apath = (char *)malloc(strlen(optarg) +
88 sizeof ("/nceucform") + 1);
89 if (apath == NULL)
90 error("No available memory "
91 "for directory name.");
92 else
93 apath = strcpy(apath, optarg);
94 break;
95 case 'c':
96 ratfor = FALSE;
97 break;
98 case 't':
99 fout = stdout;
100 break;
101 case 'v':
102 report = 1;
103 break;
104 case 'n':
105 report = 0;
106 break;
107 case 'w':
108 case 'W':
109 woption = 1;
110 handleeuc = 1;
111 widecio = 1;
112 break;
113 case 'e':
114 case 'E':
115 eoption = 1;
116 handleeuc = 1;
117 widecio = 0;
118 break;
119 default:
120 (void) fprintf(stderr,
121 "Usage: lex [-ewctvnV] [-Y directory] "
122 "[-Q(y/n)] [file]\n");
123 exit(1);
124 }
125 }
126 if (woption && eoption) {
127 error(
128 "You may not specify both -w and -e simultaneously.");
129 }
130 no_input = argc - optind;
131 if (no_input) {
132 /* XCU4: recognize "-" file operand for stdin */
133 if (strcmp(argv[optind], "-") == 0)
134 fin = stdin;
135 else {
136 fin = fopen(argv[optind], "r");
137 if (fin == NULL)
138 error(
139 "Can't open input file -- %s", argv[optind]);
140 }
141 } else
142 fin = stdin;
143
144 /* may be gotten: def, subs, sname, schar, ccl, dchar */
145 (void) gch();
146
147 /* may be gotten: name, left, right, nullstr, parent */
148 get1core();
149
150 scopy(L_INITIAL, sp);
151 sname[0] = sp;
152 sp += slength(L_INITIAL) + 1;
153 sname[1] = 0;
154
155 /* XCU4: %x exclusive start */
156 exclusive[0] = 0;
157
158 if (!handleeuc) {
159 /*
160 * Set ZCH and ncg to their default values
161 * as they may be needed to handle %t directive.
162 */
163 ZCH = ncg = NCH; /* ncg behaves as constant in this mode. */
164 }
165
166 /* may be disposed of: def, subs, dchar */
167 if (yyparse())
168 exit(1); /* error return code */
169
170 if (handleeuc) {
171 ncg = ncgidtbl * 2;
172 ZCH = ncg;
173 if (ncg >= MAXNCG)
174 error(
175 "Too complex rules -- requires too many char groups.");
176 sortcgidtbl();
177 }
178 repbycgid(); /* Call this even in ASCII compat. mode. */
179
180 /*
181 * maybe get:
182 * tmpstat, foll, positions, gotof, nexts,
183 * nchar, state, atable, sfall, cpackflg
184 */
185 free1core();
186 get2core();
187 ptail();
188 mkmatch();
189 #ifdef DEBUG
190 if (debug)
191 pccl();
192 #endif
193 sect = ENDSECTION;
194 if (tptr > 0)
195 cfoll(tptr-1);
196 #ifdef DEBUG
197 if (debug)
198 pfoll();
199 #endif
200 cgoto();
201 #ifdef DEBUG
202 if (debug) {
203 (void) printf("Print %d states:\n", stnum + 1);
204 for (i = 0; i <= stnum; i++)
205 stprt(i);
206 }
207 #endif
208 /*
209 * may be disposed of:
210 * positions, tmpstat, foll, state, name,
211 * left, right, parent, ccl, schar, sname
212 * maybe get: verify, advance, stoff
213 */
214 free2core();
215 get3core();
216 layout();
217 /*
218 * may be disposed of:
219 * verify, advance, stoff, nexts, nchar,
220 * gotof, atable, ccpackflg, sfall
221 */
222
223 #ifdef DEBUG
224 free3core();
225 #endif
226
227 if (handleeuc) {
228 if (ratfor)
229 error("Ratfor is not supported by -w or -e option.");
230 ypath = EUCNAME;
231 }
232 else
233 ypath = ratfor ? RATNAME : CNAME;
234
235 if (apath != NULL)
236 ypath = strcat(apath, strrchr(ypath, '/'));
237 fother = fopen(ypath, "r");
238 if (fother == NULL)
239 error("Lex driver missing, file %s", ypath);
240 while ((i = getc(fother)) != EOF)
241 (void) putc((char)i, fout);
242 (void) fclose(fother);
243 (void) fclose(fout);
244 free(apath);
245 if (report == 1)
246 statistics();
247 (void) fclose(stdout);
248 (void) fclose(stderr);
249 return (0); /* success return code */
250 }
251
252 static void
253 get1core(void)
254 {
255 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
256 ccptr = ccl = (CHR *)myalloc(CCLSIZE, sizeof (*ccl));
257 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
258 pcptr = pchar = (CHR *)myalloc(pchlen, sizeof (*pchar));
259 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
260 def = (CHR **)myalloc(DEFSIZE, sizeof (*def));
261 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
262 subs = (CHR **)myalloc(DEFSIZE, sizeof (*subs));
263 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
264 dp = dchar = (CHR *)myalloc(DEFCHAR, sizeof (*dchar));
265 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
266 sname = (CHR **)myalloc(STARTSIZE, sizeof (*sname));
267 /* XCU4: exclusive start array */
268 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
269 exclusive = (int *)myalloc(STARTSIZE, sizeof (*exclusive));
270 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
271 sp = schar = (CHR *)myalloc(STARTCHAR, sizeof (*schar));
272 if (ccl == 0 || def == 0 ||
273 pchar == 0 || subs == 0 || dchar == 0 ||
274 sname == 0 || exclusive == 0 || schar == 0)
275 error("Too little core to begin");
276 }
277
278 static void
279 free1core(void)
280 {
281 free(def);
282 free(subs);
283 free(dchar);
284 }
285
286 static void
287 get2core(void)
288 {
289 int i;
290 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
291 gotof = (int *)myalloc(nstates, sizeof (*gotof));
292 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
293 nexts = (int *)myalloc(ntrans, sizeof (*nexts));
294 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
295 nchar = (CHR *)myalloc(ntrans, sizeof (*nchar));
296 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
297 state = (int **)myalloc(nstates, sizeof (*state));
298 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
299 atable = (int *)myalloc(nstates, sizeof (*atable));
300 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
301 sfall = (int *)myalloc(nstates, sizeof (*sfall));
302 cpackflg = (Boolean *)myalloc(nstates, sizeof (*cpackflg));
303 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
304 tmpstat = (CHR *)myalloc(tptr+1, sizeof (*tmpstat));
305 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
306 foll = (int **)myalloc(tptr+1, sizeof (*foll));
307 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
308 nxtpos = positions = (int *)myalloc(maxpos, sizeof (*positions));
309 if (tmpstat == 0 || foll == 0 || positions == 0 ||
310 gotof == 0 || nexts == 0 || nchar == 0 ||
311 state == 0 || atable == 0 || sfall == 0 || cpackflg == 0)
312 error("Too little core for state generation");
313 for (i = 0; i <= tptr; i++)
314 foll[i] = 0;
315 }
316
317 static void
318 free2core(void)
319 {
320 free(positions);
321 free(tmpstat);
322 free(foll);
323 free(name);
324 free(left);
325 free(right);
326 free(parent);
327 free(nullstr);
328 free(state);
329 free(sname);
330 /* XCU4: exclusive start array */
331 free(exclusive);
332 free(schar);
333 free(ccl);
334 }
335
336 static void
337 get3core(void)
338 {
339 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
340 verify = (int *)myalloc(outsize, sizeof (*verify));
341 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
342 advance = (int *)myalloc(outsize, sizeof (*advance));
343 /*LINTED: E_BAD_PTR_CAST_ALIGN*/
344 stoff = (int *)myalloc(stnum+2, sizeof (*stoff));
345 if (verify == 0 || advance == 0 || stoff == 0)
346 error("Too little core for final packing");
347 }
348
349 #ifdef DEBUG
350 static void
351 free3core(void)
352 {
353 free(advance);
354 free(verify);
355 free(stoff);
356 free(gotof);
357 free(nexts);
358 free(nchar);
359 free(atable);
360 free(sfall);
361 free(cpackflg);
362 }
363 #endif
364
365 BYTE *
366 myalloc(int a, int b)
367 {
368 BYTE *i;
369 i = calloc(a, b);
370 if (i == 0)
371 warning("calloc returns a 0");
372 return (i);
373 }
374
375 void
376 yyerror(char *s)
377 {
378 (void) fprintf(stderr,
379 "\"%s\":line %d: Error: %s\n", sargv[optind], yyline, s);
380 }
381