--- /dev/null
+/*\r
+ * antlr.g -- PCCTS Version 1.xx ANTLR\r
+ *\r
+ * Parse an antlr input grammar and build a syntax-diagram.\r
+ *\r
+ * Written in itself (needs at least 1.06 to work)\r
+ *\r
+ * SOFTWARE RIGHTS\r
+ *\r
+ * We reserve no LEGAL rights to the Purdue Compiler Construction Tool\r
+ * Set (PCCTS) -- PCCTS is in the public domain. An individual or\r
+ * company may do whatever they wish with source code distributed with\r
+ * PCCTS or the code generated by PCCTS, including the incorporation of\r
+ * PCCTS, or its output, into commerical software.\r
+ *\r
+ * We encourage users to develop software with PCCTS. However, we do ask\r
+ * that credit is given to us for developing PCCTS. By "credit",\r
+ * we mean that if you incorporate our source code into one of your\r
+ * programs (commercial product, research project, or otherwise) that you\r
+ * acknowledge this fact somewhere in the documentation, research report,\r
+ * etc... If you like PCCTS and have developed a nice tool with the\r
+ * output, please mention that you developed it using PCCTS. In\r
+ * addition, we ask that this header remain intact in our source code.\r
+ * As long as these guidelines are kept, we expect to continue enhancing\r
+ * this system and expect to make other tools available as they are\r
+ * completed.\r
+ *\r
+ * ANTLR 1.33\r
+ * Terence Parr\r
+ * Parr Research Corporation\r
+ * with Purdue University and AHPCRC, University of Minnesota\r
+ * 1989-1995\r
+ */\r
+\r
+/* MR1 */\r
+/* MR1 10-Apr-97 MR1 Replace #if logic with #include "pcctscfg.h" */\r
+/* MR1 */\r
+\r
+#header <<\r
+ #include "pcctscfg.h"\r
+ #include "set.h"\r
+ #include <ctype.h>\r
+ #include "syn.h"\r
+ #include "hash.h"\r
+ #include "generic.h"\r
+ #define zzcr_attr(attr,tok,t)\r
+ >>\r
+\r
+<<\r
+\r
+/* MR20 G. Hobbelt For Borland C++ 4.x & 5.x compiling with ALL warnings enabled */\r
+#if defined(__TURBOC__)\r
+#pragma warn -aus /* unused assignment of 'xxx' */\r
+#endif\r
+\r
+\r
+#ifdef __USE_PROTOS\r
+static void chkToken(char *, char *, char *, int);\r
+#else\r
+static void chkToken();\r
+#endif\r
+\r
+#ifdef __USE_PROTOS\r
+static int isDLGmaxToken(char *Token); /* MR3 */\r
+#else\r
+static int isDLGmaxToken(); /* MR3 */\r
+#endif\r
+\r
+static int class_nest_level = 0;\r
+\r
+/* MR20 G. Hobbelt extern definitions moved to antlr.h */\r
+\r
+>>\r
+\r
+#lexaction <<\r
+/* maintained, but not used for now */\r
+set AST_nodes_refd_in_actions = set_init;\r
+int inAlt = 0;\r
+set attribsRefdFromAction = set_init; /* MR20 */\r
+int UsedOldStyleAttrib = 0;\r
+int UsedNewStyleLabel = 0;\r
+#ifdef __USE_PROTOS\r
+char *inline_set(char *);\r
+#else\r
+char *inline_set();\r
+#endif\r
+\r
+/* MR1 10-Apr-97 MR1 Previously unable to put right shift operator */\r
+/* MR1 in DLG action */\r
+\r
+int tokenActionActive=0; /* MR1 */\r
+\r
+>>\r
+\r
+#lexclass STRINGS\r
+#token QuotedTerm "\"" << zzmode(START); >>\r
+#token "\n|\r|\r\n" <<\r
+ zzline++;\r
+ warn("eoln found in string");\r
+ zzskip();\r
+ >>\r
+#token "\\(\n|\r|\r\n)" << zzline++; zzmore(); >>\r
+#token "\\~[]" << zzmore(); >>\r
+#token "~[\n\r\"\\]+" << zzmore(); >>\r
+\r
+#lexclass ACTION_STRINGS\r
+#token "\"" << zzmode(ACTIONS); zzmore(); >>\r
+#token "\n|\r|\r\n" <<\r
+ zzline++;\r
+ warn("eoln found in string (in user action)");\r
+ zzskip();\r
+ >>\r
+#token "\\(\n|\r|\r\n)" << zzline++; zzmore(); >>\r
+#token "\\~[]" << zzmore(); >>\r
+#token "~[\n\r\"\\]+" << zzmore(); >>\r
+\r
+#lexclass ACTION_CHARS\r
+#token "'" << zzmode(ACTIONS); zzmore(); >>\r
+#token "\n|\r|\r\n" <<\r
+ zzline++;\r
+ warn("eoln found in char literal (in user action)");\r
+ zzskip();\r
+ >>\r
+#token "\\~[]" << zzmore(); >>\r
+#token "~[\n\r'\\]+" << zzmore(); >>\r
+\r
+#lexclass ACTION_COMMENTS\r
+#token "\*/" << zzmode(ACTIONS); zzmore(); >>\r
+#token "\*" << zzmore(); >>\r
+#token "\n|\r|\r\n" << zzline++; zzmore(); DAWDLE; >>\r
+#token "~[\n\r\*]+" << zzmore(); >>\r
+\r
+#lexclass TOK_DEF_COMMENTS\r
+#token "\*/" << zzmode(PARSE_ENUM_FILE);\r
+ zzmore(); >>\r
+#token "\*" << zzmore(); >>\r
+#token "\n|\r|\r\n" << zzline++; zzmore(); DAWDLE; >>\r
+#token "~[\n\r\*]+" << zzmore(); >>\r
+\r
+#lexclass TOK_DEF_CPP_COMMENTS\r
+#token "\n|\r|\r\n" << zzline++; zzmode(PARSE_ENUM_FILE); zzskip(); DAWDLE; >>\r
+#token "~[\n\r]+" << zzskip(); >>\r
+\r
+#lexclass ACTION_CPP_COMMENTS\r
+#token "\n|\r|\r\n" << zzline++; zzmode(ACTIONS); zzmore(); DAWDLE; >>\r
+#token "~[\n\r]+" << zzmore(); >>\r
+\r
+#lexclass CPP_COMMENTS\r
+#token "\n|\r|\r\n" << zzline++; zzmode(START); zzskip(); DAWDLE; >>\r
+#token "~[\n\r]+" << zzskip(); >>\r
+\r
+#lexclass COMMENTS\r
+#token "\*/" << zzmode(START); zzskip(); >>\r
+#token "\*" << zzskip(); >>\r
+#token "\n|\r|\r\n" << zzline++; zzskip(); DAWDLE; >>\r
+#token "~[\n\r\*]+" << zzskip(); >>\r
+\r
+/*\r
+ * This lexical class accepts actions of type [..] and <<..>>\r
+ *\r
+ * It translates the following special items for C:\r
+ *\r
+ * $j --> "zzaArg(current zztasp, j)"\r
+ * $i.j --> "zzaArg(zztaspi, j)"\r
+ * $i.nondigit> "zzaArg(current zztasp, i).nondigit"\r
+ * $$ --> "zzaRet"\r
+ * $alnum --> "alnum" (used to ref parameters)\r
+ * $rule --> "zzaRet"\r
+ * $retval --> "_retv.retval" if > 1 return values else "_retv"\r
+ * $[token, text] --> "zzconstr_attr(token, text)"\r
+ * $[] --> "zzempty_attr()"\r
+ *\r
+ * It translates the following special items for C++:\r
+ * (attributes are now stored with 'Token' and $i's are only\r
+ * pointers to the Tokens. Rules don't have attributes now.)\r
+ *\r
+ * $j --> "_tbj" where b is the block level\r
+ * $i.j --> "_tij"\r
+ * $j->nondigit> "_tbj->nondigit"\r
+ * $$ --> "$$"\r
+ * $alnum --> "alnum" (used to ref parameters)\r
+ * $rule --> "$rule"\r
+ * $retval --> "_retv.retval" if > 1 return values else "_retv"\r
+ * $[token, text] --> invalid\r
+ * $[] --> invalid\r
+ *\r
+ * And, for trees:\r
+ *\r
+ * #0 --> "(*_root)"\r
+ * #i --> "zzastArg(i)"\r
+ * #[args] --> "zzmk_ast(zzastnew(), args)"\r
+ * #[] --> "zzastnew()"\r
+ * #( root, child1, ..., childn )\r
+ * --> "zztmake(root, child1, ...., childn, NULL)"\r
+ * #() --> "NULL"\r
+ *\r
+ * For C++, ...\r
+ *\r
+ * #0 --> "(*_root)"\r
+ * #i --> "_astbi" where b is the block level\r
+ * #alnum --> "alnum_ast" (used to ref #label)\r
+ * #[args] --> "new AST(args)"\r
+ * #[] --> "new AST"\r
+ * #( root, child1, ..., childn )\r
+ * --> "AST::tmake(root, child1, ...., childn, NULL)"\r
+ * #() --> "NULL"\r
+ *\r
+ * To escape,\r
+ *\r
+ * \] --> ]\r
+ * \) --> )\r
+ * \$ --> $\r
+ * \# --> #\r
+ *\r
+ * A stack is used to nest action terminators because they can be nested\r
+ * like crazy: << #[$[..],..] >>\r
+ */\r
+#lexclass ACTIONS\r
+#token Action "\>\>" << /* these do not nest */\r
+ zzmode(START);\r
+ NLATEXT[0] = ' ';\r
+ NLATEXT[1] = ' ';\r
+ zzbegexpr[0] = ' ';\r
+ zzbegexpr[1] = ' ';\r
+ if ( zzbufovf ) {\r
+ err( eMsgd("action buffer overflow; size %d",ZZLEXBUFSIZE));\r
+ }\r
+\r
+/* MR1 10-Apr-97 MR1 Previously unable to put right shift operator */\r
+/* MR1 in DLG action */\r
+/* MR1 Doesn't matter what kind of action it is - reset*/\r
+\r
+ tokenActionActive=0; /* MR1 */\r
+ >>\r
+#token Pred "\>\>?" << /* these do not nest */\r
+ zzmode(START);\r
+ NLATEXT[0] = ' ';\r
+ NLATEXT[1] = ' ';\r
+ zzbegexpr[0] = '\0';\r
+ if ( zzbufovf ) {\r
+ err( eMsgd("predicate buffer overflow; size %d",ZZLEXBUFSIZE));\r
+ };\r
+#ifdef __cplusplus__\r
+/* MR10 */ list_apply(CurActionLabels, (void (*)(void *))mark_label_used_in_sem_pred);\r
+#else\r
+#ifdef __STDC__\r
+/* MR10 */ list_apply(CurActionLabels, (void (*)(void *))mark_label_used_in_sem_pred);\r
+#else\r
+#ifdef __USE_PROTOS\r
+/* MRxx */ list_apply(CurActionLabels, (void (*)(void *))mark_label_used_in_sem_pred);\r
+#else\r
+/* MR10 */ list_apply(CurActionLabels,mark_label_used_in_sem_pred);\r
+#endif\r
+#endif\r
+#endif\r
+ >>\r
+#token PassAction "\]" << if ( topint() == ']' ) {\r
+ popint();\r
+ if ( istackempty() ) /* terminate action */\r
+ {\r
+ zzmode(START);\r
+ NLATEXT[0] = ' ';\r
+ zzbegexpr[0] = ' ';\r
+ if ( zzbufovf ) {\r
+ err( eMsgd("parameter buffer overflow; size %d",ZZLEXBUFSIZE));\r
+ }\r
+ }\r
+ else {\r
+ /* terminate $[..] and #[..] */\r
+ if ( GenCC ) zzreplstr("))");\r
+ else zzreplstr(")");\r
+ zzmore();\r
+ }\r
+ }\r
+ else if ( topint() == '|' ) { /* end of simple [...] */\r
+ popint();\r
+ zzmore();\r
+ }\r
+ else zzmore();\r
+ >>\r
+#token "consumeUntil\( [\ \t]* \{~[\}]+\} [\ \t]* \)"\r
+ <<\r
+ zzmore();\r
+ zzreplstr(inline_set(zzbegexpr+\r
+ strlen("consumeUntil(")));\r
+ >>\r
+#token "consumeUntil\( ~[\)]+ \)"\r
+ << zzmore(); >>\r
+#token "\n|\r|\r\n" << zzline++; zzmore(); DAWDLE; >>\r
+#token "\>" << zzmore(); >>\r
+#token "$" << zzmore(); >>\r
+#token "$$" << if ( !GenCC ) {zzreplstr("zzaRet"); zzmore();}\r
+ else err("$$ use invalid in C++ mode"); >>\r
+\r
+#token "$\[\]" << if ( !GenCC ) {zzreplstr("zzempty_attr"); zzmore();}\r
+ else err("$[] use invalid in C++ mode"); >>\r
+#token "$\[" <<\r
+ pushint(']');\r
+ if ( !GenCC ) zzreplstr("zzconstr_attr(");\r
+ else err("$[..] use invalid in C++ mode");\r
+ zzmore();\r
+ >>\r
+#token "$[0-9]+" <<{\r
+ static char buf[100];\r
+ numericActionLabel=1; /* MR10 */\r
+ if ( strlen(zzbegexpr)>(size_t)85 )\r
+ fatal("$i attrib ref too big");\r
+ set_orel(atoi(zzbegexpr+1), &attribsRefdFromAction);\r
+ if ( !GenCC ) sprintf(buf,"zzaArg(zztasp%d,%s)",\r
+ BlkLevel-1,zzbegexpr+1);\r
+ else sprintf(buf,"_t%d%s",\r
+ BlkLevel-1,zzbegexpr+1);\r
+ zzreplstr(buf);\r
+ zzmore();\r
+ UsedOldStyleAttrib = 1;\r
+ if ( UsedNewStyleLabel )\r
+ err("cannot mix old-style $i with new-style labels");\r
+ }\r
+ >>\r
+#token "$[0-9]+." <<{\r
+ static char buf[100];\r
+ numericActionLabel=1; /* MR10 */\r
+ if ( strlen(zzbegexpr)>(size_t)85 )\r
+ fatal("$i.field attrib ref too big");\r
+ zzbegexpr[strlen(zzbegexpr)-1] = ' ';\r
+ set_orel(atoi(zzbegexpr+1), &attribsRefdFromAction);\r
+ if ( !GenCC ) sprintf(buf,"zzaArg(zztasp%d,%s).",\r
+ BlkLevel-1,zzbegexpr+1);\r
+ else sprintf(buf,"_t%d%s.",\r
+ BlkLevel-1,zzbegexpr+1);\r
+ zzreplstr(buf);\r
+ zzmore();\r
+ UsedOldStyleAttrib = 1;\r
+ if ( UsedNewStyleLabel )\r
+ err("cannot mix old-style $i with new-style labels");\r
+ }\r
+ >>\r
+#token "$[0-9]+.[0-9]+" <<{\r
+ static char buf[100];\r
+ static char i[20], j[20];\r
+ char *p,*q;\r
+ numericActionLabel=1; /* MR10 */\r
+ if (strlen(zzbegexpr)>(size_t)85) fatal("$i.j attrib ref too big");\r
+ for (p=zzbegexpr+1,q= &i[0]; *p!='.'; p++) {\r
+ if ( q == &i[20] )\r
+ fatalFL("i of $i.j attrib ref too big",\r
+ FileStr[CurFile], zzline );\r
+ *q++ = *p;\r
+ }\r
+ *q = '\0';\r
+ for (p++, q= &j[0]; *p!='\0'; p++) {\r
+ if ( q == &j[20] )\r
+ fatalFL("j of $i.j attrib ref too big",\r
+ FileStr[CurFile], zzline );\r
+ *q++ = *p;\r
+ }\r
+ *q = '\0';\r
+ if ( !GenCC ) sprintf(buf,"zzaArg(zztasp%s,%s)",i,j);\r
+ else sprintf(buf,"_t%s%s",i,j);\r
+ zzreplstr(buf);\r
+ zzmore();\r
+ UsedOldStyleAttrib = 1;\r
+ if ( UsedNewStyleLabel )\r
+ err("cannot mix old-style $i with new-style labels");\r
+ }\r
+ >>\r
+#token "$[_a-zA-Z][_a-zA-Z0-9]*"\r
+ <<{ static char buf[300]; LabelEntry *el;\r
+ zzbegexpr[0] = ' ';\r
+ if ( CurRule != NULL &&\r
+ strcmp(CurRule, &zzbegexpr[1])==0 ) {\r
+ if ( !GenCC ) zzreplstr("zzaRet");\r
+ }\r
+ else if ( CurRetDef != NULL &&\r
+ strmember(CurRetDef, &zzbegexpr[1])) {\r
+ if ( hasMultipleOperands( CurRetDef ) ) {\r
+ require (strlen(zzbegexpr)<=(size_t)285,\r
+ "$retval attrib ref too big");\r
+ sprintf(buf,"_retv.%s",&zzbegexpr[1]);\r
+ zzreplstr(buf);\r
+ }\r
+ else zzreplstr("_retv");\r
+ }\r
+ else if ( CurParmDef != NULL &&\r
+ strmember(CurParmDef, &zzbegexpr[1])) {\r
+ ;\r
+ }\r
+ else if ( Elabel==NULL ) {\r
+ { err("$-variables in actions outside of rules are not allowed"); }\r
+ } else if ( (el=(LabelEntry *)hash_get(Elabel, &zzbegexpr[1]))!=NULL ) {\r
+/* MR10 */\r
+/* MR10 */ /* element labels might exist without an elem when */\r
+/* MR10 */ /* it is a forward reference (to a rule) */\r
+/* MR10 */\r
+/* MR10 */ if ( GenCC && (el->elem == NULL || el->elem->ntype==nRuleRef) )\r
+/* MR10 */ { err(eMsg1("There are no token ptrs for rule references: '$%s'",&zzbegexpr[1])); }\r
+/* MR10 */\r
+/* MR10 */ if ( !GenCC && (el->elem == NULL || el->elem->ntype==nRuleRef) && GenAST) {\r
+/* MR10 */ err("You can no longer use attributes returned by rules when also using ASTs");\r
+/* MR10 */ err(" Use upward inheritance (\"rule >[Attrib a] : ... <<$a=...\>\>\")");\r
+/* MR10 */ };\r
+/* MR10 */\r
+/* MR10 */ /* keep track of <<... $label ...>> for semantic predicates in guess mode */\r
+/* MR10 */ /* element labels contain pointer to the owners node */\r
+/* MR10 */\r
+/* MR10 */ if (el->elem != NULL && el->elem->ntype == nToken) {\r
+/* MR10 */ list_add(&CurActionLabels,el);\r
+/* MR10 */ };\r
+ }\r
+ else\r
+ warn(eMsg1("$%s not parameter, return value, (defined) element label",&zzbegexpr[1]));\r
+ }\r
+ zzmore();\r
+ >>\r
+#token "#0" << zzreplstr("(*_root)"); zzmore(); chkGTFlag(); >>\r
+#token "#\[\]" << if ( GenCC ) {\r
+ if (NewAST) zzreplstr("(newAST)");\r
+ else zzreplstr("(new AST)");}\r
+ else {zzreplstr("zzastnew()");} zzmore();\r
+ chkGTFlag();\r
+ >>\r
+#token "#\(\)" << zzreplstr("NULL"); zzmore(); chkGTFlag(); >>\r
+#token "#[0-9]+" <<{\r
+ static char buf[100];\r
+ if ( strlen(zzbegexpr)>(size_t)85 )\r
+ fatal("#i AST ref too big");\r
+ if ( GenCC ) sprintf(buf,"_ast%d%s",BlkLevel-1,zzbegexpr+1);\r
+ else sprintf(buf,"zzastArg(%s)",zzbegexpr+1);\r
+ zzreplstr(buf);\r
+ zzmore();\r
+ set_orel(atoi(zzbegexpr+1), &AST_nodes_refd_in_actions);\r
+ chkGTFlag();\r
+ }\r
+ >>\r
+\r
+/* MR14 Arpad Beszedes 26-May-98\r
+ Add support for #line directives when antlr source is pre-processed\r
+ #lexclass ACTIONS\r
+*/\r
+\r
+#token "#line[\ \t]* [0-9]+ {[\ \t]* \"~[\"]+\" ([\ \t]* [0-9]*)* } (\n|\r|\r\n)"\r
+ <<\r
+ zzline = atoi(zzbegexpr+5) - 1; zzline++; zzmore();\r
+ getFileNameFromTheLineInfo(FileStr[CurFile], zzbegexpr);\r
+ >>\r
+\r
+#token "#line ~[\n\r]* (\n|\r|\r\n)"\r
+ <<\r
+ zzline++; zzmore();\r
+ >>\r
+\r
+/* MR14 end of a block to support #line in antlr source code */\r
+\r
+#token "#[_a-zA-Z][_a-zA-Z0-9]*"\r
+ <<\r
+ if ( !(strcmp(zzbegexpr, "#ifdef")==0 ||\r
+ strcmp(zzbegexpr, "#if")==0 ||\r
+ strcmp(zzbegexpr, "#else")==0 ||\r
+ strcmp(zzbegexpr, "#endif")==0 ||\r
+ strcmp(zzbegexpr, "#ifndef")==0 ||\r
+ strcmp(zzbegexpr, "#define")==0 ||\r
+ strcmp(zzbegexpr, "#pragma")==0 ||\r
+ strcmp(zzbegexpr, "#undef")==0 ||\r
+ strcmp(zzbegexpr, "#import")==0 ||\r
+ strcmp(zzbegexpr, "#line")==0 ||\r
+ strcmp(zzbegexpr, "#include")==0 ||\r
+ strcmp(zzbegexpr, "#error")==0) )\r
+ {\r
+ static char buf[100];\r
+ sprintf(buf, "%s_ast", zzbegexpr+1);\r
+/* MR27 */ list_add(&CurAstLabelsInActions, mystrdup(zzbegexpr+1));\r
+ zzreplstr(buf);\r
+ chkGTFlag();\r
+ }\r
+ zzmore();\r
+ >>\r
+#token "#\[" <<\r
+ pushint(']');\r
+ if ( GenCC ) {\r
+ if (NewAST) zzreplstr("(newAST(");\r
+ else zzreplstr("(new AST("); }\r
+ else zzreplstr("zzmk_ast(zzastnew(),");\r
+ zzmore();\r
+ chkGTFlag();\r
+ >>\r
+#token "#\(" <<\r
+ pushint('}');\r
+ if ( GenCC ) {\r
+ if (tmakeInParser) {\r
+ zzreplstr("tmake(");\r
+ }\r
+ else {\r
+ zzreplstr("ASTBase::tmake(");\r
+ }\r
+ }\r
+ else {\r
+ zzreplstr("zztmake(");\r
+ }\r
+ zzmore();\r
+ chkGTFlag();\r
+ >>\r
+#token "#" << zzmore(); >>\r
+#token "\)" <<\r
+ if ( istackempty() )\r
+ zzmore();\r
+ else if ( topint()==')' ) {\r
+ popint();\r
+ }\r
+ else if ( topint()=='}' ) {\r
+ popint();\r
+ /* terminate #(..) */\r
+ zzreplstr(", NULL)");\r
+ }\r
+ zzmore();\r
+ >>\r
+#token "\[" <<\r
+ pushint('|'); /* look for '|' to terminate simple [...] */\r
+ zzmore();\r
+ >>\r
+#token "\(" <<\r
+ pushint(')');\r
+ zzmore();\r
+ >>\r
+\r
+#token "\\\]" << zzreplstr("]"); zzmore(); >>\r
+#token "\\\)" << zzreplstr(")"); zzmore(); >>\r
+\r
+/* MR1 10-Apr-97 MR1 Previously unable to put right shift operator */\r
+/* MR1 in DLG action */\r
+\r
+#token "\\>" << if (! tokenActionActive) zzreplstr(">"); /* MR1 */\r
+ zzmore(); /* MR1 */\r
+ >> /* MR1 */\r
+\r
+\r
+#token "'" << zzmode(ACTION_CHARS); zzmore();>>\r
+#token "\"" << zzmode(ACTION_STRINGS); zzmore();>>\r
+#token "\\$" << zzreplstr("$"); zzmore(); >>\r
+#token "\\#" << zzreplstr("#"); zzmore(); >>\r
+#token "\\(\n|\r|\r\n)" << zzline++; zzmore(); >>\r
+#token "\\~[\]\)>$#]" << zzmore(); >> /* escaped char, always ignore */\r
+#token "/" << zzmore(); >>\r
+#token "/\*" << zzmode(ACTION_COMMENTS); zzmore(); >>\r
+#token "\*/" << warn("Missing /*; found dangling */ in action"); zzmore(); >>\r
+#token "//" << zzmode(ACTION_CPP_COMMENTS); zzmore(); >>\r
+#token "~[\n\r\)\(\\$#\>\]\[\"'/]+" << zzmore(); >>\r
+\r
+#lexclass START\r
+#token "[\t\ ]+" << zzskip(); >> /* Ignore White */\r
+#token "\n|\r|\r\n" << zzline++; zzskip(); >> /* Track Line # */\r
+#token "\[" << zzmode(ACTIONS); zzmore();\r
+ istackreset();\r
+ pushint(']'); >>\r
+#token "\<\<" << action_file=CurFile; action_line=zzline;\r
+ zzmode(ACTIONS); zzmore();\r
+ list_free(&CurActionLabels,0); /* MR10 */\r
+ numericActionLabel=0; /* MR10 */\r
+ istackreset();\r
+ pushint('>'); >>\r
+#token "\"" << zzmode(STRINGS); zzmore(); >>\r
+#token "/\*" << zzmode(COMMENTS); zzskip(); >>\r
+#token "\*/" << warn("Missing /*; found dangling */"); zzskip(); >>\r
+#token "//" << zzmode(CPP_COMMENTS); zzskip(); >>\r
+\r
+/* MR14 Arpad Beszedes 26-May-98\r
+ Add support for #line directives when antlr source is pre-processed\r
+ #lexclass START\r
+*/\r
+\r
+#token "#line[\ \t]* [0-9]+ {[\ \t]* \"~[\"]+\" ([\ \t]* [0-9]*)* } (\n|\r|\r\n)"\r
+ <<\r
+ zzline = atoi(zzbegexpr+5) - 1; zzline++; zzmore();\r
+ getFileNameFromTheLineInfo(FileStr[CurFile], zzbegexpr);\r
+ >>\r
+\r
+#token "#line ~[\n\r]* (\n|\r|\r\n)"\r
+ <<\r
+ zzline++; zzmore();\r
+ >>\r
+\r
+/* MR14 end of a block to support #line in antlr source code */\r
+\r
+/* */\r
+/* 8-Apr-97 Regularize escape sequence for ">>" */\r
+/* appearing in string literals */\r
+/* */\r
+\r
+#token "\>\>" << warn("Missing <<; found dangling \>\>"); zzskip(); >> /* MR1 */\r
+#token WildCard "."\r
+#token "\@" <<FoundException = 1; /* MR6 */\r
+ FoundAtOperator = 1;>> /* MR6 */\r
+#token Eof "@"\r
+ << /* L o o k F o r A n o t h e r F i l e */\r
+ {\r
+ FILE *new_input;\r
+ new_input = NextFile();\r
+ if ( new_input == NULL ) { NLA=Eof; return; }\r
+ fclose( input );\r
+ input = new_input;\r
+ zzrdstream( input );\r
+ zzskip(); /* Skip the Eof (@) char i.e continue */\r
+ }\r
+ >>\r
+\r
+#token LABEL\r
+\r
+#errclass "grammar-element" { element }\r
+#errclass "meta-symbol" { "\}" "!" ";" "\|" "\~" "^" "\)" }\r
+\r
+#token Pragma "{\\}#pragma" /* MR21 */\r
+#token FirstSetSymbol "{\\}#FirstSetSymbol" /* MR21 */\r
+/*\r
+ * Get a grammar -- Build a list of rules like:\r
+ *\r
+ * o-->Rule1--o\r
+ * |\r
+ * o-->Rule2--o\r
+ * |\r
+ * ...\r
+ * |\r
+ * o-->RuleN--o\r
+ */\r
+\r
+/* rule grammar */\r
+\r
+grammar : <<Graph g;>>\r
+ ( "{\\}#header" Action /* MR13 */\r
+ <<\r
+ if ( HdrAction==NULL ) {\r
+ HdrAction = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(HdrAction!=NULL, "rule grammar: cannot allocate header action");\r
+ strcpy(HdrAction, LATEXT(1));\r
+ }\r
+ else warn("additional #header statement ignored");\r
+ >>\r
+ | "{\\}#first" Action\r
+ <<\r
+ if ( FirstAction==NULL ) {\r
+ FirstAction = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(FirstAction!=NULL, "rule grammar: cannot allocate #first action");\r
+ strcpy(FirstAction, LATEXT(1));\r
+ } else {\r
+ warn("additional #first statement ignored");\r
+ };\r
+ >>\r
+\r
+ | "{\\}#parser" QuotedTerm\r
+ <<\r
+ if ( GenCC ) {\r
+ warn("#parser meta-op incompatible with -CC; ignored");\r
+ }\r
+ else {\r
+ if ( strcmp(ParserName,"zzparser")==0 ) {\r
+ ParserName=StripQuotes(mystrdup(LATEXT(1)));\r
+ if ( RulePrefix[0]!='\0' )\r
+ {\r
+ warn("#parser meta-op incompatible with '-gp prefix'; '-gp' ignored");\r
+ RulePrefix[0]='\0';\r
+ }\r
+ }\r
+ else warn("additional #parser statement ignored");\r
+ }\r
+ >>\r
+ | "{\\}#tokdefs" QuotedTerm\r
+ <<{\r
+ char *fname;\r
+ zzantlr_state st; FILE *f; struct zzdlg_state dst;\r
+ UserTokenDefsFile = mystrdup(LATEXT(1));\r
+ zzsave_antlr_state(&st);\r
+ zzsave_dlg_state(&dst);\r
+ fname = mystrdup(LATEXT(1));\r
+ f = fopen(StripQuotes(fname), "r");\r
+ if ( f==NULL ) {warn(eMsg1("cannot open token defs file '%s'", fname+1));}\r
+ else {\r
+ ANTLRm(enum_file(fname+1), f, PARSE_ENUM_FILE);\r
+ UserDefdTokens = 1;\r
+ }\r
+ zzrestore_antlr_state(&st);\r
+ zzrestore_dlg_state(&dst);\r
+ }>>\r
+ )*\r
+ ( Action\r
+ <<{\r
+ UserAction *ua = newUserAction(LATEXT(1));\r
+ ua->file = action_file; ua->line = action_line;\r
+ if ( class_nest_level>0 ) list_add(&class_before_actions, ua);\r
+ else list_add(&BeforeActions, ua);\r
+ }>>\r
+ | laction\r
+ | lmember /* MR1 */\r
+ | lprefix /* MR1 */\r
+ | aLexclass\r
+ | token\r
+ | error\r
+ | tclass\r
+ | aPred /* MR11 */\r
+ | default_exception_handler\r
+ | class_def\r
+ | "\}"\r
+ <<\r
+ if ( class_nest_level==0 )\r
+ warn("missing class definition for trailing '}'");\r
+ class_nest_level--;\r
+ >>\r
+ )*\r
+ \r
+ rule <<g=$3; SynDiag = (Junction *) $3.left;>>\r
+ ( rule\r
+\r
+ <<if ( $1.left!=NULL ) {\r
+ g.right = NULL;\r
+\r
+/* MR21a */ /* Avoid use of a malformed graph when CannotContinue */\r
+/* MR21a */ /* is already set */\r
+/* MR21a */\r
+/* MR21a */ if (! (CannotContinue && g.left == NULL)) {\r
+/* MR21a */ g = Or(g, $1);\r
+/* MR21a */ }\r
+/* MR21a */ }\r
+ >>\r
+\r
+ | aLexclass\r
+ | token\r
+ | error\r
+ | tclass\r
+ | aPred /* MR11 */\r
+ | class_def\r
+ | "\}"\r
+ <<\r
+ if ( class_nest_level==0 )\r
+ warn("missing class definition for trailing '}'");\r
+ class_nest_level--;\r
+ >>\r
+ )*\r
+ ( Action\r
+ <<{\r
+ UserAction *ua = newUserAction(LATEXT(1));\r
+ ua->file = action_file; ua->line = action_line;\r
+ if ( class_nest_level>0 ) list_add(&class_after_actions, ua);\r
+ else list_add(&AfterActions, ua);\r
+ }>>\r
+ | laction\r
+ | lmember /* MR1 */\r
+ | lprefix /* MR1 */\r
+ | error\r
+ | tclass\r
+ | class_def\r
+ | aPred /* MR11 */\r
+ | "\}"\r
+ <<\r
+ if ( class_nest_level==0 )\r
+ warn("missing class definition for trailing '}'");\r
+ class_nest_level--;\r
+ >>\r
+ )*\r
+ Eof\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/* rule class_def */\r
+\r
+class_def\r
+ : <<int go=1; char name[MaxRuleName+1];>>\r
+ "class"\r
+ ( NonTerminal <<if(go) strncpy(name,LATEXT(1),MaxRuleName);>>\r
+ | TokenTerm <<if(go) strncpy(name,LATEXT(1),MaxRuleName);>>\r
+ )\r
+ <<\r
+ if ( CurrentClassName[0]!='\0' && strcmp(CurrentClassName,name)!=0\r
+ && GenCC ) {\r
+ err("only one grammar class allowed in this release");\r
+ go = 0;\r
+ }\r
+ else strcpy(CurrentClassName, name);\r
+ >>\r
+ <<if ( !GenCC ) { err("class meta-op used without C++ option"); }>>\r
+\r
+/* MR10 */ (~ "\{"\r
+/* MR10 */ <<if (ClassDeclStuff == NULL) {\r
+/* MR10 */ ClassDeclStuff=(char *)calloc(MaxClassDeclStuff+1,sizeof(char));\r
+/* MR10 */ };\r
+/* MR10 */ strncat(ClassDeclStuff," ",MaxClassDeclStuff);\r
+/* MR10 */ strncat(ClassDeclStuff,LATEXT(1),MaxClassDeclStuff);\r
+/* MR22 */ do {\r
+/* MR22 */ if (0 == strcmp(LATEXT(1),"public")) break;\r
+/* MR22 */ if (0 == strcmp(LATEXT(1),"private")) break;\r
+/* MR22 */ if (0 == strcmp(LATEXT(1),"protected")) break;\r
+/* MR22 */ if (0 == strcmp(LATEXT(1),"virtual")) break;\r
+/* MR22 */ if (0 == strcmp(LATEXT(1),",")) break;\r
+/* MR22 */ if (0 == strcmp(LATEXT(1),":")) break;\r
+/* MR22 */ if (BaseClassName != NULL) break;\r
+/* MR22 */ BaseClassName=(char *)calloc(strlen(LATEXT(1))+1,sizeof(char));\r
+/* MR22 */ require(BaseClassName!=NULL, "rule grammar: cannot allocate base class name");\r
+/* MR22 */ strcpy(BaseClassName,LATEXT(1));\r
+/* MR22 */ } while (0);\r
+/* MR10 */ >>\r
+/* MR10 */ )*\r
+\r
+ "\{"\r
+ <<\r
+ no_classes_found = 0;\r
+ if ( class_nest_level>=1 ) {warn("cannot have nested classes");}\r
+ else class_nest_level++;\r
+ >>\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/*\r
+ * Build -o-->o-R-o-->o- where -o-R-o- is the block from rule 'block'.\r
+ * Construct the RuleBlk front and EndRule node on the end of the\r
+ * block. This is used to add FOLLOW pointers to the rule end. Add the\r
+ * new rule name to the Rname hash table and sets its rulenum.\r
+ * Store the parameter definitions if any are found.\r
+ *\r
+ * Note that locks are required on the RuleBlk and EndRule nodes to thwart\r
+ * infinite recursion.\r
+ *\r
+ * Return the left graph pointer == NULL to indicate error/dupl rule def.\r
+ */\r
+\r
+/* rule rule */\r
+\r
+rule : <<\r
+\r
+ ExceptionGroup *eg;\r
+ RuleEntry *q; Junction *p; Graph r; int f, l; ECnode *e;\r
+ set toksrefd, rulesrefd;\r
+ char *pdecl=NULL, *ret=NULL, *a; CurRetDef = CurParmDef = NULL;\r
+ CurExGroups = NULL;\r
+ CurElementLabels = NULL;\r
+ CurAstLabelsInActions = NULL; /* MR27 */\r
+ /* We want a new element label hash table for each rule */\r
+ if ( Elabel!=NULL ) killHashTable(Elabel);\r
+ Elabel = newHashTable();\r
+ attribsRefdFromAction = empty;\r
+ >>\r
+ NonTerminal\r
+ <<q=NULL;\r
+ if ( hash_get(Rname, LATEXT(1))!=NULL ) {\r
+ err(eMsg1("duplicate rule definition: '%s'",LATEXT(1)));\r
+ CannotContinue=TRUE;\r
+ }\r
+ else\r
+ {\r
+ q = (RuleEntry *)hash_add(Rname,\r
+ LATEXT(1),\r
+ (Entry *)newRuleEntry(LATEXT(1)));\r
+ CurRule = q->str;\r
+ }\r
+ CurRuleNode = q;\r
+ f = CurFile; l = zzline;\r
+ NumRules++;\r
+ >>\r
+ { "!" <<if ( q!=NULL ) q->noAST = TRUE;>> }\r
+ { <<;>>\r
+ {"\<"}\r
+ PassAction\r
+ << pdecl = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(pdecl!=NULL, "rule rule: cannot allocate param decl");\r
+ strcpy(pdecl, LATEXT(1));\r
+ CurParmDef = pdecl;\r
+ >>\r
+ }\r
+ { "\>"\r
+ PassAction\r
+ << ret = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(ret!=NULL, "rule rule: cannot allocate ret type");\r
+ strcpy(ret, LATEXT(1));\r
+ CurRetDef = ret;\r
+ >>\r
+ }\r
+ { QuotedTerm <<if ( q!=NULL ) q->egroup=mystrdup(LATEXT(1));>> }\r
+ <<\r
+ if ( GenEClasseForRules && q!=NULL ) {\r
+ e = newECnode;\r
+ require(e!=NULL, "cannot allocate error class node");\r
+ if ( q->egroup == NULL ) {a = q->str; a[0] = (char)toupper(a[0]);}\r
+ else a = q->egroup;\r
+ if ( Tnum( a ) == 0 )\r
+ {\r
+ e->tok = addTname( a );\r
+ list_add(&eclasses, (char *)e);\r
+ if ( q->egroup == NULL ) a[0] = (char)tolower(a[0]);\r
+ /* refers to itself */\r
+ list_add(&(e->elist), mystrdup(q->str));\r
+ }\r
+ else {\r
+ warn(eMsg1("default errclass for '%s' would conflict with token/errclass/tokclass",a));\r
+ if ( q->egroup == NULL ) a[0] = (char)tolower(a[0]);\r
+ free((char *)e);\r
+ }\r
+ }\r
+ >>\r
+ <<BlkLevel++;\r
+ if (BlkLevel >= MAX_BLK_LEVEL) fatal("Blocks nested too deeply");\r
+/* MR23 */ CurBlockID_array[BlkLevel] = CurBlockID;\r
+/* MR23 */ CurAltNum_array[BlkLevel] = CurAltNum; \r
+ >>\r
+\r
+ ":" <<inAlt=1;>>\r
+ block[&toksrefd, &rulesrefd]\r
+ <<r = makeBlk($7,0, NULL /* pFirstSetSymbol */ );\r
+ CurRuleBlk = (Junction *)r.left;\r
+ CurRuleBlk->blockid = CurBlockID;\r
+ CurRuleBlk->jtype = RuleBlk;\r
+ if ( q!=NULL ) CurRuleBlk->rname = q->str;\r
+ CurRuleBlk->file = f;\r
+ CurRuleBlk->line = l;\r
+ CurRuleBlk->pdecl = pdecl;\r
+ CurRuleBlk->ret = ret;\r
+ CurRuleBlk->lock = makelocks();\r
+ CurRuleBlk->pred_lock = makelocks();\r
+ CurRuleBlk->tokrefs = toksrefd;\r
+ CurRuleBlk->rulerefs = rulesrefd;\r
+ p = newJunction(); /* add EndRule Node */\r
+ ((Junction *)r.right)->p1 = (Node *)p;\r
+ r.right = (Node *) p;\r
+ p->jtype = EndRule;\r
+ p->lock = makelocks();\r
+ p->pred_lock = makelocks();\r
+ CurRuleBlk->end = p;\r
+ if ( q!=NULL ) q->rulenum = NumRules;\r
+ $7 = r;\r
+ >>\r
+ <<\r
+ /* MR23 */ CurBlockID_array[BlkLevel] = (-1);\r
+ /* MR23 */ CurAltNum_array[BlkLevel] = (-1); \r
+ --BlkLevel;\r
+ >>\r
+ <<altFixup();leFixup();egFixup();>> /* MR7 */\r
+ ";" <<inAlt=0;>>\r
+ { Action\r
+ << a = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(a!=NULL, "rule rule: cannot allocate error action");\r
+ strcpy(a, LATEXT(1));\r
+ CurRuleBlk->erraction = a;\r
+ >>\r
+ }\r
+ ( exception_group > [eg]\r
+ <<if ( eg!=NULL ) {\r
+ list_add(&CurExGroups, (void *)eg);\r
+ if (eg->label == NULL || *eg->label=='\0' ) q->has_rule_exception = 1;\r
+ }\r
+ >>\r
+ )*\r
+ <<if ( q==NULL ) $0.left = NULL; else $0 = $7;>>\r
+ <<CurRuleBlk->exceptions = CurExGroups;>>\r
+ <<CurRuleBlk->el_labels = CurElementLabels;>>\r
+ <<CurRuleNode->ast_labels_in_actions = CurAstLabelsInActions;>> /* MR27 */\r
+ <<CurRuleNode = NULL;>> /* MR27 Moved */\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/*\r
+ * pragma : "{\\}#pragma" "dup\-labeled\-tokens"\r
+ * <<Pragma_DupLabeledTokens=1;>>\r
+ * ;\r
+ */\r
+\r
+/* rule laction */\r
+\r
+laction : <<char *a;>>\r
+\r
+ "{\\}#lexaction"\r
+ Action\r
+ <<\r
+ a = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(a!=NULL, "rule laction: cannot allocate action");\r
+ strcpy(a, LATEXT(1));\r
+ list_add(&LexActions, a);\r
+ >>\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/* MR1 */\r
+/* MR1 11-Apr-97 Provide mechanism for inserting code into DLG class */\r
+/* MR1 via #lexmember <<....>> & #lexprefix <<...>> */\r
+/* MR1 */\r
+\r
+/* rule lmember */\r
+\r
+lmember: <<char *a;>> /* MR1 */\r
+\r
+/* MR1 */ "{\\}#lexmember"\r
+/* MR1 */ Action\r
+/* MR1 */ <<\r
+/* MR1 */ if (! GenCC) {\r
+/* MR1 */ err("Use #lexmember only in C++ mode (to insert code in DLG class header");\r
+/* MR1 */ } else {\r
+/* MR1 */ a = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+/* MR1 */ require(a!=NULL, "rule lmember: cannot allocate action");\r
+/* MR1 */ strcpy(a, LATEXT(1));\r
+/* MR1 */ list_add(&LexMemberActions, a);\r
+/* MR1 */ };\r
+/* MR1 */ >>\r
+/* MR1 */ ;\r
+/* MR1 */ <<CannotContinue=TRUE;>>\r
+\r
+/* rule lprefix */\r
+\r
+lprefix: <<char *a;>> /* MR1 */\r
+\r
+/* MR1 */ "{\\}#lexprefix"\r
+/* MR1 */ Action\r
+/* MR1 */ <<\r
+/* MR1 */ if (! GenCC) {\r
+/* MR1 */ err("Use #lexprefix only in C++ mode (to insert code in DLG class header");\r
+/* MR1 */ } else {\r
+/* MR1 */ a = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+/* MR1 */ require(a!=NULL, "rule lprefix: cannot allocate action");\r
+/* MR1 */ strcpy(a, LATEXT(1));\r
+/* MR1 */ list_add(&LexPrefixActions, a);\r
+/* MR1 */ };\r
+/* MR1 */ >>\r
+/* MR1 */ ;\r
+/* MR1 */ <<CannotContinue=TRUE;>>\r
+\r
+/*\r
+ * #pred upper <<isupper()>>? predicate literal\r
+ * #pred lower <<islower()>>? predicate literal\r
+ * #pred up_or_low upper || lower predicate expression\r
+ * concealed interdependence\r
+ * #pred up_or_low_2 <<isletter()>>? A || B predicate literal equals predicate expr\r
+ * analyze using lower||upper\r
+ * generate using isLetter()\r
+ */\r
+\r
+/* rule aPref */\r
+\r
+aPred: <<PredEntry *predEntry=NULL;\r
+ char *name=NULL;\r
+ Predicate *predExpr=NULL;\r
+ char *predLiteral=NULL;\r
+ int save_file;\r
+ int save_line;\r
+ int predExprPresent=0;\r
+ >>\r
+\r
+ "{\\}#pred"\r
+\r
+ <<\r
+ MR_usingPredNames=1; /* will need to use -mrhoist version of genPredTree */\r
+ >>\r
+\r
+ /* used to allow NonTerminal but it caused problems\r
+ when a rule name immediately followed a #pred statement */\r
+\r
+ TokenTerm <<name=mystrdup(LATEXT(1));>>\r
+\r
+ <<\r
+ /* don't free - referenced in predicates */\r
+\r
+ CurPredName=(char *)calloc(1,strlen(name) + 10);\r
+ strcat(CurPredName,"#pred ");\r
+ strcat(CurPredName,name);\r
+\r
+ predEntry=(PredEntry *) hash_get(Pname,name);\r
+ if (predEntry != NULL) {\r
+ warnFL(eMsg1("#pred %s previously defined - ignored",name),\r
+ FileStr[action_file],action_line);\r
+ name=NULL;\r
+ };\r
+ >>\r
+\r
+ (\r
+\r
+ Pred <<predLiteral=mystrdup(LATEXT(1));\r
+ save_line=action_line;\r
+ save_file=action_file;\r
+ >>\r
+\r
+ {\r
+ predOrExpr>[predExpr] <<predExprPresent=1;>>\r
+ }\r
+\r
+ <<if (predLiteral != NULL && name != NULL) {\r
+\r
+ /*\r
+ * predExpr may be NULL due to syntax errors\r
+ * or simply omitted by the user\r
+ */\r
+\r
+ predEntry=newPredEntry(name);\r
+ predEntry->file=save_file;\r
+ predEntry->line=save_line;\r
+ predExpr=MR_predFlatten(predExpr);\r
+ predEntry->predLiteral=predLiteral;\r
+ if (! predExprPresent || predExpr == NULL) {\r
+ predExpr=new_pred();\r
+ predExpr->expr=predLiteral;\r
+ predExpr->source=newActionNode();\r
+ predExpr->source->action=predExpr->expr;\r
+ predExpr->source->rname=CurPredName;\r
+ predExpr->source->line=action_line;\r
+ predExpr->source->file=action_file;\r
+ predExpr->source->is_predicate=1;\r
+ predExpr->k=predicateLookaheadDepth(predExpr->source);\r
+ };\r
+ predEntry->pred=predExpr;\r
+ hash_add(Pname,name,(Entry *)predEntry);\r
+ predExpr=NULL;\r
+ };\r
+ predicate_free(predExpr);\r
+ >>\r
+\r
+ |\r
+ <<save_line=zzline; save_file=CurFile;>>\r
+\r
+ predOrExpr>[predExpr]\r
+\r
+ <<if (predExpr != NULL && name != NULL) {\r
+ predEntry=newPredEntry(name);\r
+ predEntry->file=CurFile;\r
+ predEntry->line=zzline;\r
+ predExpr=MR_predFlatten(predExpr);\r
+ predEntry->pred=predExpr;\r
+ hash_add(Pname,name,(Entry *)predEntry);\r
+ predExpr=NULL;\r
+ };\r
+ predicate_free(predExpr);\r
+ >>\r
+ )\r
+ {";"}\r
+;\r
+\r
+/* fail */\r
+\r
+<<predicate_free(predExpr);\r
+>>\r
+\r
+/* rule predOrExpr */\r
+\r
+predOrExpr>[Predicate *result] :\r
+ <<Predicate *ORnode;\r
+ Predicate *predExpr;\r
+ Predicate **tail=NULL;\r
+ >>\r
+ predAndExpr>[predExpr]\r
+ <<\r
+ ORnode=new_pred();\r
+ ORnode->expr=PRED_OR_LIST;\r
+ if (predExpr != NULL) {\r
+ ORnode->down=predExpr;\r
+ tail=&predExpr->right;\r
+ };\r
+ >>\r
+ ( "\|\|" predAndExpr>[predExpr]\r
+ <<\r
+ if (predExpr != NULL) {\r
+ *tail=predExpr;\r
+ tail=&predExpr->right;\r
+ };\r
+ >>\r
+ )*\r
+ <<\r
+ $result=ORnode;\r
+ ORnode=NULL;\r
+ >>\r
+;\r
+\r
+/* fail */\r
+\r
+<<predicate_free(ORnode);>>\r
+\r
+/* rule predAndExpr */\r
+\r
+predAndExpr>[Predicate *result] :\r
+ <<Predicate *ANDnode;\r
+ Predicate *predExpr;\r
+ Predicate **tail=NULL;\r
+ >>\r
+ predPrimary>[predExpr]\r
+ <<\r
+ ANDnode=new_pred();\r
+ ANDnode->expr=PRED_AND_LIST;\r
+ if (predExpr != NULL) {\r
+ ANDnode->down=predExpr;\r
+ tail=&predExpr->right;\r
+ };\r
+ >>\r
+ ( "&&" predPrimary>[predExpr]\r
+ <<\r
+ if (predExpr != NULL) {\r
+ *tail=predExpr;\r
+ tail=&predExpr->right;\r
+ };\r
+ >>\r
+ )*\r
+ <<\r
+ $result=ANDnode;\r
+ ANDnode=NULL;\r
+ >>\r
+;\r
+\r
+/* fail */\r
+\r
+<<predicate_free(ANDnode);>>\r
+\r
+\r
+/* rule predPrimary */\r
+\r
+predPrimary>[Predicate *result] :\r
+ <<\r
+ char *name=NULL;\r
+ PredEntry *predEntry=NULL;\r
+ Predicate *predExpr=NULL;\r
+ >>\r
+\r
+ TokenTerm <<name=mystrdup(LATEXT(1));>>\r
+\r
+ <<\r
+ predEntry=(PredEntry *) hash_get(Pname,name);\r
+ if (predEntry == NULL) {\r
+ warnFL(eMsg1("no previously defined #pred with name \"%s\"",name),\r
+ FileStr[CurFile],zzline);\r
+ name=NULL;\r
+ $result=NULL;\r
+ } else {\r
+ predExpr=predicate_dup(predEntry->pred);\r
+ predExpr->predEntry=predEntry;\r
+ $result=predExpr;\r
+ };\r
+ >>\r
+\r
+ | "\(" predOrExpr>[predExpr] "\)"\r
+ <<\r
+ $result=predExpr;\r
+ >>\r
+\r
+ | "!" predPrimary>[predExpr]\r
+ <<\r
+ predExpr->inverted=!predExpr->inverted;\r
+ $result=predExpr;\r
+ >>\r
+;\r
+\r
+/* fail */ <<\r
+ predicate_free(predExpr);\r
+ >>\r
+\r
+/* rule aLexclass */\r
+\r
+aLexclass: "{\\}#lexclass" TokenTerm <<lexclass(mystrdup(LATEXT(1)));>>\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/* rule error */\r
+\r
+error : <<char *t=NULL; ECnode *e; int go=1; TermEntry *p;>>\r
+ "{\\}#errclass"\r
+ (<<;>> TokenTerm <<t=mystrdup(LATEXT(1));>>\r
+ | QuotedTerm <<t=mystrdup(LATEXT(1));>>\r
+ )\r
+ <<e = newECnode;\r
+ require(e!=NULL, "cannot allocate error class node");\r
+ e->lexclass = CurrentLexClass;\r
+ if ( Tnum( (t=StripQuotes(t)) ) == 0 )\r
+ {\r
+ if ( hash_get(Texpr, t) != NULL )\r
+ warn(eMsg1("errclass name conflicts with regular expression '%s'",t));\r
+ e->tok = addTname( t );\r
+ set_orel(e->tok, &imag_tokens);\r
+ require((p=(TermEntry *)hash_get(Tname, t)) != NULL,\r
+ "hash table mechanism is broken");\r
+ p->classname = 1; /* entry is errclass name, not token */\r
+ list_add(&eclasses, (char *)e);\r
+ }\r
+ else\r
+ {\r
+ warn(eMsg1("redefinition of errclass or conflict w/token or tokclass '%s'; ignored",t));\r
+ free( (char *)e );\r
+ go=0;\r
+ }\r
+ >>\r
+ "\{"\r
+ ( NonTerminal <<if ( go ) t=mystrdup(LATEXT(1));>>\r
+ | TokenTerm <<if ( go ) t=mystrdup(LATEXT(1));>>\r
+ | QuotedTerm <<if ( go ) t=mystrdup(LATEXT(1));>>\r
+ )\r
+ <<if ( go ) list_add(&(e->elist), t);>>\r
+ (\r
+ ( NonTerminal <<if ( go ) t=mystrdup(LATEXT(1));>>\r
+ | TokenTerm <<if ( go ) t=mystrdup(LATEXT(1));>>\r
+ | QuotedTerm <<if ( go ) t=mystrdup(LATEXT(1));>>\r
+ )\r
+ <<if ( go ) list_add(&(e->elist), t);>>\r
+ )*\r
+ "\}"\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/* rule tclass */\r
+\r
+tclass : <<char *t=NULL; TCnode *e; int go=1,tok,totok; TermEntry *p, *term, *toterm;>>\r
+ <<char *akaString=NULL; int save_file; int save_line;>>\r
+ <<char *totext=NULL; >>\r
+ "{\\}#tokclass" TokenTerm <<t=mystrdup(LATEXT(1));>>\r
+ <<e = newTCnode;\r
+ require(e!=NULL, "cannot allocate token class node");\r
+ e->lexclass = CurrentLexClass;\r
+ if ( Tnum( t ) == 0 )\r
+ {\r
+ e->tok = addTname( t );\r
+ set_orel(e->tok, &imag_tokens);\r
+ set_orel(e->tok, &tokclasses);\r
+ require((p=(TermEntry *)hash_get(Tname, t)) != NULL,\r
+ "hash table mechanism is broken");\r
+ p->classname = 1; /* entry is class name, not token */\r
+ p->tclass = e; /* save ptr to this tclass def */\r
+ list_add(&tclasses, (char *)e);\r
+ }\r
+ else\r
+ {\r
+ warn(eMsg1("redefinition of tokclass or conflict w/token '%s'; ignored",t));\r
+ free( (char *)e );\r
+ go=0;\r
+ }\r
+ >>\r
+/* MR23 */ {\r
+/* MR23 */ "\("\r
+/* MR23 */ QuotedTerm\r
+/* MR23 */ <<akaString=mystrdup(StripQuotes(LATEXT(1)));\r
+/* MR11 */ save_file=CurFile;save_line=zzline;\r
+/* MR23 */ >>\r
+/* MR23 */ "\)"\r
+/* MR23 */ }\r
+/* MR23 */\r
+/* MR23 */\r
+/* MR23 */ <<\r
+/* MR23 */ if (p!= NULL && akaString != NULL) {\r
+/* MR23 */ if (p->akaString != NULL) {\r
+/* MR23 */ if (strcmp(p->akaString,akaString) != 0) {\r
+/* MR23 */ warnFL(eMsg2("this #tokclass statment conflicts with a previous #tokclass %s(\"%s\") statement",\r
+/* MR23 */ t,p->akaString),\r
+/* MR23 */ FileStr[save_file],save_line);\r
+/* MR23 */ };\r
+/* MR23 */ } else {\r
+/* MR23 */ p->akaString=akaString;\r
+/* MR23 */ };\r
+/* MR23 */ };\r
+/* MR23 */ >>\r
+\r
+ "\{"\r
+ (\r
+ ( TokenTerm\r
+ <<if ( go ) {\r
+ term = (TermEntry *) hash_get(Tname, LATEXT(1));\r
+ if ( term==NULL && UserDefdTokens ) {\r
+ err("implicit token definition not allowed with #tokdefs");\r
+ go = 0;\r
+ }\r
+ else {t=mystrdup(LATEXT(1)); tok=addTname(LATEXT(1));}\r
+ }>>\r
+\r
+ {\r
+ ".."\r
+ TokenTerm\r
+\r
+ <<if ( go ) {\r
+ toterm = (TermEntry *) hash_get(Tname, LATEXT(1));\r
+ if ( toterm==NULL && UserDefdTokens ) {\r
+ err("implicit token definition not allowed with #tokdefs");\r
+ go = 0;\r
+ } else {\r
+ totext=mystrdup(LATEXT(1)); totok=addTname(LATEXT(1));\r
+ }\r
+ }\r
+ >>\r
+ }\r
+\r
+ | QuotedTerm\r
+ <<if ( go ) {\r
+ term = (TermEntry *) hash_get(Texpr, LATEXT(1));\r
+ if ( term==NULL && UserDefdTokens ) {\r
+ err("implicit token definition not allowed with #tokdefs");\r
+ go = 0;\r
+ }\r
+ else {t=mystrdup(LATEXT(1)); tok=addTexpr(LATEXT(1));}\r
+ }>>\r
+ )\r
+ <<if ( go ) {\r
+ if (totext == NULL) {\r
+ list_add(&(e->tlist), t);\r
+ } else {\r
+ list_add(&(e->tlist),"..");\r
+ list_add(&(e->tlist),t);\r
+ list_add(&(e->tlist),totext);\r
+ }\r
+ totext=NULL;\r
+ }\r
+ >>\r
+ )+ // MR15 Manfred Kogler - forbid empty #tokclass sets (was "+")\r
+ "\}"\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/* rule token */\r
+\r
+token : <<char *t=NULL, *e=NULL, *a=NULL; int tnum=0;>>\r
+ <<char *akaString=NULL; TermEntry *te;int save_file=0,save_line=0;>> /* MR11 */\r
+ "{\\}#token"\r
+\r
+/* MR1 10-Apr-97 MR1 Allow shift right operator in DLG actions */\r
+/* MR1 Danger when parser feedback to lexer */\r
+/* MR1 */\r
+\r
+ <<tokenActionActive=1;>> /* MR1 */\r
+ { TokenTerm <<t=mystrdup(LATEXT(1));>>\r
+\r
+/* MR11 */ {\r
+/* MR11 */ "\("\r
+/* MR11 */ QuotedTerm\r
+/* MR11 */ <<akaString=mystrdup(StripQuotes(LATEXT(1)));\r
+/* MR11 */ save_file=CurFile;save_line=zzline;\r
+/* MR11 */ >>\r
+/* MR11 */ "\)"\r
+/* MR11 */ }\r
+\r
+ { "=" "[0-9]+" /* define the token type number */\r
+ <<tnum = atoi(LATEXT(1));>>\r
+ }\r
+ }\r
+ { QuotedTerm <<e=mystrdup(LATEXT(1));>> }\r
+ { Action\r
+ <<\r
+ a = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(a!=NULL, "rule token: cannot allocate action");\r
+ strcpy(a, LATEXT(1));\r
+ >>\r
+ }\r
+\r
+ { ";" } /* MR11 */\r
+\r
+ <<chkToken(t, e, a, tnum);>>\r
+\r
+ <<if (t != NULL) {\r
+ te=(TermEntry *)hash_get(Tname,t);\r
+ if (te != NULL && akaString != NULL) {\r
+ if (te->akaString != NULL) {\r
+ if (strcmp(te->akaString,akaString) != 0) {\r
+ warnFL(eMsg2("this #token statment conflicts with a previous #token %s(\"%s\") statement",\r
+ t,te->akaString),\r
+ FileStr[save_file],save_line);\r
+ };\r
+ } else {\r
+ te->akaString=akaString;\r
+ };\r
+ };\r
+ };\r
+ >>\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/* rule block */\r
+\r
+block[set *toksrefd, set *rulesrefd]\r
+ : <<\r
+ Graph g, b;\r
+ set saveblah;\r
+ int saveinalt = inAlt;\r
+ ExceptionGroup *eg;\r
+ *$toksrefd = empty;\r
+ *$rulesrefd = empty;\r
+ set_clr(AST_nodes_refd_in_actions);\r
+ CurBlockID++;\r
+/* MR23 */ CurBlockID_array[BlkLevel] = CurBlockID;\r
+ CurAltNum = 1;\r
+/* MR23 */ CurAltNum_array[BlkLevel] = CurAltNum; \r
+ saveblah = attribsRefdFromAction;\r
+ attribsRefdFromAction = empty;\r
+ >>\r
+\r
+ alt[toksrefd,rulesrefd] <<b = g = $1;>>\r
+\r
+ <<\r
+ if ( ((Junction *)g.left)->p1->ntype == nAction )\r
+ {\r
+ ActionNode *actionNode=(ActionNode *)\r
+ ( ( (Junction *)g.left) ->p1);\r
+ if (!actionNode->is_predicate )\r
+ {\r
+ actionNode->init_action = TRUE;\r
+/* MR12c */ if (actionNode->noHoist) {\r
+/* MR12c */ errFL("<<nohoist>> appears as init-action - use <<>> <<nohoist>>",\r
+/* MR12c */ FileStr[actionNode->file],actionNode->line);\r
+/* MR12c */ };\r
+ }\r
+ }\r
+ ((Junction *)g.left)->blockid = CurBlockID;\r
+ >>\r
+\r
+ ( exception_group > [eg]\r
+ <<\r
+ if ( eg!=NULL ) {\r
+/* MR7 ***** eg->altID = makeAltID(CurBlockID,CurAltNum); *****/\r
+/* MR7 ***** CurAltStart->exception_label = eg->altID; *****/\r
+ list_add(&CurExGroups, (void *)eg);\r
+ }\r
+ >>\r
+ )*\r
+ <<CurAltNum++;\r
+/* MR23 */ CurAltNum_array[BlkLevel] = CurAltNum;\r
+ >>\r
+\r
+ ( "\|" <<inAlt=1;>>\r
+ alt[toksrefd,rulesrefd] <<g = Or(g, $2);>>\r
+ <<\r
+ ((Junction *)g.left)->blockid = CurBlockID;\r
+ >>\r
+\r
+ ( exception_group > [eg]\r
+ <<\r
+ if ( eg!=NULL ) {\r
+/* MR7 ***** eg->altID = makeAltID(CurBlockID,CurAltNum); *****/\r
+/* MR7 ***** CurAltStart->exception_label = eg->altID; *****/\r
+ list_add(&CurExGroups, (void *)eg);\r
+ }\r
+ >>\r
+ )*\r
+\r
+ <<CurAltNum++;\r
+/* MR23 */ CurAltNum_array[BlkLevel] = CurAltNum; \r
+ >>\r
+\r
+ )*\r
+ <<$0 = b;>>\r
+ <<attribsRefdFromAction = saveblah; inAlt = saveinalt;>>\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/* rule alt */\r
+\r
+alt[set *toksrefd, set *rulesrefd]\r
+ : <<int n=0; Graph g; int e_num=0, old_not=0; Node *node; set elems, dif;\r
+ int first_on_line = 1, use_def_MT_handler = 0;\r
+ g.left=NULL; g.right=NULL;\r
+\r
+ CurAltStart = NULL;\r
+ elems = empty;\r
+ inAlt = 1;\r
+ >>\r
+ { "\@" /* handle MismatchedToken signals with default handler */\r
+ <<use_def_MT_handler = 1;>>\r
+ }\r
+\r
+ ( <<;>> /* MR9 Removed unreferenced variable "tok" */\r
+ { <<old_not=0;>> "\~" <<old_not=1;>> }\r
+ element[old_not, first_on_line, use_def_MT_handler] > [node]\r
+ <<if ( node!=NULL && node->ntype!=nAction ) first_on_line = 0;>>\r
+ <<\r
+ if ( $2.left!=NULL ) {\r
+ g = Cat(g, $2);\r
+ n++;\r
+ if ( node!=NULL ) {\r
+ if ( node->ntype!=nAction ) e_num++;\r
+ /* record record number of all rule and token refs */\r
+ if ( node->ntype==nToken ) {\r
+ TokNode *tk = (TokNode *)((Junction *)$2.left)->p1;\r
+ tk->elnum = e_num;\r
+ set_orel(e_num, &elems);\r
+ }\r
+ else if ( node->ntype==nRuleRef ) {\r
+ RuleRefNode *rn = (RuleRefNode *)((Junction *)$2.left)->p1;\r
+ rn->elnum = e_num;\r
+ set_orel(e_num, $rulesrefd);\r
+ }\r
+ }\r
+ }\r
+ >>\r
+ )*\r
+ <<if ( n == 0 ) g = emptyAlt();\r
+ $0 = g;\r
+ /* We want to reduce number of LT(i) calls and the number of\r
+ * local attribute variables in C++ mode (for moment, later we'll\r
+ * do for C also). However, if trees are being built, they\r
+ * require most of the attrib variables to create the tree nodes\r
+ * with; therefore, we gen a token ptr for each token ref in C++\r
+ */\r
+ if ( GenCC && !GenAST )\r
+ {\r
+ /* This now free's the temp set -ATG 5/6/95 */\r
+ set temp;\r
+ temp = set_and(elems, attribsRefdFromAction);\r
+ set_orin($toksrefd, temp);\r
+ set_free(temp);\r
+ }\r
+ else set_orin($toksrefd, elems);\r
+ if ( GenCC ) {\r
+ dif = set_dif(attribsRefdFromAction, elems);\r
+ if ( set_deg(dif)>0 )\r
+ err("one or more $i in action(s) refer to non-token elements");\r
+ set_free(dif);\r
+ }\r
+ set_free(elems);\r
+ set_free(attribsRefdFromAction);\r
+ inAlt = 0;\r
+ >>\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/* rule element_label */\r
+\r
+element_label > [LabelEntry *label]\r
+ : <<TermEntry *t=NULL; LabelEntry *l=NULL; RuleEntry *r=NULL; char *lab;>>\r
+ LABEL <<lab = mystrdup(LATEXT(1));>>\r
+ <<\r
+ UsedNewStyleLabel = 1;\r
+ if ( UsedOldStyleAttrib ) err("cannot mix with new-style labels with old-style $i");\r
+ t = (TermEntry *) hash_get(Tname, lab);\r
+ if ( t==NULL ) t = (TermEntry *) hash_get(Texpr, lab);\r
+ if ( t==NULL ) r = (RuleEntry *) hash_get(Rname, lab);\r
+ if ( t!=NULL ) {\r
+ err(eMsg1("label definition clashes with token/tokclass definition: '%s'", lab));\r
+ $label = NULL;\r
+ }\r
+ else if ( r!=NULL ) {\r
+ err(eMsg1("label definition clashes with rule definition: '%s'", lab));\r
+ $label = NULL;\r
+ }\r
+ else {\r
+ /* we don't clash with anybody else */\r
+ l = (LabelEntry *) hash_get(Elabel, lab);\r
+ if ( l==NULL ) { /* ok to add new element label */\r
+ l = (LabelEntry *)hash_add(Elabel,\r
+ lab,\r
+ (Entry *)newLabelEntry(lab));\r
+ /* add to list of element labels for this rule */\r
+ list_add(&CurElementLabels, (void *)lab);\r
+/* MR7 */ leAdd(l); /* list of labels waiting for exception group definitions */\r
+ $label = l;\r
+ }\r
+ else {\r
+ err(eMsg1("label definitions must be unique per rule: '%s'", lab));\r
+ $label = NULL;\r
+ }\r
+ }\r
+ >>\r
+ ":"\r
+ ;\r
+\r
+/* rule element */\r
+\r
+element[int old_not, int first_on_line, int use_def_MT_handler] > [Node *node]\r
+ : <<\r
+ Attrib blk;\r
+ Predicate *pred = NULL;\r
+ int local_use_def_MT_handler=0;\r
+ ActionNode *act;\r
+ RuleRefNode *rr;\r
+ set toksrefd, rulesrefd;\r
+ TermEntry *term;\r
+ TokNode *p=NULL; RuleRefNode *q; int approx=0;\r
+ LabelEntry *label=NULL;\r
+ int predMsgDone=0;\r
+ int semDepth=0;\r
+ int ampersandStyle;\r
+ int height; /* MR11 */\r
+ int equal_height; /* MR11 */\r
+\r
+ char* pFirstSetSymbol = NULL; /* MR21 */\r
+\r
+ $node = NULL;\r
+ >>\r
+ {element_label>[label]}\r
+ ( TokenTerm\r
+ <<\r
+ term = (TermEntry *) hash_get(Tname, LATEXT(1));\r
+ if ( term==NULL && UserDefdTokens ) {\r
+ err("implicit token definition not allowed with #tokdefs");\r
+ $$.left = $$.right = NULL;\r
+ }\r
+ else {\r
+ $$ = buildToken(LATEXT(1));\r
+ p=((TokNode *)((Junction *)$$.left)->p1);\r
+ term = (TermEntry *) hash_get(Tname, LATEXT(1));\r
+ require( term!= NULL, "hash table mechanism is broken");\r
+ p->tclass = term->tclass;\r
+ p->complement = $old_not;\r
+ if ( label!=NULL ) {\r
+ p->el_label = label->str;\r
+ label->elem = (Node *)p;\r
+ }\r
+ }\r
+ >>\r
+ { ".."\r
+ ( QuotedTerm\r
+ <<if ( p!=NULL ) setUpperRange(p, LATEXT(1));>>\r
+ | TokenTerm\r
+ <<if ( p!=NULL ) setUpperRange(p, LATEXT(1));>>\r
+ )\r
+ }\r
+ <<\r
+ if ( p!=NULL && (p->upper_range!=0 || p->tclass || $old_not) )\r
+ list_add(&MetaTokenNodes, (void *)p);\r
+ >>\r
+ ( "^" <<if ( p!=NULL ) p->astnode=ASTroot;>>\r
+ | <<if ( p!=NULL ) p->astnode=ASTchild;>>\r
+ | "!" <<if ( p!=NULL ) p->astnode=ASTexclude;>>\r
+ )\r
+ { "\@" <<local_use_def_MT_handler = 1;>> }\r
+ <<\r
+ if ( p!=NULL && $first_on_line ) {\r
+ CurAltStart = (Junction *)$$.left;\r
+ altAdd(CurAltStart); /* MR7 */\r
+ p->altstart = CurAltStart;\r
+ }\r
+ if ( p!=NULL )\r
+ p->use_def_MT_handler = $use_def_MT_handler || local_use_def_MT_handler;\r
+ $node = (Node *)p;\r
+ >>\r
+ | QuotedTerm\r
+ <<\r
+ term = (TermEntry *) hash_get(Texpr, LATEXT(1));\r
+ if ( term==NULL && UserDefdTokens ) {\r
+ err("implicit token definition not allowed with #tokdefs");\r
+ $$.left = $$.right = NULL;\r
+ }\r
+ else {\r
+ $$ = buildToken(LATEXT(1)); p=((TokNode *)((Junction *)$$.left)->p1);\r
+ p->complement = $old_not;\r
+ if ( label!=NULL ) {\r
+ p->el_label = label->str;\r
+ label->elem = (Node *)p;\r
+ }\r
+ }\r
+ >>\r
+ { ".."\r
+ ( QuotedTerm\r
+ <<if ( p!=NULL ) setUpperRange(p, LATEXT(1));>>\r
+ | TokenTerm\r
+ <<if ( p!=NULL ) setUpperRange(p, LATEXT(1));>>\r
+ )\r
+ }\r
+ ( "^" <<if ( p!=NULL ) p->astnode=ASTroot;>>\r
+ | <<if ( p!=NULL ) p->astnode=ASTchild;>>\r
+ | "!" <<if ( p!=NULL ) p->astnode=ASTexclude;>>\r
+ )\r
+ { "\@" <<local_use_def_MT_handler = 1;>> }\r
+ <<\r
+ if ( p!=NULL && (p->upper_range!=0 || p->tclass || $old_not) )\r
+ list_add(&MetaTokenNodes, (void *)p);\r
+ >>\r
+ <<\r
+ if ( $first_on_line ) {\r
+ CurAltStart = (Junction *)$$.left;\r
+ altAdd(CurAltStart); /* MR7 */\r
+ p->altstart = CurAltStart;\r
+ }\r
+ if ( p!=NULL )\r
+ p->use_def_MT_handler = $use_def_MT_handler || local_use_def_MT_handler;\r
+ $node = (Node *)p;\r
+ >>\r
+\r
+ | <<if ( $old_not ) warn("~ WILDCARD is an undefined operation (implies 'nothing')");>>\r
+ "."\r
+ <<$$ = buildWildCard(LATEXT(1)); p=((TokNode *)((Junction *)$$.left)->p1);>>\r
+ ( "^" <<p->astnode=ASTroot;>>\r
+ | <<p->astnode=ASTchild;>>\r
+ | "!" <<p->astnode=ASTexclude;>>\r
+ )\r
+ <<list_add(&MetaTokenNodes, (void *)p);>>\r
+ <<\r
+ if ( $first_on_line ) {\r
+ CurAltStart = (Junction *)$$.left;\r
+ altAdd(CurAltStart); /* MR7 */\r
+ p->altstart = CurAltStart;\r
+ if ( label!=NULL ) {\r
+ p->el_label = label->str;\r
+ label->elem = (Node *)p;\r
+ }\r
+ }\r
+ $node = (Node *)p;\r
+ >>\r
+\r
+ | <<if ( $old_not ) warn("~ NONTERMINAL is an undefined operation");>>\r
+ NonTerminal\r
+ <<$$ = buildRuleRef(LATEXT(1));>>\r
+ { "!" <<q = (RuleRefNode *) ((Junction *)$$.left)->p1;\r
+ q->astnode=ASTexclude;>>\r
+ }\r
+ { {"\<"}\r
+ PassAction <<addParm(((Junction *)$$.left)->p1, LATEXT(1));>>\r
+ }\r
+ <<rr=(RuleRefNode *) ((Junction *)$$.left)->p1;>>\r
+ { <<char *a;>>\r
+ "\>"\r
+ PassAction\r
+ <<\r
+ a = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(a!=NULL, "rule element: cannot allocate assignment");\r
+ strcpy(a, LATEXT(1));\r
+ rr->assign = a;\r
+ >>\r
+ }\r
+ <<\r
+ if ( label!=NULL ) {\r
+ rr->el_label = label->str;\r
+ label->elem = (Node *)rr;\r
+ }\r
+ if ( $first_on_line ) {\r
+ CurAltStart = (Junction *)$$.left;\r
+ altAdd(CurAltStart); /* MR7 */\r
+ ((RuleRefNode *)((Junction *)$$.left)->p1)->altstart = CurAltStart;\r
+ }\r
+ $node = (Node *)rr;\r
+ >>\r
+ )\r
+\r
+ | <<if ( $old_not ) warn("~ ACTION is an undefined operation");>>\r
+ Action <<$0 = buildAction(LATEXT(1),action_file,action_line, 0);>>\r
+ <<if ( $first_on_line ) { /* MR7 */\r
+ CurAltStart = (Junction *)$0.left; /* MR7 */\r
+ altAdd(CurAltStart); /* MR7 */\r
+ };>> /* MR7 */\r
+ <<$node = (Node *) ((Junction *)$0.left)->p1;>>\r
+\r
+ | <<if ( $old_not ) warn("~ SEMANTIC-PREDICATE is an undefined operation");>>\r
+ Pred <<$0 = buildAction(LATEXT(1),action_file,action_line, 1);>>\r
+ <<act = (ActionNode *) ((Junction *)$0.left)->p1;>>\r
+ <<if (numericActionLabel) { /* MR10 */\r
+ list_add(&NumericPredLabels,act); /* MR10 */\r
+ numericActionLabel=0; /* MR10 */\r
+ }; /* MR10 */\r
+ >>\r
+ { <<char *a;>>\r
+ PassAction\r
+ <<\r
+ a = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(a!=NULL, "rule element: cannot allocate predicate fail action");\r
+ strcpy(a, LATEXT(1));\r
+ act->pred_fail = a;\r
+ >>\r
+ }\r
+ <<if ( $first_on_line ) { /* MR7 */\r
+ CurAltStart = (Junction *)$0.left; /* MR7 */\r
+ altAdd(CurAltStart); /* MR7 */\r
+ };>> /* MR7 */\r
+ <<$node = (Node *)act;>>\r
+\r
+ | <<if ( $old_not ) warn("~ BLOCK is an undefined operation");>>\r
+ <<BlkLevel++;\r
+ if (BlkLevel >= MAX_BLK_LEVEL) fatal("Blocks nested too deeply");\r
+/* MR23 */ CurBlockID_array[BlkLevel] = CurBlockID;\r
+/* MR23 */ CurAltNum_array[BlkLevel] = CurAltNum; \r
+ >>\r
+ { Pragma\r
+ ( "approx" <<approx=LL_k;>>\r
+ | "LL\(1\)" <<approx = 1;>> /* MR20 */\r
+ | "LL\(2\)" <<approx = 2;>> /* MR20 */\r
+ )\r
+ }\r
+\r
+/* MR21 */ { FirstSetSymbol\r
+/* MR21 */ "\("\r
+/* MR21 */ ( NonTerminal\r
+/* MR21 */ <<\r
+/* MR21 */ pFirstSetSymbol = (char *) calloc(strlen(LATEXT(1))+1,\r
+/* MR21 */ sizeof(char));\r
+/* MR21 */ require(pFirstSetSymbol!=NULL,\r
+/* MR21 */ "cannot allocate first set name");\r
+/* MR21 */ strcpy(pFirstSetSymbol, LATEXT(1));\r
+/* MR21 */ >>\r
+/* MR21 */ | TokenTerm\r
+/* MR21 */ <<\r
+/* MR21 */ pFirstSetSymbol = (char *) calloc(strlen(LATEXT(1))+1,\r
+/* MR21 */ sizeof(char));\r
+/* MR21 */ require(pFirstSetSymbol!=NULL,\r
+/* MR21 */ "cannot allocate first set name");\r
+/* MR21 */ strcpy(pFirstSetSymbol, LATEXT(1));\r
+/* MR21 */ >>\r
+/* MR21 */ )\r
+/* MR21 */ "\)"\r
+/* MR21 */ }\r
+\r
+ (\r
+\r
+ "\(" block[&toksrefd,&rulesrefd] "\)"\r
+ <<blk = $$ = $2;\r
+ /* MR23 */ CurBlockID_array[BlkLevel] = (-1);\r
+ /* MR23 */ CurAltNum_array[BlkLevel] = (-1); \r
+ --BlkLevel;\r
+ >>\r
+\r
+ ( "\*" <<$$ = makeLoop($$,approx,pFirstSetSymbol);>>\r
+ | "\+" <<$$ = makePlus($$,approx,pFirstSetSymbol);>>\r
+ | "?"\r
+ ( \r
+ ( "=>" <<ampersandStyle=0;>>\r
+ | "&&" <<ampersandStyle=1;>> /* MR10 (g)? && <<p>>? */\r
+ )\r
+ Pred /* generalized predicate */\r
+ /* first make into a predicate */\r
+ <<$$ = buildAction(LATEXT(1),action_file,action_line,1);>>\r
+ <<act = (ActionNode *) ((Junction *)$$.left)->p1;>>\r
+ <<semDepth=predicateLookaheadDepth(act);>> /* MR10 */\r
+ <<if (numericActionLabel) { /* MR10 */\r
+ list_add(&NumericPredLabels,act); /* MR10 */\r
+ numericActionLabel=0; /* MR10 */\r
+ }; /* MR10 */\r
+ >>\r
+ { <<char *a;>>\r
+ PassAction\r
+ <<\r
+ a = (char *)calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(a!=NULL, "rule element: cannot allocate predicate fail action");\r
+ strcpy(a, LATEXT(1));\r
+ act->pred_fail = a;\r
+ >>\r
+ }\r
+ <<if ($first_on_line) { /* MR7 */\r
+ CurAltStart=(Junction *)$$.left; /* MR7 */\r
+ altAdd(CurAltStart); /* MR7 */\r
+ };>>\r
+ <<$node = (Node *)act;>>\r
+\r
+ /* for now, just snag context */\r
+ <<\r
+ pred = computePredFromContextGuard(blk,&predMsgDone); /* MR10 */\r
+ if ( pred==NULL) { /* MR10 */\r
+ if ( !predMsgDone) err("invalid or missing context guard"); /* MR10 */\r
+ predMsgDone=1; /* MR10 */\r
+ } else { /* MR10 */\r
+ act->guardNodes=(Junction *)blk.left; /* MR11 */\r
+ pred->expr = act->action;\r
+ pred->source = act;\r
+/* MR10 */ pred->ampersandStyle = ampersandStyle; /* 0 means (g)? => ... 1 means (g)? && ... */\r
+/* MR13 */ if (pred->tcontext != NULL) {\r
+/* MR13 */ height=MR_max_height_of_tree(pred->tcontext);\r
+/* MR13 */ equal_height=MR_all_leaves_same_height(pred->tcontext,height);\r
+/* MR13 */ if (! equal_height) {\r
+/* MR13 */ errFL("in guarded predicates all tokens in the guard must be at the same height",\r
+/* MR13 */ FileStr[act->file],act->line);\r
+/* MR13 */ };\r
+/* MR13 */ }\r
+/* MR10 */ if (ampersandStyle) {\r
+/* MR10 */ act->ampersandPred = pred;\r
+/* MR11 */ if (! HoistPredicateContext) {\r
+/* MR11 */ errFL("without \"-prc on\" (guard)? && <<pred>>? ... doesn't make sense",\r
+/* MR11 */ FileStr[act->file],act->line);\r
+/* MR11 */ };\r
+/* MR10 */ } else {\r
+/* MR10 */ act->guardpred = pred;\r
+/* MR10 */ };\r
+/* MR10 */ if (pred->k != semDepth) {\r
+/* MR10 */ warn(eMsgd2("length of guard (%d) does not match the length of semantic predicate (%d)",\r
+/* MR10 */ pred->k,semDepth));\r
+/* MR10 */ };\r
+ }\r
+ >>\r
+ | <<$$ = makeBlk($$,approx,pFirstSetSymbol);\r
+ FoundGuessBlk = 1;\r
+ ((Junction *) ((Junction *)$$.left)->p1)->guess=1;\r
+ if ( !$first_on_line ) {\r
+ err("(...)? predicate must be first element of production");\r
+ }\r
+ >>\r
+ )\r
+ | <<$$ = makeBlk($$,approx,pFirstSetSymbol);>>\r
+ )\r
+ <<\r
+ if ( pred==NULL && !predMsgDone) { /* MR10 */\r
+ ((Junction *)((Junction *)$$.left)->p1)->blockid = CurBlockID;\r
+ ((Junction *)((Junction *)$$.left)->p1)->tokrefs = toksrefd;\r
+ ((Junction *)((Junction *)$$.left)->p1)->rulerefs = rulesrefd;\r
+ if ( $first_on_line ) { /* MR7 */\r
+ CurAltStart = (Junction *)((Junction *)((Junction *)$$.left)->p1); /* MR7 */\r
+ altAdd(CurAltStart); /* MR7 */\r
+ }; /* MR7 */\r
+ $node = (Node *) ((Junction *)$$.left)->p1;\r
+ }\r
+ >>\r
+\r
+ | "\{" block[&toksrefd,&rulesrefd]\r
+ <<$$ = makeOpt($2,approx,pFirstSetSymbol);\r
+ /* MR23 */ CurBlockID_array[BlkLevel] = (-1);\r
+ /* MR23 */ CurAltNum_array[BlkLevel] = (-1); \r
+ --BlkLevel;\r
+ >>\r
+ "\}"\r
+ <<\r
+ ((Junction *)((Junction *)$$.left)->p1)->blockid = CurBlockID;\r
+ ((Junction *)((Junction *)$$.left)->p1)->tokrefs = toksrefd;\r
+ ((Junction *)((Junction *)$$.left)->p1)->rulerefs = rulesrefd;\r
+ >>\r
+ <<if ( $first_on_line ) { /* MR7 */\r
+ CurAltStart = (Junction *) ((Junction *)((Junction *)$$.left)->p1); /* MR7 */\r
+ altAdd(CurAltStart); /* MR7 */\r
+ };\r
+ >>\r
+ <<$node = (Node *) ((Junction *)$$.left)->p1;>>\r
+\r
+ )\r
+\r
+/* Error catching alternatives */\r
+ | "\*" <<warn("don't you want a ')' with that '*'?"); CannotContinue=TRUE;>>\r
+ | "\+" <<warn("don't you want a ')' with that '+'?"); CannotContinue=TRUE;>>\r
+ | "\>" <<warn("'>' can only appear after a nonterminal"); CannotContinue=TRUE;>>\r
+ | PassAction <<warn("[...] out of context 'rule > [...]'");\r
+ CannotContinue=TRUE;>>\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/* rule default_exception_handler */\r
+\r
+default_exception_handler\r
+ : exception_group > [DefaultExGroup]\r
+ ;\r
+\r
+/* rule exception_group */\r
+\r
+exception_group > [ExceptionGroup *eg]\r
+ : <<ExceptionHandler *h; LabelEntry *label=NULL; /* MR6 */\r
+ FoundException = 1; FoundExceptionGroup = 1;>> /* MR6 */\r
+\r
+ "exception" <<$eg = (ExceptionGroup *)calloc(1, sizeof(ExceptionGroup));>>\r
+ { <<char *p;>>\r
+ PassAction /* did they attach a label? */\r
+ <<\r
+ p = LATEXT(1)+1;\r
+ p[strlen(p)-1] = '\0'; /* kill trailing space */\r
+ label = (LabelEntry *) hash_get(Elabel, LATEXT(1)+1);\r
+ if ( label==NULL )\r
+ {\r
+ err(eMsg1("unknown label in exception handler: '%s'", LATEXT(1)+1));\r
+ }\r
+ >>\r
+ }\r
+ ( exception_handler > [h]\r
+ <<list_add(&($eg->handlers), (void *)h);>>\r
+ )*\r
+ { "default" ":" Action\r
+ <<{\r
+ ExceptionHandler *eh = (ExceptionHandler *)\r
+ calloc(1, sizeof(ExceptionHandler));\r
+ char *a = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require(eh!=NULL, "exception: cannot allocate handler");\r
+ require(a!=NULL, "exception: cannot allocate action");\r
+ strcpy(a, LATEXT(1));\r
+ eh->action = a;\r
+ eh->signalname = (char *) calloc(strlen("default")+1, sizeof(char));\r
+ require(eh->signalname!=NULL, "exception: cannot allocate sig name");\r
+ strcpy(eh->signalname, "default");\r
+ list_add(&($eg->handlers), (void *)eh);\r
+ }>>\r
+ }\r
+\r
+ <<\r
+ if ( label!=NULL ) {\r
+ /* Record ex group in sym tab for this label */\r
+ if ( label->ex_group!=NULL ) {\r
+ err(eMsg1("duplicate exception handler for label '%s'",label->str));\r
+ } else {\r
+ label->ex_group = $eg;\r
+ /* Label the exception group itself */\r
+ $eg->label = label->str;\r
+ /* Make the labelled element pt to the exception also */\r
+/* MR6 */ if (label->elem == NULL) {\r
+/* MR6 */ err(eMsg1("reference in exception handler to undefined label '%s'",label->str));\r
+/* MR6 */ } else {\r
+ switch ( label->elem->ntype ) {\r
+ case nRuleRef :\r
+ {\r
+ RuleRefNode *r = (RuleRefNode *)label->elem;\r
+ r->ex_group = $eg;\r
+ break;\r
+ }\r
+ case nToken :\r
+ {\r
+ TokNode *t = (TokNode *)label->elem;\r
+ t->ex_group = $eg;\r
+ break;\r
+ }\r
+ } /* end switch */\r
+/* MR6 */ }; /* end test on label->elem */\r
+ } /* end test on label->ex_group */\r
+\r
+ } /* end test on exception label */\r
+\r
+/* MR7 */\r
+/* MR7 */ if (BlkLevel == 1 && label == NULL) {\r
+/* MR7 */ $eg->forRule=1;\r
+/* MR7 */ } else if (label == NULL) {\r
+/* MR7 */ $eg->altID = makeAltID(CurBlockID_array[BlkLevel], CurAltNum_array[BlkLevel]);\r
+/* MR7 */ egAdd($eg);\r
+/* MR7 */ } else {\r
+/* MR7 */ $eg->labelEntry=label;\r
+/* MR7 */ };\r
+/* MR7 */\r
+/* MR7 */ /* You may want to remove this exc from the rule list */\r
+/* MR7 */ /* and handle at the labeled element site. */\r
+/* MR7 */\r
+/* MR7 */ if (label != NULL) {\r
+/* MR7 */ $eg = NULL;\r
+/* MR7 */ };\r
+\r
+ >>\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+/* rule exception_handler */\r
+\r
+exception_handler > [ExceptionHandler *eh]\r
+ : <<;>> /* MR9 Removed unreferenced variable "a" */\r
+ "catch"\r
+ <<\r
+ $eh = (ExceptionHandler *)calloc(1, sizeof(ExceptionHandler));\r
+ require($eh!=NULL, "exception: cannot allocate handler");\r
+ >>\r
+ ( NonTerminal\r
+ <<\r
+ $eh->signalname = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require($eh->signalname!=NULL, "exception: cannot allocate sig name");\r
+ strcpy($eh->signalname, LATEXT(1));\r
+ >>\r
+ | TokenTerm\r
+ <<\r
+ $eh->signalname = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require($eh->signalname!=NULL, "exception: cannot allocate sig name");\r
+ strcpy($eh->signalname, LATEXT(1));\r
+ >>\r
+ )\r
+ ":"\r
+ { <<$eh->action = NULL;>>\r
+ Action\r
+ <<\r
+ $eh->action = (char *) calloc(strlen(LATEXT(1))+1, sizeof(char));\r
+ require($eh->action!=NULL, "exception: cannot allocate action");\r
+ strcpy($eh->action, LATEXT(1));\r
+ >>\r
+ }\r
+ ;\r
+ <<CannotContinue=TRUE;>>\r
+\r
+#token NonTerminal "[a-z] [A-Za-z0-9_]*"\r
+ <<\r
+ while ( zzchar==' ' || zzchar=='\t' ) {\r
+ zzadvance();\r
+ }\r
+ if ( zzchar == ':' && inAlt ) NLA = LABEL;\r
+ >>\r
+#token TokenTerm "[A-Z] [A-Za-z0-9_]*"\r
+ <<\r
+ while ( zzchar==' ' || zzchar=='\t' ) {\r
+ zzadvance();\r
+ }\r
+ if ( zzchar == ':' && inAlt ) NLA = LABEL;\r
+ >>\r
+#token "{\\}#[A-Za-z0-9_]*" <<warn(eMsg1("unknown meta-op: %s",LATEXT(1))); zzskip(); >>\r
+\r
+#lexclass PARSE_ENUM_FILE\r
+\r
+#token "[\t\ ]+" << zzskip(); >> /* Ignore White */\r
+#token "\n|\r|\r\n" << zzline++; zzskip(); >> /* Track Line # */\r
+#token "//" << zzmode(TOK_DEF_CPP_COMMENTS); zzmore(); >>\r
+#token "/\*" << zzmode(TOK_DEF_COMMENTS); zzskip(); >>\r
+#token "#ifdef" << zzmode(TOK_DEF_CPP_COMMENTS); zzskip(); >>\r
+#token "#if" << zzmode(TOK_DEF_CPP_COMMENTS); zzskip(); >>\r
+#token "#ifndef" << ; >>\r
+#token "#else" << zzmode(TOK_DEF_CPP_COMMENTS); zzskip(); >>\r
+#token "#endif" << zzmode(TOK_DEF_CPP_COMMENTS); zzskip(); >>\r
+#token "#undef" << zzmode(TOK_DEF_CPP_COMMENTS); zzskip(); >>\r
+#token "#import" << zzmode(TOK_DEF_CPP_COMMENTS); zzskip(); >>\r
+#token "@" << ; >>\r
+\r
+/* rule enum_file */\r
+\r
+enum_file[char *fname]\r
+ : { "#ifndef" ID\r
+ { "#define" ID /* ignore if it smells like a gate */\r
+ /* First #define after the first #ifndef (if any) is ignored */\r
+ }\r
+ }\r
+ ( ( enum_def[$fname] )+\r
+ | defines[$fname]\r
+ )\r
+ |\r
+ ;\r
+\r
+/* rule defines */\r
+\r
+defines[char *fname]\r
+ : <<int v; int maxt=(-1); char *t;>> /* MR3 */\r
+ (\r
+ "#define" ID\r
+ <<t = mystrdup(LATEXT(1));>>\r
+ INT\r
+ <<\r
+ v = atoi(LATEXT(1));\r
+/* fprintf(stderr, "#token %s=%d\n", t, v);*/\r
+\r
+ /* MR2 Andreas Magnusson (Andreas.Magnusson@mailbox.swipnet.se) */\r
+ /* MR2 Fix to bug introduced by 1.33MR1 for #tokdefs */\r
+ /* MR2 Don't let #tokdefs be confused by */\r
+ /* MR2 DLGminToken and DLGmaxToken */\r
+\r
+ if ( ! isDLGmaxToken(t)) { /* MR2 */\r
+ TokenNum = v;\r
+ if ( v>maxt ) maxt=v;\r
+ if ( Tnum( t ) == 0 ) {\r
+ addForcedTname( t, v );\r
+ } else {\r
+ warnFL(eMsg1("redefinition of token %s; ignored",t),$fname,zzline);\r
+ };\r
+ };\r
+ >>\r
+ )+\r
+ <<TokenNum = maxt + 1;>>\r
+ ;\r
+\r
+/* rule enum_def */\r
+\r
+enum_def[char *fname]\r
+ : <<int v= 0; int maxt=(-1); char *t;>> /* MR3 */\r
+ "enum" ID\r
+ "\{"\r
+ ID\r
+ <<t = mystrdup(LATEXT(1));>>\r
+ ( "=" INT <<v=atoi(LATEXT(1));>>\r
+ | <<v++;>>\r
+ )\r
+ <<\r
+/* fprintf(stderr, "#token %s=%d\n", t, v);*/\r
+ TokenNum = v;\r
+ if ( v>maxt ) maxt=v; /* MR3 */\r
+ if ( Tnum( t ) == 0 ) addForcedTname( t, v );\r
+ else {\r
+ warnFL(eMsg1("redefinition of token %s; ignored",t),$fname,zzline);\r
+ }\r
+ >>\r
+ ( ","\r
+\r
+ /* MR2 Andreas Magnusson (Andreas.Magnusson@mailbox.swipnet.se) */\r
+ /* MR2 Fix to bug introduced by 1.33MR1 for #tokdefs */\r
+ /* MR2 Don't let #tokdefs be confused by */\r
+ /* MR2 DLGminToken and DLGmaxToken */\r
+\r
+ {\r
+ <<isDLGmaxToken(LATEXT(1))>>? ID { "=" INT } /* MR2 */\r
+ | ID /* MR2 */\r
+ <<t = mystrdup(LATEXT(1));>>\r
+ ( "=" INT <<v=atoi(LATEXT(1));>>\r
+ | <<v++;>>\r
+ )\r
+ <<\r
+/* fprintf(stderr, "#token %s=%d\n", t, v);*/\r
+ TokenNum = v;\r
+ if ( v>maxt ) maxt=v; /* MR3 */\r
+ if ( Tnum( t ) == 0 ) addForcedTname( t, v );\r
+ else {\r
+ warnFL(eMsg1("redefinition of token %s; ignored",t),$fname,zzline);\r
+ }\r
+ >>\r
+ }\r
+ )*\r
+ "\}"\r
+ ";"\r
+ <<TokenNum = maxt + 1;>> /* MR3 */\r
+ ;\r
+\r
+#token INT "[0-9]+"\r
+#token ID "[a-zA-Z_][_a-zA-Z0-9]*"\r
+\r
+#lexclass START\r
+\r
+/* MR14 Arpad Beszedes 26-May-98\r
+ Add support for #line directives when antlr source is pre-processed\r
+*/\r
+\r
+#lexaction\r
+<<\r
+\r
+static char *\r
+#ifdef __USE_PROTOS\r
+getFileNameFromTheLineInfo(char *toStr, char *fromStr)\r
+#else\r
+getFileNameFromTheLineInfo(toStr, fromStr)\r
+char *toStr, *fromStr;\r
+#endif\r
+{\r
+ int i, j, k;\r
+\r
+ if (!fromStr || !toStr) return toStr;\r
+\r
+ /* find the first " */\r
+\r
+ for (i=0;\r
+ (i<MaxFileName) &&\r
+ (fromStr[i] != '\n') &&\r
+ (fromStr[i] != '\r') &&\r
+ (fromStr[i] != '\"');\r
+ i++) /* nothing */ ;\r
+\r
+ if ( (i == MaxFileName) ||\r
+ (fromStr[i] == '\n') ||\r
+ (fromStr[i] == '\r') ) {\r
+ return toStr;\r
+ }\r
+\r
+ /* find the second " */\r
+\r
+ for (j=i+1;\r
+ (j<MaxFileName) &&\r
+ (fromStr[j] != '\n') &&\r
+ (fromStr[j] != '\r') &&\r
+ (fromStr[j] != '\"');\r
+ j++) /* nothing */ ;\r
+\r
+ if ((j == MaxFileName) ||\r
+ (fromStr[j] == '\n') ||\r
+ (fromStr[j] == '\r') ) {\r
+ return toStr;\r
+ }\r
+\r
+ /* go back until the last / or \ */\r
+\r
+ for (k=j-1;\r
+ (fromStr[k] != '\"') &&\r
+ (fromStr[k] != '/') &&\r
+ (fromStr[k] != '\\');\r
+ k--) /* nothing */ ;\r
+\r
+ /* copy the string after " / or \ into toStr */\r
+\r
+ for (i=k+1; fromStr[i] != '\"'; i++) {\r
+ toStr[i-k-1] = fromStr[i];\r
+ }\r
+\r
+ toStr[i-k-1] = '\0';\r
+\r
+ return toStr;\r
+}\r
+\r
+/* MR14 end of a block to support #line in antlr source code */\r
+\r
+>>\r
+\r
+<<\r
+\r
+/* MR2 Andreas Magnusson (Andreas.Magnusson@mailbox.swipnet.se) */\r
+/* MR2 Fix to bug introduced by 1.33MR1 for #tokdefs */\r
+/* MR2 Don't let #tokdefs be confused by */\r
+/* MR2 DLGminToken and DLGmaxToken */\r
+\r
+/* semantic check on DLGminToken and DLGmaxmaxToken in #tokdefs */\r
+\r
+#ifdef __USE_PROTOS\r
+static int isDLGmaxToken(char *Token)\r
+#else\r
+static int isDLGmaxToken(Token)\r
+ char * Token;\r
+#endif\r
+{\r
+ static char checkStr1[] = "DLGmaxToken";\r
+ static char checkStr2[] = "DLGminToken";\r
+\r
+ if (strcmp(Token, checkStr1) == 0)\r
+ return 1;\r
+ else if (strcmp(Token, checkStr2) == 0)\r
+ return 1;\r
+ else\r
+ return 0;\r
+}\r
+\r
+/* semantics of #token */\r
+static void\r
+#ifdef __USE_PROTOS\r
+chkToken(char *t, char *e, char *a, int tnum)\r
+#else\r
+chkToken(t,e,a,tnum)\r
+char *t, *e, *a;\r
+int tnum;\r
+#endif\r
+{\r
+ TermEntry *p;\r
+\r
+ /* check to see that they don't try to redefine a token as a token class */\r
+ if ( t!=NULL ) {\r
+ p = (TermEntry *) hash_get(Tname, t);\r
+ if ( p!=NULL && p->classname ) {\r
+ err(eMsg1("redefinition of #tokclass '%s' to #token not allowed; ignored",t));\r
+ if ( a!=NULL ) free((char *)a);\r
+ return;\r
+ }\r
+ }\r
+\r
+ if ( t==NULL && e==NULL ) { /* none found */\r
+ err("#token requires at least token name or rexpr");\r
+ }\r
+ else if ( t!=NULL && e!=NULL ) { /* both found */\r
+ if ( UserDefdTokens ) { /* if #tokdefs, must not define new */\r
+ p = (TermEntry *) hash_get(Tname, t);\r
+ if ( p == NULL) {\r
+err(eMsg1("new token definition '%s' not allowed - only #token with name already defined by #tokdefs file allowed",t));\r
+ return;\r
+ };\r
+ }\r
+ Tklink(t, e);\r
+ if ( a!=NULL ) {\r
+ if ( hasAction(e) ) {\r
+ err(eMsg1("redefinition of action for %s; ignored",e));\r
+ }\r
+ else setHasAction(e, a);\r
+ }\r
+ }\r
+ else if ( t!=NULL ) { /* only one found */\r
+ if ( UserDefdTokens ) {\r
+ p = (TermEntry *) hash_get(Tname, t);\r
+ if (p == NULL) {\r
+err(eMsg1("new token definition '%s' not allowed - only #token with name already defined by #tokdefs file allowed",t));\r
+ };\r
+ return;\r
+ }\r
+ if ( Tnum( t ) == 0 ) addTname( t );\r
+ else {\r
+ err(eMsg1("redefinition of token %s; ignored",t));\r
+ }\r
+ if ( a!=NULL ) {\r
+ err(eMsg1("action cannot be attached to a token name (%s); ignored",t));\r
+ free((char *)a);\r
+ }\r
+ }\r
+ else if ( e!=NULL ) {\r
+ if ( Tnum( e ) == 0 ) addTexpr( e );\r
+ else {\r
+ if ( hasAction(e) ) {\r
+ err(eMsg1("redefinition of action for expr %s; ignored",e));\r
+ }\r
+ else if ( a==NULL ) {\r
+ err(eMsg1("redefinition of expr %s; ignored",e));\r
+ }\r
+ }\r
+ if ( a!=NULL ) setHasAction(e, a);\r
+ }\r
+\r
+ /* if a token type number was specified, then add the token ID and 'tnum'\r
+ * pair to the ForcedTokens list. (only applies if an id was given)\r
+ */\r
+ if ( t!=NULL && tnum>0 )\r
+ {\r
+ if ( set_el(tnum, reserved_positions) )\r
+ {\r
+ err(eMsgd("a token has already been forced to token number %d; ignored", tnum));\r
+ }\r
+ else\r
+ {\r
+ list_add(&ForcedTokens, newForcedToken(t,tnum));\r
+ set_orel(tnum, &reserved_positions);\r
+ }\r
+ }\r
+}\r
+>>\r
+\r
+<<\r
+static int\r
+#ifdef __USE_PROTOS\r
+match_token(char *s, char **nxt)\r
+#else\r
+match_token(s,nxt)\r
+char *s;\r
+char **nxt;\r
+#endif\r
+{\r
+ if ( !(*s>='A' && *s<='Z') ) return 0;\r
+ s++;\r
+ while ( (*s>='a' && *s<='z') ||\r
+ (*s>='A' && *s<='Z') ||\r
+ (*s>='0' && *s<='9') ||\r
+ *s=='_' )\r
+ {\r
+ s++;\r
+ }\r
+ if ( *s!=' ' && *s!='}' ) return 0;\r
+ *nxt = s;\r
+ return 1;\r
+}\r
+\r
+static int\r
+#ifdef __USE_PROTOS\r
+match_rexpr(char *s, char **nxt)\r
+#else\r
+match_rexpr(s,nxt)\r
+char *s;\r
+char **nxt;\r
+#endif\r
+{\r
+ if ( *s!='"' ) return 0;\r
+ s++;\r
+ while ( *s!='"' )\r
+ {\r
+ if ( *s=='\n' || *s=='\r' ) /* MR13 */\r
+ warn("eoln found in regular expression");\r
+ if ( *s=='\\' ) s++;\r
+ s++;\r
+ }\r
+ *nxt = s+1;\r
+ return 1;\r
+}\r
+\r
+/*\r
+ * Walk a string "{ A .. Z }" where A..Z is a space separated list\r
+ * of token references (either labels or reg exprs). Return a\r
+ * string "inlineX_set" for some unique integer X. Basically,\r
+ * we pretend as if we had seen "#tokclass inlineX { A .. Z }"\r
+ * on the input stream outside of an action.\r
+ */\r
+char *\r
+#ifdef __USE_PROTOS\r
+inline_set(char *s)\r
+#else\r
+inline_set(s)\r
+char *s;\r
+#endif\r
+{\r
+ char *nxt;\r
+ fprintf(stderr, "found consumeUntil( {...} )\n");\r
+ while ( *s==' ' || *s=='\t' || *s=='\n' || *s=='\r' ) {s++;}\r
+ if ( *s!='{' )\r
+ {\r
+ err("malformed consumeUntil( {...} ); missing '{'");\r
+ return "bad_set";\r
+ }\r
+ s++;\r
+ while ( *s==' ' || *s=='\t' || *s=='\n' || *s=='\r' ) {s++;}\r
+ while ( *s!='}' )\r
+ {\r
+ if ( match_token(s,&nxt) ) fprintf(stderr, "found token %s\n", s);\r
+ else if ( match_rexpr(s,&nxt) ) fprintf(stderr, "found rexpr %s\n", s);\r
+ else {\r
+ err("invalid element in consumeUntil( {...} )");\r
+ return "bad_set";\r
+ }\r
+ s = nxt;\r
+ while ( *s==' ' || *s=='\t' || *s=='\n' || *s=='\r' ) {s++;}\r
+ }\r
+ return "inlineX_set";\r
+}\r
+>>\r
+\r
+<<\r
+/* ANTLR-specific syntax error message generator\r
+ * (define USER_ZZSYN when compiling so don't get 2 definitions)\r
+ */\r
+void\r
+#ifdef __USE_PROTOS\r
+zzsyn(char *text, int tok, char *egroup, SetWordType *eset, int etok,\r
+int k, char *bad_text)\r
+#else\r
+zzsyn(text, tok, egroup, eset, etok, k, bad_text)\r
+char *text, *egroup, *bad_text;\r
+int tok;\r
+int etok;\r
+int k;\r
+SetWordType *eset;\r
+#endif\r
+{\r
+ fprintf(stderr, ErrHdr, FileStr[CurFile]!=NULL?FileStr[CurFile]:"stdin", zzline);\r
+ fprintf(stderr, " syntax error at \"%s\"", (tok==zzEOF_TOKEN)?"EOF":text);\r
+ if ( !etok && !eset ) {fprintf(stderr, "\n"); return;}\r
+ if ( k==1 ) fprintf(stderr, " missing");\r
+ else\r
+ {\r
+ fprintf(stderr, "; \"%s\" not", bad_text);\r
+ if ( zzset_deg(eset)>1 ) fprintf(stderr, " in");\r
+ }\r
+ if ( zzset_deg(eset)>0 ) zzedecode(eset);\r
+ else fprintf(stderr, " %s", zztokens[etok]);\r
+ if ( strlen(egroup) > (size_t)0 ) fprintf(stderr, " in %s", egroup);\r
+ fprintf(stderr, "\n");\r
+}\r
+>>\r
+\r
+#lexaction <<\r
+#ifdef __USE_PROTOS\r
+void mark_label_used_in_sem_pred(LabelEntry *le) /* MR10 */\r
+#else\r
+void mark_label_used_in_sem_pred(le) /* MR10 */\r
+ LabelEntry *le;\r
+#endif\r
+{\r
+ TokNode *tn;\r
+ require (le->elem->ntype == nToken,"mark_label_used... ntype != nToken");\r
+ tn=(TokNode *)le->elem;\r
+ require (tn->label != 0,"mark_label_used... TokNode has no label");\r
+ tn->label_used_in_semantic_pred=1;\r
+}\r
+>>\r