]>
Commit | Line | Data |
---|---|---|
878ddf1f | 1 | /*\r |
2 | * lex.c -- Generate all of the lexical type files: parser.dlg tokens.h\r | |
3 | *\r | |
4 | * SOFTWARE RIGHTS\r | |
5 | *\r | |
6 | * We reserve no LEGAL rights to the Purdue Compiler Construction Tool\r | |
7 | * Set (PCCTS) -- PCCTS is in the public domain. An individual or\r | |
8 | * company may do whatever they wish with source code distributed with\r | |
9 | * PCCTS or the code generated by PCCTS, including the incorporation of\r | |
10 | * PCCTS, or its output, into commerical software.\r | |
11 | *\r | |
12 | * We encourage users to develop software with PCCTS. However, we do ask\r | |
13 | * that credit is given to us for developing PCCTS. By "credit",\r | |
14 | * we mean that if you incorporate our source code into one of your\r | |
15 | * programs (commercial product, research project, or otherwise) that you\r | |
16 | * acknowledge this fact somewhere in the documentation, research report,\r | |
17 | * etc... If you like PCCTS and have developed a nice tool with the\r | |
18 | * output, please mention that you developed it using PCCTS. In\r | |
19 | * addition, we ask that this header remain intact in our source code.\r | |
20 | * As long as these guidelines are kept, we expect to continue enhancing\r | |
21 | * this system and expect to make other tools available as they are\r | |
22 | * completed.\r | |
23 | *\r | |
24 | * ANTLR 1.33\r | |
25 | * Terence Parr\r | |
26 | * Parr Research Corporation\r | |
27 | * with Purdue University and AHPCRC, University of Minnesota\r | |
28 | * 1989-2001\r | |
29 | */\r | |
30 | \r | |
31 | #include <stdio.h>\r | |
32 | #include <ctype.h>\r | |
33 | /* MR1 */\r | |
34 | /* MR1 10-Apr-97 MR1 Replace use of __STDC__ with __USE_PROTOS */\r | |
35 | /* MR1 */\r | |
36 | #include "pcctscfg.h"\r | |
37 | #include "set.h"\r | |
38 | #include "syn.h"\r | |
39 | #include "hash.h"\r | |
40 | #include "generic.h"\r | |
41 | \r | |
42 | #define DLGErrorString "invalid token"\r | |
43 | \r | |
44 | /* Generate a complete lexical description of the lexemes found in the grammar */\r | |
45 | void\r | |
46 | #ifdef __USE_PROTOS\r | |
47 | genLexDescr( void )\r | |
48 | #else\r | |
49 | genLexDescr( )\r | |
50 | #endif\r | |
51 | {\r | |
52 | ListNode *p;\r | |
53 | FILE *dlgFile = fopen(OutMetaName(DlgFileName), "w");\r | |
54 | require(dlgFile!=NULL, eMsg1("genLexFile: cannot open %s", OutMetaName(DlgFileName)) );\r | |
55 | #ifdef SPECIAL_FOPEN\r | |
56 | special_fopen_actions(OutMetaName(DlgFileName)); /* MR1 */\r | |
57 | #endif\r | |
58 | fprintf(dlgFile, "<<\n");\r | |
59 | fprintf(dlgFile, "/* %s -- DLG Description of scanner\n", DlgFileName);\r | |
60 | fprintf(dlgFile, " *\n");\r | |
61 | fprintf(dlgFile, " * Generated from:");\r | |
62 | {int i; for (i=0; i<NumFiles; i++) fprintf(dlgFile, " %s", FileStr[i]);}\r | |
63 | fprintf(dlgFile, "\n");\r | |
64 | fprintf(dlgFile, " *\n");\r | |
65 | fprintf(dlgFile, " * Terence Parr, Will Cohen, and Hank Dietz: 1989-2001\n");\r | |
66 | fprintf(dlgFile, " * Purdue University Electrical Engineering\n");\r | |
67 | fprintf(dlgFile, " * With AHPCRC, University of Minnesota\n");\r | |
68 | fprintf(dlgFile, " * ANTLR Version %s\n", Version);\r | |
69 | fprintf(dlgFile, " */\n\n");\r | |
70 | if (FirstAction != NULL ) dumpAction( FirstAction, dlgFile, 0, -1, 0, 1 ); /* MR11 MR15b */\r | |
71 | fprintf(dlgFile, "#define ANTLR_VERSION %s\n", VersionDef);\r | |
72 | if ( GenCC )\r | |
73 | {\r | |
74 | if ( !UserDefdTokens ) fprintf(dlgFile, "#include \"%s\"\n", DefFileName);\r | |
75 | else fprintf(dlgFile, "#include %s\n", UserTokenDefsFile);\r | |
76 | fprintf(dlgFile, "#include \"%s\"\n", ATOKEN_H);\r | |
77 | if ( GenAST ) fprintf(dlgFile, "#include \"%s\"\n", ASTBASE_H);\r | |
78 | if ( HdrAction != NULL ) dumpAction( HdrAction, dlgFile, 0, -1, 0, 1 );\r | |
79 | }\r | |
80 | else\r | |
81 | {\r | |
82 | fprintf(dlgFile, "#include \"pcctscfg.h\"\n");\r | |
83 | fprintf(dlgFile, "#include \"pccts_stdio.h\"\n");\r | |
84 | if ( strcmp(ParserName, DefaultParserName)!=0 )\r | |
85 | fprintf(dlgFile, "#define %s %s\n", DefaultParserName, ParserName);\r | |
86 | if ( strcmp(ParserName, DefaultParserName)!=0 )\r | |
87 | fprintf(dlgFile, "#include \"%s\"\n", RemapFileName);\r | |
88 | if ( HdrAction != NULL ) dumpAction( HdrAction, dlgFile, 0, -1, 0, 1 );\r | |
89 | if ( FoundGuessBlk )\r | |
90 | {\r | |
91 | fprintf(dlgFile, "#define ZZCAN_GUESS\n");\r | |
92 | fprintf(dlgFile, "#include \"pccts_setjmp.h\"\n");\r | |
93 | }\r | |
94 | if ( OutputLL_k > 1 ) fprintf(dlgFile, "#define LL_K %d\n", OutputLL_k);\r | |
95 | if ( DemandLookahead ) fprintf(dlgFile, "#define DEMAND_LOOK\n");\r | |
96 | if (TraceGen) {\r | |
97 | fprintf(dlgFile,"#ifndef zzTRACE_RULES\n"); /* MR20 */\r | |
98 | fprintf(dlgFile,"#define zzTRACE_RULES\n"); /* MR20 */\r | |
99 | fprintf(dlgFile,"#endif\n"); /* MR22 */\r | |
100 | };\r | |
101 | fprintf(dlgFile, "#include \"antlr.h\"\n");\r | |
102 | if ( GenAST ) {\r | |
103 | fprintf(dlgFile, "#include \"ast.h\"\n");\r | |
104 | }\r | |
105 | if ( UserDefdTokens )\r | |
106 | fprintf(dlgFile, "#include %s\n", UserTokenDefsFile);\r | |
107 | /* still need this one as it has the func prototypes */\r | |
108 | fprintf(dlgFile, "#include \"%s\"\n", DefFileName);\r | |
109 | fprintf(dlgFile, "#include \"dlgdef.h\"\n");\r | |
110 | fprintf(dlgFile, "LOOKAHEAD\n");\r | |
111 | fprintf(dlgFile, "\n");\r | |
112 | fprintf(dlgFile, "void\n");\r | |
113 | fprintf(dlgFile, "#ifdef __USE_PROTOS\n");\r | |
114 | fprintf(dlgFile, "zzerraction(void)\n");\r | |
115 | fprintf(dlgFile, "#else\n");\r | |
116 | fprintf(dlgFile, "zzerraction()\n");\r | |
117 | fprintf(dlgFile, "#endif\n");\r | |
118 | fprintf(dlgFile, "{\n");\r | |
119 | fprintf(dlgFile, "\t(*zzerr)(\"%s\");\n", DLGErrorString);\r | |
120 | fprintf(dlgFile, "\tzzadvance();\n");\r | |
121 | fprintf(dlgFile, "\tzzskip();\n");\r | |
122 | fprintf(dlgFile, "}\n");\r | |
123 | }\r | |
124 | fprintf(dlgFile, ">>\n\n");\r | |
125 | \r | |
126 | /* dump all actions */\r | |
127 | \r | |
128 | /* MR1 */\r | |
129 | /* MR1 11-Apr-97 Provide mechanism for inserting code into DLG class */\r | |
130 | /* MR1 via <<%%lexmember ....>> & <<%%lexprefix ...>> */\r | |
131 | /* MR1 */\r | |
132 | if (LexActions != NULL) {\r | |
133 | for (p = LexActions->next; p!=NULL; p=p->next)\r | |
134 | {\r | |
135 | /* MR1 */ fprintf(dlgFile, "<<%%%%lexaction\n");\r | |
136 | dumpAction( (char *)p->elem, dlgFile, 0, -1, 0, 1 );\r | |
137 | fprintf(dlgFile, ">>\n\n");\r | |
138 | }\r | |
139 | };\r | |
140 | \r | |
141 | /* MR1 */ if (GenCC) {\r | |
142 | /* MR1 */ fprintf(dlgFile,"<<%%%%parserclass %s>>\n\n",CurrentClassName);\r | |
143 | /* MR1 */ };\r | |
144 | \r | |
145 | /* MR1 */ if (LexPrefixActions != NULL) {\r | |
146 | /* MR1 */ for (p = LexPrefixActions->next; p!=NULL; p=p->next)\r | |
147 | /* MR1 */ {\r | |
148 | /* MR1 */ fprintf(dlgFile, "<<%%%%lexprefix\n");\r | |
149 | /* MR1 */ dumpAction( (char *)p->elem, dlgFile, 0, -1, 0, 1 );\r | |
150 | /* MR1 */ fprintf(dlgFile, ">>\n\n");\r | |
151 | /* MR1 */ }\r | |
152 | /* MR1 */ };\r | |
153 | \r | |
154 | /* MR1 */ if (LexMemberActions != NULL) {\r | |
155 | /* MR1 */ for (p = LexMemberActions->next; p!=NULL; p=p->next)\r | |
156 | /* MR1 */ {\r | |
157 | /* MR1 */ fprintf(dlgFile, "<<%%%%lexmember\n");\r | |
158 | /* MR1 */ dumpAction( (char *)p->elem, dlgFile, 0, -1, 0, 1 );\r | |
159 | /* MR1 */ fprintf(dlgFile, ">>\n\n");\r | |
160 | /* MR1 */ }\r | |
161 | /* MR1 */ };\r | |
162 | \r | |
163 | /* dump all regular expression rules/actions (skip sentinel node) */\r | |
164 | if ( ExprOrder == NULL ) {\r | |
165 | warnNoFL("no regular expressions found in grammar");\r | |
166 | }\r | |
167 | else dumpLexClasses(dlgFile);\r | |
168 | fprintf(dlgFile, "%%%%\n");\r | |
169 | fclose( dlgFile );\r | |
170 | }\r | |
171 | \r | |
172 | /* For each lexical class, scan ExprOrder looking for expressions\r | |
173 | * in that lexical class. Print out only those that match.\r | |
174 | * Each element of the ExprOrder list has both an expr and an lclass\r | |
175 | * field.\r | |
176 | */\r | |
177 | void\r | |
178 | #ifdef __USE_PROTOS\r | |
179 | dumpLexClasses( FILE *dlgFile )\r | |
180 | #else\r | |
181 | dumpLexClasses( dlgFile )\r | |
182 | FILE *dlgFile;\r | |
183 | #endif\r | |
184 | {\r | |
185 | int i;\r | |
186 | TermEntry *t;\r | |
187 | ListNode *p;\r | |
188 | Expr *q;\r | |
189 | \r | |
190 | for (i=0; i<NumLexClasses; i++)\r | |
191 | {\r | |
192 | fprintf(dlgFile, "\n%%%%%s\n\n", lclass[i].classnum);\r | |
193 | for (p=ExprOrder->next; p!=NULL; p=p->next)\r | |
194 | {\r | |
195 | q = (Expr *) p->elem;\r | |
196 | if ( q->lclass != i ) continue;\r | |
197 | lexmode(i);\r | |
198 | t = (TermEntry *) hash_get(Texpr, q->expr);\r | |
199 | require(t!=NULL, eMsg1("genLexDescr: rexpr %s not in hash table",q->expr) );\r | |
200 | if ( t->token == EpToken ) continue;\r | |
201 | fprintf(dlgFile, "%s\n\t<<\n", StripQuotes(q->expr));\r | |
202 | /* replace " killed by StripQuotes() */\r | |
203 | q->expr[ strlen(q->expr) ] = '"';\r | |
204 | if ( !GenCC ) {\r | |
205 | if ( TokenString(t->token) != NULL )\r | |
206 | fprintf(dlgFile, "\t\tNLA = %s;\n", TokenString(t->token));\r | |
207 | else\r | |
208 | fprintf(dlgFile, "\t\tNLA = %d;\n", t->token);\r | |
209 | }\r | |
210 | if ( t->action != NULL ) dumpAction( t->action, dlgFile, 2,-1,0,1 );\r | |
211 | if ( GenCC ) {\r | |
212 | if ( TokenString(t->token) != NULL )\r | |
213 | fprintf(dlgFile, "\t\treturn %s;\n", TokenString(t->token));\r | |
214 | else\r | |
215 | fprintf(dlgFile, "\t\treturn (ANTLRTokenType)%d;\n", t->token);\r | |
216 | }\r | |
217 | fprintf(dlgFile, "\t>>\n\n");\r | |
218 | }\r | |
219 | }\r | |
220 | }\r | |
221 | \r | |
222 | /* Strip the leading path (if any) from a filename */\r | |
223 | char *\r | |
224 | #ifdef __USE_PROTOS\r | |
225 | StripPath( char *fileName )\r | |
226 | #else\r | |
227 | StripPath( fileName )\r | |
228 | char *fileName;\r | |
229 | #endif\r | |
230 | {\r | |
231 | char *p;\r | |
232 | static char dirSym[2] = DirectorySymbol;\r | |
233 | \r | |
234 | if(NULL != (p = strrchr(fileName, dirSym[0])))\r | |
235 | p++;\r | |
236 | else\r | |
237 | p = fileName;\r | |
238 | \r | |
239 | return(p);\r | |
240 | }\r | |
241 | \r | |
242 | /* Generate a list of #defines && list of struct definitions for\r | |
243 | * aggregate retv's */\r | |
244 | void\r | |
245 | #ifdef __USE_PROTOS\r | |
246 | genDefFile( void )\r | |
247 | #else\r | |
248 | genDefFile( )\r | |
249 | #endif\r | |
250 | {\r | |
251 | int i;\r | |
252 | \r | |
253 | /* If C++ mode and #tokdef used, then don't need anything in here since\r | |
254 | * C++ puts all definitions in the class file name.\r | |
255 | */\r | |
256 | if ( GenCC && UserTokenDefsFile ) return;\r | |
257 | if ( MR_Inhibit_Tokens_h_Gen) return;\r | |
258 | \r | |
259 | DefFile = fopen(OutMetaName(DefFileName), "w");\r | |
260 | require(DefFile!=NULL, eMsg1("genDefFile: cannot open %s", OutMetaName(DefFileName)) );\r | |
261 | #ifdef SPECIAL_FOPEN\r | |
262 | special_fopen_actions(OutMetaName(DefFileName)); /* MR1 */\r | |
263 | #endif\r | |
264 | fprintf(DefFile, "#ifndef %s\n", StripPath(gate_symbol(DefFileName)));\r | |
265 | fprintf(DefFile, "#define %s\n", StripPath(gate_symbol(DefFileName)));\r | |
266 | \r | |
267 | fprintf(DefFile, "/* %s -- List of labelled tokens and stuff\n", DefFileName);\r | |
268 | fprintf(DefFile, " *\n");\r | |
269 | fprintf(DefFile, " * Generated from:");\r | |
270 | for (i=0; i<NumFiles; i++) fprintf(DefFile, " %s", FileStr[i]);\r | |
271 | fprintf(DefFile, "\n");\r | |
272 | fprintf(DefFile, " *\n");\r | |
273 | fprintf(DefFile, " * Terence Parr, Will Cohen, and Hank Dietz: 1989-2001\n");\r | |
274 | fprintf(DefFile, " * Purdue University Electrical Engineering\n");\r | |
275 | fprintf(DefFile, " * ANTLR Version %s\n", Version);\r | |
276 | fprintf(DefFile, " */\n");\r | |
277 | \r | |
278 | if ( !GenCC && LexGen ) {\r | |
279 | fprintf(DefFile,"#define zzEOF_TOKEN %d\n",\r | |
280 | TokenInd!=NULL?TokenInd[EofToken]:EofToken);\r | |
281 | }\r | |
282 | \r | |
283 | if ( !UserDefdTokens )\r | |
284 | {\r | |
285 | int first=1;\r | |
286 | \r | |
287 | if ( GenCC ) fprintf(DefFile, "enum ANTLRTokenType {\n");\r | |
288 | for (i=1; i<TokenNum; i++)\r | |
289 | {\r | |
290 | /* Don't do EpToken or expr w/o labels */\r | |
291 | if ( TokenString(i)!=NULL && i != EpToken )\r | |
292 | {\r | |
293 | TermEntry *p;\r | |
294 | \r | |
295 | if ( WarningLevel>1 )\r | |
296 | {\r | |
297 | int j;\r | |
298 | /* look in all lexclasses for the reg expr */\r | |
299 | \r | |
300 | /* MR10 Derek Pappas */\r | |
301 | /* MR10 A #tokclass doesn't have associated regular expressiones */\r | |
302 | /* MR10 so don't warn user about it's omission */\r | |
303 | \r | |
304 | p = (TermEntry *) hash_get(Tname, TokenString(i));\r | |
305 | \r | |
306 | if (p != NULL && ! p->classname) {\r | |
307 | for (j=0; j<NumLexClasses; j++)\r | |
308 | {\r | |
309 | lexmode(j);\r | |
310 | if ( ExprString(i)!=NULL ) break;\r | |
311 | }\r | |
312 | if ( j>=NumLexClasses )\r | |
313 | {\r | |
314 | warnNoFL(eMsg1("token label has no associated rexpr: %s",TokenString(i)));\r | |
315 | }\r | |
316 | };\r | |
317 | }\r | |
318 | require((p=(TermEntry *)hash_get(Tname, TokenString(i))) != NULL,\r | |
319 | "token not in sym tab when it should be");\r | |
320 | if ( !p->classname )\r | |
321 | {\r | |
322 | if ( GenCC ) {\r | |
323 | if ( !first ) fprintf(DefFile, ",\n");\r | |
324 | first = 0;\r | |
325 | fprintf(DefFile, "\t%s=%d", TokenString(i), i);\r | |
326 | }\r | |
327 | else\r | |
328 | fprintf(DefFile, "#define %s %d\n", TokenString(i), i);\r | |
329 | }\r | |
330 | }\r | |
331 | }\r | |
332 | /* MR1 */\r | |
333 | /* MR1 10-Apr-97 133MR1 Prevent use of varying sizes of integer */\r | |
334 | /* MR1 for the enum ANTLRTokenType */\r | |
335 | /* MR1 */\r | |
336 | if ( GenCC ) { /* MR1 */\r | |
337 | if ( !first ) fprintf(DefFile, ",\n"); /* MR14 */\r | |
338 | fprintf(DefFile, "\tDLGminToken=0"); /* MR1 */\r | |
339 | fprintf(DefFile, ",\n\tDLGmaxToken=9999};\n"); /* MR1 */\r | |
340 | }; /* MR1 */\r | |
341 | }\r | |
342 | \r | |
343 | if ( !GenCC ) GenRulePrototypes(DefFile, SynDiag);\r | |
344 | \r | |
345 | fprintf(DefFile, "\n#endif\n");\r | |
346 | }\r | |
347 | \r | |
348 | void\r | |
349 | #ifdef __USE_PROTOS\r | |
350 | GenRemapFile( void )\r | |
351 | #else\r | |
352 | GenRemapFile( )\r | |
353 | #endif\r | |
354 | {\r | |
355 | if ( strcmp(ParserName, DefaultParserName)!=0 )\r | |
356 | {\r | |
357 | FILE *f;\r | |
358 | int i;\r | |
359 | \r | |
360 | f = fopen(OutMetaName(RemapFileName), "w");\r | |
361 | require(f!=NULL, eMsg1("GenRemapFile: cannot open %s", OutMetaName(RemapFileName)) );\r | |
362 | #ifdef SPECIAL_FOPEN\r | |
363 | special_fopen_actions(OutMetaName(RemapFileName)); /* MR1 */\r | |
364 | #endif\r | |
365 | fprintf(f, "/* %s -- List of symbols to remap\n", RemapFileName);\r | |
366 | fprintf(f, " *\n");\r | |
367 | fprintf(f, " * Generated from:");\r | |
368 | for (i=0; i<NumFiles; i++) fprintf(f, " %s", FileStr[i]);\r | |
369 | fprintf(f, "\n");\r | |
370 | fprintf(f, " *\n");\r | |
371 | fprintf(f, " * Terence Parr, Will Cohen, and Hank Dietz: 1989-2001\n");\r | |
372 | fprintf(f, " * Purdue University Electrical Engineering\n");\r | |
373 | fprintf(f, " * ANTLR Version %s\n", Version);\r | |
374 | fprintf(f, " */\n");\r | |
375 | \r | |
376 | GenRuleFuncRedefs(f, SynDiag);\r | |
377 | GenPredefinedSymbolRedefs(f);\r | |
378 | if ( GenAST ) GenASTSymbolRedefs(f);\r | |
379 | GenSetRedefs(f);\r | |
380 | \r | |
381 | fclose(f);\r | |
382 | }\r | |
383 | }\r | |
384 | \r | |
385 | /* Generate a bunch of #defines that rename all functions to be "ParserName_func" */\r | |
386 | void\r | |
387 | #ifdef __USE_PROTOS\r | |
388 | GenRuleFuncRedefs( FILE *f, Junction *p )\r | |
389 | #else\r | |
390 | GenRuleFuncRedefs( f, p )\r | |
391 | FILE *f;\r | |
392 | Junction *p;\r | |
393 | #endif\r | |
394 | {\r | |
395 | fprintf(f, "\n/* rename rule functions to be 'ParserName_func' */\n");\r | |
396 | while ( p!=NULL )\r | |
397 | {\r | |
398 | fprintf(f, "#define %s %s_%s\n", p->rname, ParserName, p->rname);\r | |
399 | p = (Junction *)p->p2;\r | |
400 | }\r | |
401 | }\r | |
402 | \r | |
403 | /* Generate a bunch of #defines that rename all standard symbols to be\r | |
404 | * "ParserName_symbol". The list of standard symbols to change is in\r | |
405 | * globals.c.\r | |
406 | */\r | |
407 | void\r | |
408 | #ifdef __USE_PROTOS\r | |
409 | GenPredefinedSymbolRedefs( FILE *f )\r | |
410 | #else\r | |
411 | GenPredefinedSymbolRedefs( f )\r | |
412 | FILE *f;\r | |
413 | #endif\r | |
414 | {\r | |
415 | char **p;\r | |
416 | \r | |
417 | fprintf(f, "\n/* rename PCCTS-supplied symbols to be 'ParserName_symbol' */\n");\r | |
418 | for (p = &StandardSymbols[0]; *p!=NULL; p++)\r | |
419 | {\r | |
420 | fprintf(f, "#define %s %s_%s\n", *p, ParserName, *p);\r | |
421 | }\r | |
422 | }\r | |
423 | \r | |
424 | /* Generate a bunch of #defines that rename all AST symbols to be\r | |
425 | * "ParserName_symbol". The list of AST symbols to change is in\r | |
426 | * globals.c.\r | |
427 | */\r | |
428 | void\r | |
429 | #ifdef __USE_PROTOS\r | |
430 | GenASTSymbolRedefs( FILE *f )\r | |
431 | #else\r | |
432 | GenASTSymbolRedefs( f )\r | |
433 | FILE *f;\r | |
434 | #endif\r | |
435 | {\r | |
436 | char **p;\r | |
437 | \r | |
438 | fprintf(f, "\n/* rename PCCTS-supplied AST symbols to be 'ParserName_symbol' */\n");\r | |
439 | for (p = &ASTSymbols[0]; *p!=NULL; p++)\r | |
440 | {\r | |
441 | fprintf(f, "#define %s %s_%s\n", *p, ParserName, *p);\r | |
442 | }\r | |
443 | }\r | |
444 | \r | |
445 | /* redefine all sets generated by ANTLR; WARNING: 'zzerr', 'setwd' must match\r | |
446 | * use in bits.c (DumpSetWd() etc...)\r | |
447 | */\r | |
448 | void\r | |
449 | #ifdef __USE_PROTOS\r | |
450 | GenSetRedefs( FILE *f )\r | |
451 | #else\r | |
452 | GenSetRedefs( f )\r | |
453 | FILE *f;\r | |
454 | #endif\r | |
455 | {\r | |
456 | int i;\r | |
457 | \r | |
458 | for (i=1; i<=wordnum; i++)\r | |
459 | {\r | |
460 | fprintf(f, "#define setwd%d %s_setwd%d\n", i, ParserName, i);\r | |
461 | }\r | |
462 | for (i=1; i<=esetnum; i++)\r | |
463 | {\r | |
464 | fprintf(f, "#define zzerr%d %s_err%d\n", i, ParserName, i);\r | |
465 | }\r | |
466 | }\r | |
467 | \r | |
468 | /* Find all return types/parameters that require structs and def\r | |
469 | * all rules with ret types.\r | |
470 | *\r | |
471 | * This is for the declaration, not the definition.\r | |
472 | */\r | |
473 | void\r | |
474 | #ifdef __USE_PROTOS\r | |
475 | GenRulePrototypes( FILE *f, Junction *p )\r | |
476 | #else\r | |
477 | GenRulePrototypes( f, p )\r | |
478 | FILE *f;\r | |
479 | Junction *p;\r | |
480 | #endif\r | |
481 | {\r | |
482 | int i;\r | |
483 | \r | |
484 | i = 1;\r | |
485 | while ( p!=NULL )\r | |
486 | {\r | |
487 | if ( p->ret != NULL )\r | |
488 | {\r | |
489 | /* MR23 */ if ( hasMultipleOperands(p->ret) )\r | |
490 | {\r | |
491 | DumpRetValStruct(f, p->ret, i);\r | |
492 | }\r | |
493 | fprintf(f, "\n#ifdef __USE_PROTOS\n");\r | |
494 | /* MR23 */ if ( hasMultipleOperands(p->ret) ) \r | |
495 | {\r | |
496 | fprintf(f, "extern struct _rv%d", i);\r | |
497 | }\r | |
498 | else\r | |
499 | {\r | |
500 | fprintf(f, "extern ");\r | |
501 | DumpType(p->ret, f);\r | |
502 | }\r | |
503 | fprintf(f, " %s%s(", RulePrefix, p->rname);\r | |
504 | DumpANSIFunctionArgDef(f,p,1 /* emit initializers ? */);\r | |
505 | fprintf(f, ";\n");\r | |
506 | fprintf(f, "#else\n");\r | |
507 | /* MR23 */ if ( hasMultipleOperands(p->ret) )\r | |
508 | {\r | |
509 | fprintf(f, "extern struct _rv%d", i);\r | |
510 | }\r | |
511 | else\r | |
512 | {\r | |
513 | fprintf(f, "extern ");\r | |
514 | DumpType(p->ret, f);\r | |
515 | }\r | |
516 | fprintf(f, " %s%s();\n", RulePrefix, p->rname);\r | |
517 | fprintf(f, "#endif\n");\r | |
518 | }\r | |
519 | else\r | |
520 | {\r | |
521 | fprintf(f, "\n#ifdef __USE_PROTOS\n");\r | |
522 | fprintf(f, "void %s%s(", RulePrefix, p->rname);\r | |
523 | DumpANSIFunctionArgDef(f,p, 1 /* emit initializers ? */ );\r | |
524 | fprintf(f, ";\n");\r | |
525 | #ifdef OLD\r | |
526 | if ( p->pdecl != NULL || GenAST )\r | |
527 | {\r | |
528 | if ( GenAST ) {\r | |
529 | fprintf(f, "AST **%s",(p->pdecl!=NULL)?",":"");\r | |
530 | }\r | |
531 | if ( p->pdecl!=NULL ) fprintf(f, "%s", p->pdecl);\r | |
532 | }\r | |
533 | else fprintf(f, "void");\r | |
534 | fprintf(f, ");\n");\r | |
535 | #endif\r | |
536 | fprintf(f, "#else\n");\r | |
537 | fprintf(f, "extern void %s%s();\n", RulePrefix, p->rname);\r | |
538 | fprintf(f, "#endif\n");\r | |
539 | }\r | |
540 | i++;\r | |
541 | p = (Junction *)p->p2;\r | |
542 | }\r | |
543 | }\r | |
544 | \r | |
545 | /* Define all rules in the class.h file; generate any required\r | |
546 | * struct definitions first, however.\r | |
547 | */\r | |
548 | void\r | |
549 | #ifdef __USE_PROTOS\r | |
550 | GenRuleMemberDeclarationsForCC( FILE *f, Junction *q )\r | |
551 | #else\r | |
552 | GenRuleMemberDeclarationsForCC( f, q )\r | |
553 | FILE *f;\r | |
554 | Junction *q;\r | |
555 | #endif\r | |
556 | {\r | |
557 | Junction *p = q;\r | |
558 | int i;\r | |
559 | \r | |
560 | fprintf(f, "private:\n");\r | |
561 | \r | |
562 | /* Dump dflt handler declaration */\r | |
563 | fprintf(f, "\tvoid zzdflthandlers( int _signal, int *_retsignal );\n\n");\r | |
564 | \r | |
565 | fprintf(f, "public:\n");\r | |
566 | \r | |
567 | /* Dump return value structs */\r | |
568 | i = 1;\r | |
569 | while ( p!=NULL )\r | |
570 | {\r | |
571 | if ( p->ret != NULL )\r | |
572 | {\r | |
573 | /* MR23 */ if ( hasMultipleOperands(p->ret) )\r | |
574 | {\r | |
575 | DumpRetValStruct(f, p->ret, i);\r | |
576 | }\r | |
577 | }\r | |
578 | i++;\r | |
579 | p = (Junction *)p->p2;\r | |
580 | }\r | |
581 | \r | |
582 | /* Dump member func defs && CONSTRUCTOR */\r | |
583 | fprintf(f, "\t%s(ANTLRTokenBuffer *input);\n", CurrentClassName);\r | |
584 | /*\r | |
585 | fprintf(f, "\t%s(ANTLRTokenBuffer *input, ANTLRTokenType eof);\n",\r | |
586 | CurrentClassName);\r | |
587 | */\r | |
588 | \r | |
589 | i = 1;\r | |
590 | p = q;\r | |
591 | while ( p!=NULL )\r | |
592 | {\r | |
593 | if ( p->ret != NULL )\r | |
594 | {\r | |
595 | /* MR23 */ if ( hasMultipleOperands(p->ret) )\r | |
596 | {\r | |
597 | fprintf(f, "\tstruct _rv%d", i);\r | |
598 | }\r | |
599 | else\r | |
600 | {\r | |
601 | fprintf(f, "\t");\r | |
602 | DumpType(p->ret, f);\r | |
603 | }\r | |
604 | fprintf(f, " %s%s(",RulePrefix,p->rname);\r | |
605 | DumpANSIFunctionArgDef(f,p, 1 /* emit initializers ? */ );\r | |
606 | fprintf(f, ";\n");\r | |
607 | #ifdef OLD\r | |
608 | if ( p->pdecl != NULL || GenAST )\r | |
609 | {\r | |
610 | if ( GenAST ) fprintf(f, "ASTBase **%s",(p->pdecl!=NULL)?",":"");\r | |
611 | if ( p->pdecl!=NULL ) fprintf(f, "%s", p->pdecl);\r | |
612 | }\r | |
613 | fprintf(f, ");\n");\r | |
614 | #endif\r | |
615 | }\r | |
616 | else\r | |
617 | {\r | |
618 | fprintf(f, "\tvoid %s%s(",RulePrefix,p->rname);\r | |
619 | DumpANSIFunctionArgDef(f,p, 1 /* emit initializers ? */);\r | |
620 | fprintf(f, ";\n");\r | |
621 | #ifdef OLD\r | |
622 | if ( p->pdecl != NULL || GenAST )\r | |
623 | {\r | |
624 | if ( GenAST ) fprintf(f, "ASTBase **%s",(p->pdecl!=NULL)?",":"");\r | |
625 | if ( p->pdecl!=NULL ) fprintf(f, "%s", p->pdecl);\r | |
626 | }\r | |
627 | fprintf(f, ");\n");\r | |
628 | #endif\r | |
629 | }\r | |
630 | i++;\r | |
631 | p = (Junction *)p->p2;\r | |
632 | }\r | |
633 | }\r | |
634 | \r | |
635 | /* Given a list of ANSI-style parameter declarations, print out a\r | |
636 | * comma-separated list of the symbols (w/o types).\r | |
637 | * Basically, we look for a comma, then work backwards until start of\r | |
638 | * the symbol name. Then print it out until 1st non-alnum char. Now,\r | |
639 | * move on to next parameter.\r | |
640 | *\r | |
641 | */\r | |
642 | \r | |
643 | /* MR5 Jan Mikkelsen 26-May-97 - added initalComma parameter */\r | |
644 | \r | |
645 | void\r | |
646 | #ifdef __USE_PROTOS\r | |
647 | DumpListOfParmNames(char *pdecl, FILE *output, int initialComma) /* MR5 */\r | |
648 | #else\r | |
649 | DumpListOfParmNames(pdecl, output, initialComma) /* MR5 */\r | |
650 | char *pdecl; /* MR5 */\r | |
651 | FILE *output; /* MR5 */\r | |
652 | int initialComma; /* MR5 */\r | |
653 | #endif\r | |
654 | {\r | |
655 | int firstTime = 1, done = 0;\r | |
656 | require(output!=NULL, "DumpListOfParmNames: NULL parm");\r | |
657 | \r | |
658 | if ( pdecl == NULL ) return;\r | |
659 | while ( !done )\r | |
660 | {\r | |
661 | if ( !firstTime || initialComma ) putc(',', output); /* MR5 */\r | |
662 | done = DumpNextNameInDef(&pdecl, output);\r | |
663 | firstTime = 0;\r | |
664 | }\r | |
665 | }\r | |
666 | \r | |
667 | /* given a list of parameters or return values, dump the next\r | |
668 | * name to output. Return 1 if last one just printed, 0 if more to go.\r | |
669 | */\r | |
670 | \r | |
671 | /* MR23 Total rewrite */\r | |
672 | \r | |
673 | int\r | |
674 | #ifdef __USE_PROTOS\r | |
675 | DumpNextNameInDef( char **q, FILE *output )\r | |
676 | #else\r | |
677 | DumpNextNameInDef( q, output )\r | |
678 | char **q;\r | |
679 | FILE *output;\r | |
680 | #endif\r | |
681 | {\r | |
682 | char *p;\r | |
683 | char *t;\r | |
684 | char *pDataType;\r | |
685 | char *pSymbol;\r | |
686 | char *pEqualSign;\r | |
687 | char *pValue;\r | |
688 | char *pSeparator;\r | |
689 | int nest = 0;\r | |
690 | \r | |
691 | p = endFormal(*q,\r | |
692 | &pDataType,\r | |
693 | &pSymbol,\r | |
694 | &pEqualSign,\r | |
695 | &pValue,\r | |
696 | &pSeparator,\r | |
697 | &nest);\r | |
698 | \r | |
699 | /* MR26 Handle rule arguments such as: IIR_Bool (IIR_Decl::*contstraint)()\r | |
700 | For this we need to strip off anything which follows the symbol.\r | |
701 | */\r | |
702 | \r | |
703 | /* MR26 */ t = pSymbol;\r | |
704 | /* MR26 */ if (t != NULL) {\r | |
705 | /* MR26 */ for (t = pSymbol; *t != 0; t++) {\r | |
706 | /* MR26 */ if (! (isalpha(*t) || isdigit(*t) || *t == '_' || *t == '$')) break;\r | |
707 | /* MR26 */ }\r | |
708 | /* MR26 */ }\r | |
709 | /* MR26 */ fprintf(output,strBetween(pSymbol, t, pSeparator));\r | |
710 | \r | |
711 | *q = p;\r | |
712 | return (*pSeparator == 0);\r | |
713 | }\r | |
714 | \r | |
715 | /* Given a list of ANSI-style parameter declarations, dump K&R-style\r | |
716 | * declarations, one per line for each parameter. Basically, convert\r | |
717 | * comma to semi-colon, newline.\r | |
718 | */\r | |
719 | void\r | |
720 | #ifdef __USE_PROTOS\r | |
721 | DumpOldStyleParms( char *pdecl, FILE *output )\r | |
722 | #else\r | |
723 | DumpOldStyleParms( pdecl, output )\r | |
724 | char *pdecl;\r | |
725 | FILE *output;\r | |
726 | #endif\r | |
727 | {\r | |
728 | require(output!=NULL, "DumpOldStyleParms: NULL parm");\r | |
729 | \r | |
730 | if ( pdecl == NULL ) return;\r | |
731 | while ( *pdecl != '\0' )\r | |
732 | {\r | |
733 | if ( *pdecl == ',' )\r | |
734 | {\r | |
735 | pdecl++;\r | |
736 | putc(';', output); putc('\n', output);\r | |
737 | while ( *pdecl==' ' || *pdecl=='\t' || *pdecl=='\n' ) pdecl++;\r | |
738 | }\r | |
739 | else {putc(*pdecl, output); pdecl++;}\r | |
740 | }\r | |
741 | putc(';', output);\r | |
742 | putc('\n', output);\r | |
743 | }\r | |
744 | \r | |
745 | /* Take in a type definition (type + symbol) and print out type only */\r | |
746 | /* MR23 Total rewrite */\r | |
747 | \r | |
748 | void\r | |
749 | #ifdef __USE_PROTOS\r | |
750 | DumpType( char *s, FILE *f )\r | |
751 | #else\r | |
752 | DumpType( s, f )\r | |
753 | char *s;\r | |
754 | FILE *f;\r | |
755 | #endif\r | |
756 | {\r | |
757 | char *p;\r | |
758 | char *pDataType;\r | |
759 | char *pSymbol;\r | |
760 | char *pEqualSign;\r | |
761 | char *pValue;\r | |
762 | char *pSeparator;\r | |
763 | int nest = 0;\r | |
764 | \r | |
765 | require(s!=NULL, "DumpType: invalid type string"); \r | |
766 | \r | |
767 | p = endFormal(s,\r | |
768 | &pDataType,\r | |
769 | &pSymbol,\r | |
770 | &pEqualSign,\r | |
771 | &pValue,\r | |
772 | &pSeparator,\r | |
773 | &nest);\r | |
774 | fprintf(f,strBetween(pDataType, pSymbol, pSeparator));\r | |
775 | }\r | |
776 | \r | |
777 | /* check to see if string e is a word in string s */\r | |
778 | int\r | |
779 | #ifdef __USE_PROTOS\r | |
780 | strmember( char *s, char *e )\r | |
781 | #else\r | |
782 | strmember( s, e )\r | |
783 | char *s;\r | |
784 | char *e;\r | |
785 | #endif\r | |
786 | {\r | |
787 | register char *p;\r | |
788 | require(s!=NULL&&e!=NULL, "strmember: NULL string");\r | |
789 | \r | |
790 | if ( *e=='\0' ) return 1; /* empty string is always member */\r | |
791 | do {\r | |
792 | while ( *s!='\0' && !isalnum(*s) && *s!='_' )\r | |
793 | ++s;\r | |
794 | p = e;\r | |
795 | while ( *p!='\0' && *p==*s ) {p++; s++;}\r | |
796 | if ( *p=='\0' ) {\r | |
797 | if ( *s=='\0' ) return 1;\r | |
798 | if ( !isalnum (*s) && *s != '_' ) return 1;\r | |
799 | }\r | |
800 | while ( isalnum(*s) || *s == '_' )\r | |
801 | ++s;\r | |
802 | } while ( *s!='\0' );\r | |
803 | return 0;\r | |
804 | }\r | |
805 | \r | |
806 | #if 0\r | |
807 | \r | |
808 | /* MR23 Replaced by hasMultipleOperands() */\r | |
809 | \r | |
810 | int\r | |
811 | #ifdef __USE_PROTOS\r | |
812 | HasComma( char *s )\r | |
813 | #else\r | |
814 | HasComma( s )\r | |
815 | char *s;\r | |
816 | #endif\r | |
817 | {\r | |
818 | while (*s!='\0')\r | |
819 | if ( *s++ == ',' ) return 1;\r | |
820 | return 0;\r | |
821 | }\r | |
822 | #endif\r | |
823 | \r | |
824 | \r | |
825 | /* MR23 Total rewrite */\r | |
826 | \r | |
827 | void\r | |
828 | #ifdef __USE_PROTOS\r | |
829 | DumpRetValStruct( FILE *f, char *ret, int i )\r | |
830 | #else\r | |
831 | DumpRetValStruct( f, ret, i )\r | |
832 | FILE *f;\r | |
833 | char *ret;\r | |
834 | int i;\r | |
835 | #endif\r | |
836 | {\r | |
837 | char *p = ret;\r | |
838 | char *pDataType;\r | |
839 | char *pSymbol;\r | |
840 | char *pEqualSign;\r | |
841 | char *pValue;\r | |
842 | char *pSeparator;\r | |
843 | int nest = 0;\r | |
844 | \r | |
845 | fprintf(f, "\nstruct _rv%d {\n", i);\r | |
846 | while (*p != 0 && nest == 0) {\r | |
847 | p = endFormal(p,\r | |
848 | &pDataType,\r | |
849 | &pSymbol,\r | |
850 | &pEqualSign,\r | |
851 | &pValue,\r | |
852 | &pSeparator,\r | |
853 | &nest);\r | |
854 | fprintf(f,"\t");\r | |
855 | fprintf(f,strBetween(pDataType, pSymbol, pSeparator));\r | |
856 | fprintf(f," ");\r | |
857 | fprintf(f,strBetween(pSymbol, pEqualSign, pSeparator));\r | |
858 | fprintf(f,";\n");\r | |
859 | }\r | |
860 | fprintf(f,"};\n");\r | |
861 | }\r | |
862 | \r | |
863 | /* given "s" yield s -- DESTRUCTIVE (we modify s if starts with " else return s) */\r | |
864 | char *\r | |
865 | #ifdef __USE_PROTOS\r | |
866 | StripQuotes( char *s )\r | |
867 | #else\r | |
868 | StripQuotes( s )\r | |
869 | char *s;\r | |
870 | #endif\r | |
871 | {\r | |
872 | if ( *s == '"' )\r | |
873 | {\r | |
874 | s[ strlen(s)-1 ] = '\0'; /* remove last quote */\r | |
875 | return( s+1 ); /* return address past initial quote */\r | |
876 | }\r | |
877 | return( s );\r | |
878 | }\r |