From: helly Date: Sun, 20 Jan 2008 11:59:12 +0000 (+0000) Subject: - Add support for ':=>' style rules. X-Git-Tag: 0.13.6~112 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=aadfe74b40e28e42afa175d72221ecbb474282a1;p=re2c - Add support for ':=>' style rules. - Fix issue with star rules that use '=>'. --- diff --git a/re2c/CHANGELOG b/re2c/CHANGELOG index 91cfefee..21c3a635 100644 --- a/re2c/CHANGELOG +++ b/re2c/CHANGELOG @@ -1,6 +1,8 @@ Version 0.13.2 (2007-??-??) --------------------------- -- Add support for ':=' style rules +- Add support for ':=' style rules. +- Add support for ':=>' style rules. +- Fix issue with star rules that use '=>'. Version 0.13.1 (2007-08-24) --------------------------- diff --git a/re2c/actions.cc b/re2c/actions.cc index 6a8d6754..40ff3356 100644 --- a/re2c/actions.cc +++ b/re2c/actions.cc @@ -902,7 +902,8 @@ RuleOp::RuleOp(RegExp *e, RegExp *c, Token *t, uint a) RuleOp* RuleOp::copy(uint a) const { - return new RuleOp(exp, ctx, new Token(code->text, code->line), a); + Token *token = new Token(*code); + return new RuleOp(exp, ctx, token, a); } void RuleOp::calcSize(Char *rep) diff --git a/re2c/bootstrap/parser.cc b/re2c/bootstrap/parser.cc index 5a459023..c5f41f2c 100644 --- a/re2c/bootstrap/parser.cc +++ b/re2c/bootstrap/parser.cc @@ -155,6 +155,50 @@ static char* strdup(const char* s) } #endif +void context_check(CondList *clist) +{ + if (!cFlag) + { + delete clist; + in->fatal("conditions are only allowed when using -c switch"); + } +} + +void context_none(CondList *clist) +{ + delete clist; + context_check(NULL); + in->fatal("no expression specified"); +} + +void context_rule(CondList *clist, RegExp *expr, RegExp *look, Str *newcond, Token *code) +{ + context_check(clist); + bool condchange = !newcond || clist->size() > 1 + || clist->find(newcond->to_string()) == clist->end(); + for(CondList::const_iterator it = clist->begin(); it != clist->end(); ++it) + { + Str *condcpy = newcond ? new Str(*newcond) : newcond; + Token *token = new Token(code, in->get_line(), condcpy, condchange); + RuleOp *rule = new RuleOp(expr, look, token, accept++); + + RegExpMap::iterator itRE = specMap.find(*it); + + if (itRE != specMap.end()) + { + itRE->second.second = mkAlt(itRE->second.second, rule); + } + else + { + size_t nIndex = specMap.size() + 1; // 0 is reserved for "0"-spec + specMap[*it] = std::make_pair(nIndex, rule); + } + + } + delete clist; + delete code; +} + /* Enabling traces. */ @@ -177,7 +221,7 @@ static char* strdup(const char* s) #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED typedef union YYSTYPE -#line 63 "parser.y" +#line 107 "parser.y" { re2c::Symbol *symbol; re2c::RegExp *regexp; @@ -189,7 +233,7 @@ typedef union YYSTYPE re2c::CondList *clist; } /* Line 187 of yacc.c. */ -#line 193 "parser.cc" +#line 237 "parser.cc" YYSTYPE; # define yystype YYSTYPE /* obsolescent; will be withdrawn */ # define YYSTYPE_IS_DECLARED 1 @@ -202,7 +246,7 @@ typedef union YYSTYPE /* Line 216 of yacc.c. */ -#line 206 "parser.cc" +#line 250 "parser.cc" #ifdef short # undef short @@ -417,16 +461,16 @@ union yyalloc /* YYFINAL -- State number of the termination state. */ #define YYFINAL 2 /* YYLAST -- Last index in YYTABLE. */ -#define YYLAST 71 +#define YYLAST 89 /* YYNTOKENS -- Number of terminals. */ -#define YYNTOKENS 24 +#define YYNTOKENS 25 /* YYNNTS -- Number of nonterminals. */ #define YYNNTS 14 /* YYNRULES -- Number of rules. */ -#define YYNRULES 39 +#define YYNRULES 44 /* YYNRULES -- Number of states. */ -#define YYNSTATES 71 +#define YYNSTATES 81 /* YYTRANSLATE(YYLEX) -- Bison symbol number corresponding to YYLEX. */ #define YYUNDEFTOK 2 @@ -442,15 +486,15 @@ static const yytype_uint8 yytranslate[] = 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 22, 23, 2, 2, 19, 2, 2, 16, 2, 2, - 2, 2, 2, 2, 2, 2, 2, 2, 2, 15, + 23, 24, 2, 2, 20, 2, 2, 16, 2, 2, + 2, 2, 2, 2, 2, 2, 2, 2, 19, 15, 17, 14, 18, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 21, 2, 2, 2, 2, 2, 2, 2, + 2, 2, 22, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, - 2, 2, 2, 2, 20, 2, 2, 2, 2, 2, + 2, 2, 2, 2, 21, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, @@ -473,37 +517,42 @@ static const yytype_uint8 yytranslate[] = static const yytype_uint8 yyprhs[] = { 0, 0, 3, 4, 7, 10, 15, 20, 25, 30, - 34, 42, 49, 57, 64, 68, 69, 71, 73, 77, - 78, 82, 83, 86, 88, 92, 94, 98, 100, 103, - 105, 108, 111, 113, 115, 118, 121, 123, 125, 127 + 34, 42, 50, 57, 64, 72, 80, 87, 94, 98, + 102, 103, 105, 107, 111, 112, 116, 117, 120, 122, + 126, 128, 132, 134, 137, 139, 142, 145, 147, 149, + 152, 155, 157, 159, 161 }; /* YYRHS -- A `-1'-separated list of the rules' RHS. */ static const yytype_int8 yyrhs[] = { - 25, 0, -1, -1, 25, 27, -1, 25, 26, -1, - 7, 14, 32, 15, -1, 7, 14, 32, 16, -1, + 26, 0, -1, -1, 26, 28, -1, 26, 27, -1, + 7, 14, 33, 15, -1, 7, 14, 33, 16, -1, 11, 14, 12, 15, -1, 11, 14, 13, 15, -1, - 32, 31, 8, -1, 17, 28, 18, 32, 31, 30, - 8, -1, 17, 28, 18, 31, 30, 8, -1, 17, - 5, 18, 32, 31, 30, 8, -1, 17, 5, 18, - 31, 30, 8, -1, 6, 30, 8, -1, -1, 29, - -1, 7, -1, 29, 19, 7, -1, -1, 14, 18, - 7, -1, -1, 16, 32, -1, 33, -1, 32, 20, - 33, -1, 34, -1, 33, 21, 34, -1, 35, -1, - 34, 35, -1, 37, -1, 37, 36, -1, 37, 3, - -1, 4, -1, 5, -1, 36, 4, -1, 36, 5, - -1, 7, -1, 9, -1, 10, -1, 22, 32, 23, - -1 + 33, 32, 8, -1, 17, 29, 18, 33, 32, 31, + 8, -1, 17, 29, 18, 33, 32, 19, 31, -1, + 17, 29, 18, 32, 31, 8, -1, 17, 29, 18, + 32, 19, 31, -1, 17, 5, 18, 33, 32, 31, + 8, -1, 17, 5, 18, 33, 32, 19, 31, -1, + 17, 5, 18, 32, 31, 8, -1, 17, 5, 18, + 32, 19, 31, -1, 6, 31, 8, -1, 6, 19, + 31, -1, -1, 30, -1, 7, -1, 30, 20, 7, + -1, -1, 14, 18, 7, -1, -1, 16, 33, -1, + 34, -1, 33, 21, 34, -1, 35, -1, 34, 22, + 35, -1, 36, -1, 35, 36, -1, 38, -1, 38, + 37, -1, 38, 3, -1, 4, -1, 5, -1, 37, + 4, -1, 37, 5, -1, 7, -1, 9, -1, 10, + -1, 23, 33, 24, -1 }; /* YYRLINE[YYN] -- source line where rule number YYN was defined. */ static const yytype_uint16 yyrline[] = { - 0, 92, 92, 96, 97, 101, 109, 113, 119, 127, - 136, 165, 174, 183, 191, 208, 211, 218, 223, 232, - 235, 243, 246, 253, 257, 264, 268, 279, 283, 290, - 294, 309, 316, 320, 324, 328, 335, 343, 347, 351 + 0, 136, 136, 140, 141, 145, 153, 157, 163, 171, + 180, 184, 189, 193, 198, 204, 211, 215, 220, 230, + 245, 248, 255, 260, 269, 272, 280, 283, 290, 294, + 301, 305, 316, 320, 327, 331, 346, 353, 357, 361, + 365, 372, 380, 384, 388 }; #endif @@ -514,7 +563,7 @@ static const char *const yytname[] = { "$end", "error", "$undefined", "CLOSESIZE", "CLOSE", "STAR", "NOCOND", "ID", "CODE", "RANGE", "STRING", "CONFIG", "VALUE", "NUMBER", "'='", - "';'", "'/'", "'<'", "'>'", "','", "'|'", "'\\\\'", "'('", "')'", + "';'", "'/'", "'<'", "'>'", "':'", "','", "'|'", "'\\\\'", "'('", "')'", "$accept", "spec", "decl", "rule", "cond", "clist", "newcond", "look", "expr", "diff", "term", "factor", "close", "primary", 0 }; @@ -526,27 +575,29 @@ static const char *const yytname[] = static const yytype_uint16 yytoknum[] = { 0, 256, 257, 258, 259, 260, 261, 262, 263, 264, - 265, 266, 267, 268, 61, 59, 47, 60, 62, 44, - 124, 92, 40, 41 + 265, 266, 267, 268, 61, 59, 47, 60, 62, 58, + 44, 124, 92, 40, 41 }; # endif /* YYR1[YYN] -- Symbol number of symbol that rule YYN derives. */ static const yytype_uint8 yyr1[] = { - 0, 24, 25, 25, 25, 26, 26, 26, 26, 27, - 27, 27, 27, 27, 27, 28, 28, 29, 29, 30, - 30, 31, 31, 32, 32, 33, 33, 34, 34, 35, - 35, 35, 36, 36, 36, 36, 37, 37, 37, 37 + 0, 25, 26, 26, 26, 27, 27, 27, 27, 28, + 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, + 29, 29, 30, 30, 31, 31, 32, 32, 33, 33, + 34, 34, 35, 35, 36, 36, 36, 37, 37, 37, + 37, 38, 38, 38, 38 }; /* YYR2[YYN] -- Number of symbols composing right hand side of rule YYN. */ static const yytype_uint8 yyr2[] = { 0, 2, 0, 2, 2, 4, 4, 4, 4, 3, - 7, 6, 7, 6, 3, 0, 1, 1, 3, 0, - 3, 0, 2, 1, 3, 1, 3, 1, 2, 1, - 2, 2, 1, 1, 2, 2, 1, 1, 1, 3 + 7, 7, 6, 6, 7, 7, 6, 6, 3, 3, + 0, 1, 1, 3, 0, 3, 0, 2, 1, 3, + 1, 3, 1, 2, 1, 2, 2, 1, 1, 2, + 2, 1, 1, 1, 3 }; /* YYDEFACT[STATE-NAME] -- Default rule to reduce with in state @@ -554,21 +605,22 @@ static const yytype_uint8 yyr2[] = means the default is an error. */ static const yytype_uint8 yydefact[] = { - 2, 0, 1, 19, 36, 37, 38, 0, 15, 0, - 4, 3, 21, 23, 25, 27, 29, 0, 0, 0, - 0, 0, 17, 0, 16, 36, 0, 0, 0, 0, - 0, 28, 31, 32, 33, 30, 0, 14, 0, 0, - 0, 21, 21, 0, 39, 22, 24, 9, 26, 34, - 35, 20, 5, 6, 7, 8, 19, 21, 19, 21, - 18, 0, 19, 0, 19, 13, 0, 11, 0, 12, + 2, 0, 1, 24, 41, 42, 43, 0, 20, 0, + 4, 3, 26, 28, 30, 32, 34, 0, 24, 0, + 0, 0, 0, 22, 0, 21, 41, 0, 0, 0, + 0, 0, 33, 36, 37, 38, 35, 0, 19, 18, + 0, 0, 0, 26, 26, 0, 44, 27, 29, 9, + 31, 39, 40, 25, 5, 6, 7, 8, 24, 26, + 24, 26, 23, 24, 0, 24, 24, 0, 24, 17, + 16, 24, 0, 13, 12, 24, 0, 15, 14, 11, 10 }; /* YYDEFGOTO[NTERM-NUM]. */ static const yytype_int8 yydefgoto[] = { - -1, 1, 10, 11, 23, 24, 18, 29, 12, 13, - 14, 15, 35, 16 + -1, 1, 10, 11, 24, 25, 19, 30, 12, 13, + 14, 15, 36, 16 }; /* YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing @@ -576,21 +628,22 @@ static const yytype_int8 yydefgoto[] = #define YYPACT_NINF -38 static const yytype_int8 yypact[] = { - -38, 1, -38, -12, -8, -38, -38, -5, 25, 7, - -38, -38, -1, 10, 7, -38, 45, 19, 33, 7, - 39, 37, -38, 38, 26, -38, 5, 7, 7, 50, - 7, -38, -38, -38, -38, 49, 52, -38, 27, 42, - 46, 17, 17, 53, -38, 43, 10, -38, 7, -38, - -38, -38, -38, -38, -38, -38, -12, -1, -12, -1, - -38, 54, -12, 56, -12, -38, 57, -38, 58, -38, + -38, 2, -38, -9, -11, -38, -38, 29, 51, 7, + -38, -38, 10, 33, 7, -38, 57, 34, 49, 60, + 7, 52, 53, -38, 54, 50, -38, 8, 7, 7, + 61, 7, -38, -38, -38, -38, 62, 66, -38, -38, + 20, 59, 63, 11, 11, 68, -38, 55, 33, -38, + 7, -38, -38, -38, -38, -38, -38, -38, 14, 10, + 30, 10, -38, 49, 69, 32, 49, 71, 40, -38, + -38, 49, 72, -38, -38, 49, 73, -38, -38, -38, -38 }; /* YYPGOTO[NTERM-NUM]. */ static const yytype_int8 yypgoto[] = { - -38, -38, -38, -38, -38, -38, -18, -37, -6, 40, - 41, -14, -38, -38 + -38, -38, -38, -38, -38, -38, -18, -37, -5, 56, + 58, -13, -38, -38 }; /* YYTABLE[YYPACT[STATE-NUM]]. What to do in state STATE-NUM. If @@ -600,39 +653,42 @@ static const yytype_int8 yypgoto[] = #define YYTABLE_NINF -1 static const yytype_uint8 yytable[] = { - 31, 2, 17, 26, 56, 58, 19, 3, 4, 20, - 5, 6, 7, 38, 25, 27, 5, 6, 8, 28, - 62, 45, 64, 9, 25, 28, 5, 6, 44, 9, - 21, 30, 22, 27, 31, 57, 59, 36, 61, 9, - 63, 37, 52, 53, 66, 43, 68, 28, 32, 33, - 34, 39, 40, 49, 50, 41, 42, 54, 47, 51, - 60, 55, 65, 28, 67, 69, 70, 0, 46, 0, - 0, 48 + 38, 32, 2, 20, 27, 17, 58, 60, 3, 4, + 18, 5, 6, 7, 26, 40, 5, 6, 26, 8, + 5, 6, 65, 47, 68, 9, 28, 28, 17, 29, + 9, 29, 46, 63, 9, 54, 55, 32, 59, 61, + 64, 29, 67, 21, 17, 69, 17, 72, 73, 66, + 76, 71, 37, 77, 17, 31, 22, 79, 23, 75, + 33, 34, 35, 17, 41, 42, 51, 52, 39, 49, + 45, 43, 44, 53, 56, 62, 29, 70, 57, 74, + 78, 80, 0, 0, 0, 48, 0, 0, 0, 50 }; static const yytype_int8 yycheck[] = { - 14, 0, 14, 9, 41, 42, 14, 6, 7, 14, - 9, 10, 11, 19, 7, 16, 9, 10, 17, 20, - 57, 27, 59, 22, 7, 20, 9, 10, 23, 22, - 5, 21, 7, 16, 48, 41, 42, 18, 56, 22, - 58, 8, 15, 16, 62, 19, 64, 20, 3, 4, - 5, 12, 13, 4, 5, 18, 18, 15, 8, 7, - 7, 15, 8, 20, 8, 8, 8, -1, 28, -1, - -1, 30 + 18, 14, 0, 14, 9, 14, 43, 44, 6, 7, + 19, 9, 10, 11, 7, 20, 9, 10, 7, 17, + 9, 10, 59, 28, 61, 23, 16, 16, 14, 21, + 23, 21, 24, 19, 23, 15, 16, 50, 43, 44, + 58, 21, 60, 14, 14, 63, 14, 65, 66, 19, + 68, 19, 18, 71, 14, 22, 5, 75, 7, 19, + 3, 4, 5, 14, 12, 13, 4, 5, 8, 8, + 20, 18, 18, 7, 15, 7, 21, 8, 15, 8, + 8, 8, -1, -1, -1, 29, -1, -1, -1, 31 }; /* YYSTOS[STATE-NUM] -- The (internal number of the) accessing symbol of state STATE-NUM. */ static const yytype_uint8 yystos[] = { - 0, 25, 0, 6, 7, 9, 10, 11, 17, 22, - 26, 27, 32, 33, 34, 35, 37, 14, 30, 14, - 14, 5, 7, 28, 29, 7, 32, 16, 20, 31, - 21, 35, 3, 4, 5, 36, 18, 8, 32, 12, - 13, 18, 18, 19, 23, 32, 33, 8, 34, 4, - 5, 7, 15, 16, 15, 15, 31, 32, 31, 32, - 7, 30, 31, 30, 31, 8, 30, 8, 30, 8, + 0, 26, 0, 6, 7, 9, 10, 11, 17, 23, + 27, 28, 33, 34, 35, 36, 38, 14, 19, 31, + 14, 14, 5, 7, 29, 30, 7, 33, 16, 21, + 32, 22, 36, 3, 4, 5, 37, 18, 31, 8, + 33, 12, 13, 18, 18, 20, 24, 33, 34, 8, + 35, 4, 5, 7, 15, 16, 15, 15, 32, 33, + 32, 33, 7, 19, 31, 32, 19, 31, 32, 31, + 8, 19, 31, 31, 8, 19, 31, 31, 8, 31, 8 }; @@ -1448,7 +1504,7 @@ yyreduce: switch (yyn) { case 2: -#line 92 "parser.y" +#line 136 "parser.y" { accept = 0; spec = NULL; @@ -1456,7 +1512,7 @@ yyreduce: break; case 5: -#line 102 "parser.y" +#line 146 "parser.y" { if((yyvsp[(1) - (4)].symbol)->re) { @@ -1467,14 +1523,14 @@ yyreduce: break; case 6: -#line 110 "parser.y" +#line 154 "parser.y" { in->fatal("trailing contexts are not allowed in named definitions"); } break; case 7: -#line 114 "parser.y" +#line 158 "parser.y" { in->config(*(yyvsp[(1) - (4)].str), *(yyvsp[(3) - (4)].str)); delete (yyvsp[(1) - (4)].str); @@ -1483,7 +1539,7 @@ yyreduce: break; case 8: -#line 120 "parser.y" +#line 164 "parser.y" { in->config(*(yyvsp[(1) - (4)].str), (yyvsp[(3) - (4)].number)); delete (yyvsp[(1) - (4)].str); @@ -1491,7 +1547,7 @@ yyreduce: break; case 9: -#line 128 "parser.y" +#line 172 "parser.y" { if (cFlag) { @@ -1503,79 +1559,73 @@ yyreduce: break; case 10: -#line 137 "parser.y" +#line 181 "parser.y" { - if (!cFlag) - { - delete (yyvsp[(2) - (7)].clist); - in->fatal("conditions are only allowed when using -c switch"); - } - (yyvsp[(7) - (7)].token)->newcond = (yyvsp[(6) - (7)].str); - for(CondList::const_iterator it = (yyvsp[(2) - (7)].clist)->begin(); it != (yyvsp[(2) - (7)].clist)->end(); ++it) - { - // Duplicating stuff, slow but safe - (yyval.regexp) = new RuleOp((yyvsp[(4) - (7)].regexp), (yyvsp[(5) - (7)].regexp), new Token(*(yyvsp[(7) - (7)].token)), accept++); - - RegExpMap::iterator itRE = specMap.find(*it); - - if (itRE != specMap.end()) - { - itRE->second.second = mkAlt(itRE->second.second, (yyval.regexp)); - } - else - { - size_t nIndex = specMap.size() + 1; // 0 is reserved for "0"-spec - specMap[*it] = std::make_pair(nIndex, (yyval.regexp)); - } - - } - delete (yyvsp[(2) - (7)].clist); - delete (yyvsp[(7) - (7)].token); + context_rule((yyvsp[(2) - (7)].clist), (yyvsp[(4) - (7)].regexp), (yyvsp[(5) - (7)].regexp), (yyvsp[(6) - (7)].str), (yyvsp[(7) - (7)].token)); } break; case 11: -#line 166 "parser.y" +#line 185 "parser.y" { - delete (yyvsp[(2) - (6)].clist); - if (!cFlag) - { - in->fatal("conditions are only allowed when using -c switch"); - } - in->fatal("no expression specified"); + assert((yyvsp[(7) - (7)].str)); + context_rule((yyvsp[(2) - (7)].clist), (yyvsp[(4) - (7)].regexp), (yyvsp[(5) - (7)].regexp), (yyvsp[(7) - (7)].str), NULL); } break; case 12: -#line 175 "parser.y" +#line 190 "parser.y" { - if (!cFlag) - { - in->fatal("conditions are only allowed when using -c switch"); - } - (yyvsp[(7) - (7)].token)->newcond = (yyvsp[(6) - (7)].str); - specStar.push_back(new RuleOp((yyvsp[(4) - (7)].regexp), (yyvsp[(5) - (7)].regexp), (yyvsp[(7) - (7)].token), accept++)); + context_none((yyvsp[(2) - (6)].clist)); } break; case 13: -#line 184 "parser.y" +#line 194 "parser.y" { - if (!cFlag) - { - in->fatal("conditions are only allowed when using -c switch"); - } - in->fatal("no expression specified"); + assert((yyvsp[(6) - (6)].str)); + context_none((yyvsp[(2) - (6)].clist)); } break; case 14: -#line 192 "parser.y" +#line 199 "parser.y" { - if (!cFlag) - { - in->fatal("conditions are only allowed when using -c switch"); - } + context_check(NULL); + (yyvsp[(7) - (7)].token)->newcond = (yyvsp[(6) - (7)].str); + specStar.push_back(new RuleOp((yyvsp[(4) - (7)].regexp), (yyvsp[(5) - (7)].regexp), (yyvsp[(7) - (7)].token), accept++)); + } + break; + + case 15: +#line 205 "parser.y" + { + assert((yyvsp[(7) - (7)].str)); + context_check(NULL); + Token *token = new Token(NULL, in->get_line(), (yyvsp[(7) - (7)].str), true); + specStar.push_back(new RuleOp((yyvsp[(4) - (7)].regexp), (yyvsp[(5) - (7)].regexp), token, accept++)); + } + break; + + case 16: +#line 212 "parser.y" + { + context_none(NULL); + } + break; + + case 17: +#line 216 "parser.y" + { + assert((yyvsp[(6) - (6)].str)); + context_none(NULL); + } + break; + + case 18: +#line 221 "parser.y" + { + context_check(NULL); if (specNone) { in->fatal("code to handle illegal condition already defined"); @@ -1585,87 +1635,101 @@ yyreduce: } break; - case 15: -#line 208 "parser.y" + case 19: +#line 231 "parser.y" + { + assert((yyvsp[(3) - (3)].str)); + context_check(NULL); + if (specNone) + { + in->fatal("code to handle illegal condition already defined"); + } + Token *token = new Token(NULL, in->get_line(), (yyvsp[(3) - (3)].str), true); + (yyval.regexp) = specNone = new RuleOp(new NullOp(), new NullOp(), token, accept++); + } + break; + + case 20: +#line 245 "parser.y" { in->fatal("unnamed condition not supported"); } break; - case 16: -#line 212 "parser.y" + case 21: +#line 249 "parser.y" { (yyval.clist) = (yyvsp[(1) - (1)].clist); } break; - case 17: -#line 219 "parser.y" + case 22: +#line 256 "parser.y" { (yyval.clist) = new CondList(); (yyval.clist)->insert((yyvsp[(1) - (1)].symbol)->GetName().to_string()); } break; - case 18: -#line 224 "parser.y" + case 23: +#line 261 "parser.y" { (yyvsp[(1) - (3)].clist)->insert((yyvsp[(3) - (3)].symbol)->GetName().to_string()); (yyval.clist) = (yyvsp[(1) - (3)].clist); } break; - case 19: -#line 232 "parser.y" + case 24: +#line 269 "parser.y" { (yyval.str) = NULL; } break; - case 20: -#line 236 "parser.y" + case 25: +#line 273 "parser.y" { (yyval.str) = new Str((yyvsp[(3) - (3)].symbol)->GetName().to_string().c_str()); } break; - case 21: -#line 243 "parser.y" + case 26: +#line 280 "parser.y" { (yyval.regexp) = new NullOp; } break; - case 22: -#line 247 "parser.y" + case 27: +#line 284 "parser.y" { (yyval.regexp) = (yyvsp[(2) - (2)].regexp); } break; - case 23: -#line 254 "parser.y" + case 28: +#line 291 "parser.y" { (yyval.regexp) = (yyvsp[(1) - (1)].regexp); } break; - case 24: -#line 258 "parser.y" + case 29: +#line 295 "parser.y" { (yyval.regexp) = mkAlt((yyvsp[(1) - (3)].regexp), (yyvsp[(3) - (3)].regexp)); } break; - case 25: -#line 265 "parser.y" + case 30: +#line 302 "parser.y" { (yyval.regexp) = (yyvsp[(1) - (1)].regexp); } break; - case 26: -#line 269 "parser.y" + case 31: +#line 306 "parser.y" { (yyval.regexp) = mkDiff((yyvsp[(1) - (3)].regexp), (yyvsp[(3) - (3)].regexp)); if(!(yyval.regexp)) @@ -1675,29 +1739,29 @@ yyreduce: } break; - case 27: -#line 280 "parser.y" + case 32: +#line 317 "parser.y" { (yyval.regexp) = (yyvsp[(1) - (1)].regexp); } break; - case 28: -#line 284 "parser.y" + case 33: +#line 321 "parser.y" { (yyval.regexp) = new CatOp((yyvsp[(1) - (2)].regexp), (yyvsp[(2) - (2)].regexp)); } break; - case 29: -#line 291 "parser.y" + case 34: +#line 328 "parser.y" { (yyval.regexp) = (yyvsp[(1) - (1)].regexp); } break; - case 30: -#line 295 "parser.y" + case 35: +#line 332 "parser.y" { switch((yyvsp[(2) - (2)].op)) { @@ -1714,43 +1778,43 @@ yyreduce: } break; - case 31: -#line 310 "parser.y" + case 36: +#line 347 "parser.y" { (yyval.regexp) = new CloseVOp((yyvsp[(1) - (2)].regexp), (yyvsp[(2) - (2)].extop).minsize, (yyvsp[(2) - (2)].extop).maxsize); } break; - case 32: -#line 317 "parser.y" + case 37: +#line 354 "parser.y" { (yyval.op) = (yyvsp[(1) - (1)].op); } break; - case 33: -#line 321 "parser.y" + case 38: +#line 358 "parser.y" { (yyval.op) = (yyvsp[(1) - (1)].op); } break; - case 34: -#line 325 "parser.y" + case 39: +#line 362 "parser.y" { (yyval.op) = ((yyvsp[(1) - (2)].op) == (yyvsp[(2) - (2)].op)) ? (yyvsp[(1) - (2)].op) : '*'; } break; - case 35: -#line 329 "parser.y" + case 40: +#line 366 "parser.y" { (yyval.op) = ((yyvsp[(1) - (2)].op) == (yyvsp[(2) - (2)].op)) ? (yyvsp[(1) - (2)].op) : '*'; } break; - case 36: -#line 336 "parser.y" + case 41: +#line 373 "parser.y" { if(!(yyvsp[(1) - (1)].symbol)->re) { @@ -1760,22 +1824,22 @@ yyreduce: } break; - case 37: -#line 344 "parser.y" + case 42: +#line 381 "parser.y" { (yyval.regexp) = (yyvsp[(1) - (1)].regexp); } break; - case 38: -#line 348 "parser.y" + case 43: +#line 385 "parser.y" { (yyval.regexp) = (yyvsp[(1) - (1)].regexp); } break; - case 39: -#line 352 "parser.y" + case 44: +#line 389 "parser.y" { (yyval.regexp) = (yyvsp[(2) - (3)].regexp); } @@ -1783,7 +1847,7 @@ yyreduce: /* Line 1267 of yacc.c. */ -#line 1787 "parser.cc" +#line 1851 "parser.cc" default: break; } YY_SYMBOL_PRINT ("-> $$ =", yyr1[yyn], &yyval, &yyloc); @@ -1997,7 +2061,7 @@ yyreturn: } -#line 357 "parser.y" +#line 394 "parser.y" extern "C" { diff --git a/re2c/bootstrap/scanner.cc b/re2c/bootstrap/scanner.cc index 98ac6ed8..07cf0f1c 100644 --- a/re2c/bootstrap/scanner.cc +++ b/re2c/bootstrap/scanner.cc @@ -1,4 +1,4 @@ -/* Generated by re2c 0.13.2.dev on Sun Jan 13 18:42:09 2008 */ +/* Generated by re2c 0.13.2.dev on Sat Jan 19 21:52:28 2008 */ /* $Id$ */ #include #include @@ -500,10 +500,10 @@ yy71: yyaccept = 0; yych = *(YYMARKER = ++YYCURSOR); if(yych <= '/') { - if(yych == ',') goto yy152; + if(yych == ',') goto yy154; } else { - if(yych <= '0') goto yy149; - if(yych <= '9') goto yy150; + if(yych <= '0') goto yy151; + if(yych <= '9') goto yy152; } yy72: { @@ -511,6 +511,7 @@ yy72: goto code; } yy73: + YYCTXMARKER = YYCURSOR + 1; ++YYCURSOR; if((yych = *YYCURSOR) == '=') goto yy147; yy74: @@ -686,7 +687,7 @@ yy109: if(yyaccept <= 6) { goto yy112; } else { - goto yy153; + goto yy155; } } } @@ -887,6 +888,7 @@ yy145: } yy147: ++YYCURSOR; + if((yych = *YYCURSOR) == '>') goto yy149; { cur = cursor; tok+= 2; /* skip ":=" */ @@ -894,51 +896,57 @@ yy147: goto code; } yy149: + ++YYCURSOR; + YYCURSOR = YYCTXMARKER; + { + RETURN(*tok); + } +yy151: yych = *++YYCURSOR; - if(yych == ',') goto yy163; - goto yy151; -yy150: + if(yych == ',') goto yy165; + goto yy153; +yy152: ++YYCURSOR; if((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; -yy151: +yy153: if(yybm[0+yych] & 128) { - goto yy150; + goto yy152; } - if(yych == ',') goto yy156; - if(yych == '}') goto yy154; + if(yych == ',') goto yy158; + if(yych == '}') goto yy156; goto yy109; -yy152: +yy154: ++YYCURSOR; -yy153: +yy155: { fatal("illegal closure form, use '{n}', '{n,}', '{n,m}' where n and m are numbers"); } -yy154: +yy156: ++YYCURSOR; { yylval.extop.minsize = atoi((char *)tok+1); yylval.extop.maxsize = atoi((char *)tok+1); RETURN(CLOSESIZE); } -yy156: +yy158: yyaccept = 7; yych = *(YYMARKER = ++YYCURSOR); - if(yych <= '/') goto yy153; - if(yych <= '9') goto yy159; - if(yych != '}') goto yy153; + if(yych <= '/') goto yy155; + if(yych <= '9') goto yy161; + if(yych != '}') goto yy155; ++YYCURSOR; { yylval.extop.minsize = atoi((char *)tok+1); yylval.extop.maxsize = -1; RETURN(CLOSESIZE); } -yy159: +yy161: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; if(yych <= '/') goto yy109; - if(yych <= '9') goto yy159; + if(yych <= '9') goto yy161; if(yych != '}') goto yy109; ++YYCURSOR; { @@ -946,12 +954,12 @@ yy159: yylval.extop.maxsize = MAX(yylval.extop.minsize,atoi(strchr((char *)tok, ',')+1)); RETURN(CLOSESIZE); } -yy163: +yy165: yyaccept = 7; yych = *(YYMARKER = ++YYCURSOR); - if(yych <= '/') goto yy153; - if(yych <= '9') goto yy159; - if(yych != '}') goto yy153; + if(yych <= '/') goto yy155; + if(yych <= '9') goto yy161; + if(yych != '}') goto yy155; ++YYCURSOR; { yylval.op = '*'; @@ -1002,20 +1010,20 @@ code: yych = *YYCURSOR; if(yych <= '&') { if(yych <= 0x0A) { - if(yych <= 0x00) goto yy174; - if(yych <= 0x09) goto yy176; - goto yy172; + if(yych <= 0x00) goto yy176; + if(yych <= 0x09) goto yy178; + goto yy174; } else { - if(yych == '"') goto yy178; - goto yy176; + if(yych == '"') goto yy180; + goto yy178; } } else { if(yych <= '{') { - if(yych <= '\'') goto yy179; - if(yych <= 'z') goto yy176; - goto yy170; + if(yych <= '\'') goto yy181; + if(yych <= 'z') goto yy178; + goto yy172; } else { - if(yych != '}') goto yy176; + if(yych != '}') goto yy178; } } ++YYCURSOR; @@ -1032,7 +1040,7 @@ code: } goto code; } -yy170: +yy172: ++YYCURSOR; { if (depth == 0) @@ -1045,17 +1053,17 @@ yy170: } goto code; } -yy172: +yy174: YYCTXMARKER = YYCURSOR + 1; ++YYCURSOR; if((yych = *YYCURSOR) <= 0x0C) { - if(yych <= 0x08) goto yy173; - if(yych <= 0x0A) goto yy187; + if(yych <= 0x08) goto yy175; + if(yych <= 0x0A) goto yy189; } else { - if(yych <= 0x0D) goto yy187; - if(yych == ' ') goto yy187; + if(yych <= 0x0D) goto yy189; + if(yych == ' ') goto yy189; } -yy173: +yy175: { if (depth == 0) { @@ -1076,7 +1084,7 @@ yy173: cline++; goto code; } -yy174: +yy176: ++YYCURSOR; { if (cursor == eof) @@ -1089,56 +1097,56 @@ yy174: } goto code; } -yy176: +yy178: ++YYCURSOR; -yy177: +yy179: { goto code; } -yy178: +yy180: yych = *(YYMARKER = ++YYCURSOR); - if(yych == 0x0A) goto yy177; - goto yy185; -yy179: + if(yych == 0x0A) goto yy179; + goto yy187; +yy181: yych = *(YYMARKER = ++YYCURSOR); - if(yych == 0x0A) goto yy177; - goto yy181; -yy180: + if(yych == 0x0A) goto yy179; + goto yy183; +yy182: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; -yy181: +yy183: if(yybm[0+yych] & 64) { - goto yy180; + goto yy182; } - if(yych <= '&') goto yy182; - if(yych <= '\'') goto yy176; - goto yy183; -yy182: + if(yych <= '&') goto yy184; + if(yych <= '\'') goto yy178; + goto yy185; +yy184: YYCURSOR = YYMARKER; - goto yy177; -yy183: + goto yy179; +yy185: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; - if(yych == 0x0A) goto yy182; - goto yy180; -yy184: + if(yych == 0x0A) goto yy184; + goto yy182; +yy186: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; -yy185: +yy187: if(yybm[0+yych] & 128) { - goto yy184; + goto yy186; } - if(yych <= '!') goto yy182; - if(yych <= '"') goto yy176; + if(yych <= '!') goto yy184; + if(yych <= '"') goto yy178; ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; - if(yych == 0x0A) goto yy182; - goto yy184; -yy187: + if(yych == 0x0A) goto yy184; + goto yy186; +yy189: ++YYCURSOR; YYCURSOR = YYCTXMARKER; { @@ -1164,17 +1172,17 @@ comment: if((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if(yych <= ')') { - if(yych == 0x0A) goto yy194; - goto yy196; + if(yych == 0x0A) goto yy196; + goto yy198; } else { - if(yych <= '*') goto yy191; - if(yych == '/') goto yy193; - goto yy196; + if(yych <= '*') goto yy193; + if(yych == '/') goto yy195; + goto yy198; } -yy191: +yy193: ++YYCURSOR; - if((yych = *YYCURSOR) == '/') goto yy199; -yy192: + if((yych = *YYCURSOR) == '/') goto yy201; +yy194: { if(cursor == eof) { @@ -1182,11 +1190,11 @@ yy192: } goto comment; } -yy193: +yy195: yych = *++YYCURSOR; - if(yych == '*') goto yy197; - goto yy192; -yy194: + if(yych == '*') goto yy199; + goto yy194; +yy196: ++YYCURSOR; { if(cursor == eof) @@ -1197,17 +1205,17 @@ yy194: cline++; goto comment; } -yy196: +yy198: yych = *++YYCURSOR; - goto yy192; -yy197: + goto yy194; +yy199: ++YYCURSOR; { ++depth; fatal("ambiguous /* found"); goto comment; } -yy199: +yy201: ++YYCURSOR; { if(--depth == 0) @@ -1263,52 +1271,52 @@ config: if((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if(yych <= 0x1F) { - if(yych != 0x09) goto yy207; + if(yych != 0x09) goto yy209; } else { - if(yych <= ' ') goto yy203; - if(yych == '=') goto yy205; - goto yy207; + if(yych <= ' ') goto yy205; + if(yych == '=') goto yy207; + goto yy209; } -yy203: +yy205: ++YYCURSOR; yych = *YYCURSOR; - goto yy212; -yy204: + goto yy214; +yy206: { goto config; } -yy205: +yy207: ++YYCURSOR; yych = *YYCURSOR; - goto yy210; -yy206: + goto yy212; +yy208: { iscfg = 2; cur = cursor; RETURN('='); } -yy207: +yy209: ++YYCURSOR; { fatal("missing '='"); } -yy209: +yy211: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; -yy210: +yy212: if(yybm[0+yych] & 128) { - goto yy209; + goto yy211; } - goto yy206; -yy211: + goto yy208; +yy213: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; -yy212: - if(yych == 0x09) goto yy211; - if(yych == ' ') goto yy211; - goto yy204; +yy214: + if(yych == 0x09) goto yy213; + if(yych == ' ') goto yy213; + goto yy206; } @@ -1354,191 +1362,191 @@ value: yych = *YYCURSOR; if(yych <= '&') { if(yych <= 0x0D) { - if(yych <= 0x08) goto yy221; - if(yych <= 0x0A) goto yy215; - if(yych <= 0x0C) goto yy221; + if(yych <= 0x08) goto yy223; + if(yych <= 0x0A) goto yy217; + if(yych <= 0x0C) goto yy223; } else { if(yych <= ' ') { - if(yych <= 0x1F) goto yy221; + if(yych <= 0x1F) goto yy223; } else { - if(yych == '"') goto yy223; - goto yy221; + if(yych == '"') goto yy225; + goto yy223; } } } else { if(yych <= '/') { - if(yych <= '\'') goto yy225; - if(yych == '-') goto yy218; - goto yy221; + if(yych <= '\'') goto yy227; + if(yych == '-') goto yy220; + goto yy223; } else { if(yych <= '9') { - if(yych <= '0') goto yy216; - goto yy219; + if(yych <= '0') goto yy218; + goto yy221; } else { - if(yych != ';') goto yy221; + if(yych != ';') goto yy223; } } } -yy215: +yy217: { cur = cursor; yylval.str = new Str(token()); iscfg = 0; return VALUE; } -yy216: +yy218: ++YYCURSOR; if(yybm[0+(yych = *YYCURSOR)] & 8) { - goto yy221; + goto yy223; } -yy217: +yy219: { cur = cursor; yylval.number = atoi(token().to_string().c_str()); iscfg = 0; return NUMBER; } -yy218: +yy220: yych = *++YYCURSOR; - if(yych <= '0') goto yy222; - if(yych >= ':') goto yy222; -yy219: + if(yych <= '0') goto yy224; + if(yych >= ':') goto yy224; +yy221: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; if(yybm[0+yych] & 4) { - goto yy219; + goto yy221; } if(yych <= 0x0D) { - if(yych <= 0x08) goto yy221; - if(yych <= 0x0A) goto yy217; - if(yych >= 0x0D) goto yy217; + if(yych <= 0x08) goto yy223; + if(yych <= 0x0A) goto yy219; + if(yych >= 0x0D) goto yy219; } else { if(yych <= ' ') { - if(yych >= ' ') goto yy217; + if(yych >= ' ') goto yy219; } else { - if(yych == ';') goto yy217; + if(yych == ';') goto yy219; } } -yy221: +yy223: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; -yy222: +yy224: if(yybm[0+yych] & 8) { - goto yy221; + goto yy223; } - goto yy215; -yy223: + goto yy217; +yy225: YYMARKER = ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; if(yybm[0+yych] & 16) { - goto yy223; + goto yy225; } if(yych <= '!') { - if(yych == 0x0A) goto yy215; - goto yy233; - } else { - if(yych <= '"') goto yy221; - if(yych <= '[') goto yy233; + if(yych == 0x0A) goto yy217; goto yy235; + } else { + if(yych <= '"') goto yy223; + if(yych <= '[') goto yy235; + goto yy237; } -yy225: +yy227: YYMARKER = ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; if(yybm[0+yych] & 32) { - goto yy225; + goto yy227; } if(yych <= '&') { - if(yych == 0x0A) goto yy215; + if(yych == 0x0A) goto yy217; } else { - if(yych <= '\'') goto yy221; - if(yych >= '\\') goto yy230; + if(yych <= '\'') goto yy223; + if(yych >= '\\') goto yy232; } -yy227: +yy229: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; if(yybm[0+yych] & 64) { - goto yy227; + goto yy229; } - if(yych <= '&') goto yy229; - if(yych <= '\'') goto yy231; - goto yy232; -yy229: + if(yych <= '&') goto yy231; + if(yych <= '\'') goto yy233; + goto yy234; +yy231: YYCURSOR = YYMARKER; - goto yy215; -yy230: + goto yy217; +yy232: YYMARKER = ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; if(yych <= 0x0D) { if(yych <= 0x09) { - if(yych <= 0x08) goto yy225; - goto yy227; + if(yych <= 0x08) goto yy227; + goto yy229; } else { - if(yych <= 0x0A) goto yy215; - if(yych <= 0x0C) goto yy225; - goto yy227; + if(yych <= 0x0A) goto yy217; + if(yych <= 0x0C) goto yy227; + goto yy229; } } else { if(yych <= ' ') { - if(yych <= 0x1F) goto yy225; - goto yy227; + if(yych <= 0x1F) goto yy227; + goto yy229; } else { - if(yych == ';') goto yy227; - goto yy225; + if(yych == ';') goto yy229; + goto yy227; } } -yy231: +yy233: yych = *++YYCURSOR; - goto yy215; -yy232: + goto yy217; +yy234: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; - if(yych == 0x0A) goto yy229; - goto yy227; -yy233: + if(yych == 0x0A) goto yy231; + goto yy229; +yy235: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; if(yybm[0+yych] & 128) { - goto yy233; + goto yy235; } - if(yych <= '!') goto yy229; - if(yych <= '"') goto yy231; - goto yy236; -yy235: + if(yych <= '!') goto yy231; + if(yych <= '"') goto yy233; + goto yy238; +yy237: YYMARKER = ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; if(yych <= 0x0D) { if(yych <= 0x09) { - if(yych <= 0x08) goto yy223; - goto yy233; + if(yych <= 0x08) goto yy225; + goto yy235; } else { - if(yych <= 0x0A) goto yy215; - if(yych <= 0x0C) goto yy223; - goto yy233; + if(yych <= 0x0A) goto yy217; + if(yych <= 0x0C) goto yy225; + goto yy235; } } else { if(yych <= ' ') { - if(yych <= 0x1F) goto yy223; - goto yy233; + if(yych <= 0x1F) goto yy225; + goto yy235; } else { - if(yych == ';') goto yy233; - goto yy223; + if(yych == ';') goto yy235; + goto yy225; } } -yy236: +yy238: ++YYCURSOR; if(YYLIMIT == YYCURSOR) YYFILL(1); yych = *YYCURSOR; - if(yych == 0x0A) goto yy229; - goto yy233; + if(yych == 0x0A) goto yy231; + goto yy235; } } diff --git a/re2c/bootstrap/y.tab.h b/re2c/bootstrap/y.tab.h index f711722b..cdafad0e 100644 --- a/re2c/bootstrap/y.tab.h +++ b/re2c/bootstrap/y.tab.h @@ -70,7 +70,7 @@ #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED typedef union YYSTYPE -#line 63 "parser.y" +#line 107 "parser.y" { re2c::Symbol *symbol; re2c::RegExp *regexp; diff --git a/re2c/code.cc b/re2c/code.cc index 2fae957c..b7100133 100644 --- a/re2c/code.cc +++ b/re2c/code.cc @@ -677,7 +677,7 @@ void Rule::emit(std::ostream &o, uint ind, bool &) const o << indent(ind) << mapCodeName["YYCURSOR"] << " = " << mapCodeName["YYCTXMARKER"] << ";\n"; } - if (rule->code->newcond) + if (rule->code->newcond && rule->code->condchange) { genSetCondition(o, ind, rule->code->newcond->to_string()); } @@ -686,7 +686,16 @@ void Rule::emit(std::ostream &o, uint ind, bool &) const o << file_info(sourceFileInfo, &rl); o << indent(ind); - o << rule->code->text; + if (rule->code->autogen) + { + // TODO: When an empty rule is present, we need to go there. So we need + // an option to generate a 'continue' rather than the 'goto' line. + o << "goto " << condPrefix << rule->code->newcond << ";"; + } + else + { + o << rule->code->text; + } o << "\n"; o << outputFileInfo; } diff --git a/re2c/htdocs/index.html b/re2c/htdocs/index.html index 2df5a546..762359ca 100755 --- a/re2c/htdocs/index.html +++ b/re2c/htdocs/index.html @@ -82,6 +82,8 @@ fixes which were incorporated. Changelog

2007-??-??: 0.13.2

  • Added support for ':=' style rules.
  • +
  • Add support for ':=>' style rules.
  • +
  • Fix issue with star rules that use '=>'.

    2007-08-24: 0.13.1

    diff --git a/re2c/htdocs/manual.html b/re2c/htdocs/manual.html index 720d2af1..d02a263b 100755 --- a/re2c/htdocs/manual.html +++ b/re2c/htdocs/manual.html @@ -35,7 +35,7 @@ char *scan(char *p) re2c:yych:conversion = 1; re2c:indent:top = 1; [0-9]+ {return p;} - [\000-\377] {return (char*)0;} + [^] {return (char*)0;} */ } @@ -308,14 +308,28 @@ special cases. A rule may contain the single condition name '*' and no contition name at all. In the latter case the rule cannot have a regular expression. Non empty rules may further more specify the new condition. In that case re2c will generated the necessary code to chnage the condition automatically. Just as above -code can be started with a curly brace of the sequence ':='. +code can be started with a curly brace of the sequence ':='. Further more +rules can use ':=>' as a shortcut to automatically generate code that not only +sets the new condition state but also continues execution with the new state. A +shortcutrule should not be used in a loop where there is code between the start +of the loop and the re2c block.

    -
    <condition-list> regular-expression => condition { C/C++ code }
    -
    <*> regular-expression => condition { C/C++ code }
    <condition-list> regular-expression { C/C++ code }
    +
    <condition-list> regular-expression := C/C++ code
    +
    <condition-list> regular-expression => condition { C/C++ code }
    +
    <condition-list> regular-expression => condition := C/C++ code
    +
    <condition-list> regular-expression :=> condition
    <*> regular-expression { C/C++ code }
    +
    <*> regular-expression := C/C++ code
    +
    <*> regular-expression => condition { C/C++ code }
    +
    <*> regular-expression => condition := C/C++ code
    +
    <*> regular-expression :=> condition
    <> { C/C++ code }
    +
    <> := C/C++ code
    +
    <> => condition { C/C++ code }
    +
    <> => condition := C/C++ code
    +
    <> :=> condition

    Named definitions are of the form:

    diff --git a/re2c/parser.y b/re2c/parser.y index 20fd467d..1fe93e07 100644 --- a/re2c/parser.y +++ b/re2c/parser.y @@ -56,6 +56,50 @@ static char* strdup(const char* s) } #endif +void context_check(CondList *clist) +{ + if (!cFlag) + { + delete clist; + in->fatal("conditions are only allowed when using -c switch"); + } +} + +void context_none(CondList *clist) +{ + delete clist; + context_check(NULL); + in->fatal("no expression specified"); +} + +void context_rule(CondList *clist, RegExp *expr, RegExp *look, Str *newcond, Token *code) +{ + context_check(clist); + bool condchange = !newcond || clist->size() > 1 + || clist->find(newcond->to_string()) == clist->end(); + for(CondList::const_iterator it = clist->begin(); it != clist->end(); ++it) + { + Str *condcpy = newcond ? new Str(*newcond) : newcond; + Token *token = new Token(code, in->get_line(), condcpy, condchange); + RuleOp *rule = new RuleOp(expr, look, token, accept++); + + RegExpMap::iterator itRE = specMap.find(*it); + + if (itRE != specMap.end()) + { + itRE->second.second = mkAlt(itRE->second.second, rule); + } + else + { + size_t nIndex = specMap.size() + 1; // 0 is reserved for "0"-spec + specMap[*it] = std::make_pair(nIndex, rule); + } + + } + delete clist; + delete code; +} + %} %start spec @@ -135,65 +179,47 @@ rule: } | '<' cond '>' expr look newcond CODE { - if (!cFlag) - { - delete $2; - in->fatal("conditions are only allowed when using -c switch"); - } - $7->newcond = $6; - for(CondList::const_iterator it = $2->begin(); it != $2->end(); ++it) - { - // Duplicating stuff, slow but safe - $$ = new RuleOp($4, $5, new Token(*$7), accept++); - - RegExpMap::iterator itRE = specMap.find(*it); - - if (itRE != specMap.end()) - { - itRE->second.second = mkAlt(itRE->second.second, $$); - } - else - { - size_t nIndex = specMap.size() + 1; // 0 is reserved for "0"-spec - specMap[*it] = std::make_pair(nIndex, $$); - } - - } - delete $2; - delete $7; + context_rule($2, $4, $5, $6, $7); + } + | '<' cond '>' expr look ':' newcond + { + assert($7); + context_rule($2, $4, $5, $7, NULL); } | '<' cond '>' look newcond CODE { - delete $2; - if (!cFlag) - { - in->fatal("conditions are only allowed when using -c switch"); - } - in->fatal("no expression specified"); + context_none($2); + } + | '<' cond '>' look ':' newcond + { + assert($6); + context_none($2); } | '<' STAR '>' expr look newcond CODE { - if (!cFlag) - { - in->fatal("conditions are only allowed when using -c switch"); - } + context_check(NULL); $7->newcond = $6; specStar.push_back(new RuleOp($4, $5, $7, accept++)); } + | '<' STAR '>' expr look ':' newcond + { + assert($7); + context_check(NULL); + Token *token = new Token(NULL, in->get_line(), $7, true); + specStar.push_back(new RuleOp($4, $5, token, accept++)); + } | '<' STAR '>' look newcond CODE { - if (!cFlag) - { - in->fatal("conditions are only allowed when using -c switch"); - } - in->fatal("no expression specified"); + context_none(NULL); + } + | '<' STAR '>' look ':' newcond + { + assert($6); + context_none(NULL); } | NOCOND newcond CODE { - if (!cFlag) - { - in->fatal("conditions are only allowed when using -c switch"); - } + context_check(NULL); if (specNone) { in->fatal("code to handle illegal condition already defined"); @@ -201,6 +227,17 @@ rule: $3->newcond = $2; $$ = specNone = new RuleOp(new NullOp(), new NullOp(), $3, accept++); } + | NOCOND ':' newcond + { + assert($3); + context_check(NULL); + if (specNone) + { + in->fatal("code to handle illegal condition already defined"); + } + Token *token = new Token(NULL, in->get_line(), $3, true); + $$ = specNone = new RuleOp(new NullOp(), new NullOp(), token, accept++); + } ; cond: diff --git a/re2c/scanner.re b/re2c/scanner.re index 0e7e86e8..07f6b599 100644 --- a/re2c/scanner.re +++ b/re2c/scanner.re @@ -248,6 +248,10 @@ scan: goto code; } + ":" / "=>" { + RETURN(*tok); + } + ":=" { cur = cursor; tok+= 2; /* skip ":=" */ @@ -388,7 +392,7 @@ code: "}" { if (depth == 0) { - fatal("Curly braces are not allowed after #:='"); + fatal("Curly braces are not allowed after ':='"); } else if (--depth == 0) { @@ -401,7 +405,7 @@ code: "{" { if (depth == 0) { - fatal("Curly braces are not allowed after #:='"); + fatal("Curly braces are not allowed after ':='"); } else { diff --git a/re2c/test/condition_11.cg.c b/re2c/test/condition_11.cg.c index 75d18efe..eca563bb 100755 --- a/re2c/test/condition_11.cg.c +++ b/re2c/test/condition_11.cg.c @@ -13,10 +13,9 @@ /* *********************************** */ yyc_0: - YYSETCONDITION(yycr1); #line 3 "condition_11.cg.re" { return NULL; } -#line 20 "" +#line 19 "" /* *********************************** */ yyc_r1: if(YYLIMIT == YYCURSOR) YYFILL(1); @@ -35,24 +34,24 @@ yy6: ++YYCURSOR; #line 5 "condition_11.cg.re" { return "2"; } -#line 39 "" +#line 38 "" yy8: ++YYCURSOR; #line 4 "condition_11.cg.re" { return "1"; } -#line 44 "" +#line 43 "" yy10: ++YYCURSOR; YYSETCONDITION(yycr2); #line 6 "condition_11.cg.re" { return "a"; } -#line 50 "" +#line 49 "" yy12: ++YYCURSOR; YYSETCONDITION(yycr2); #line 7 "condition_11.cg.re" { return "b"; } -#line 56 "" +#line 55 "" /* *********************************** */ yyc_r2: if(YYLIMIT == YYCURSOR) YYFILL(1); @@ -69,18 +68,18 @@ yy17: ++YYCURSOR; #line 5 "condition_11.cg.re" { return "2"; } -#line 73 "" +#line 72 "" yy19: ++YYCURSOR; #line 4 "condition_11.cg.re" { return "1"; } -#line 78 "" +#line 77 "" yy21: ++YYCURSOR; YYSETCONDITION(yyc); #line 7 "condition_11.cg.re" { return "b"; } -#line 84 "" +#line 83 "" } #line 9 "condition_11.cg.re" diff --git a/re2c/test/condition_12.cgif.c b/re2c/test/condition_12.cgif.c new file mode 100755 index 00000000..c180072c --- /dev/null +++ b/re2c/test/condition_12.cgif.c @@ -0,0 +1,441 @@ +/* Generated by re2c */ +#include +#include +#include + +#define BSIZE 8192 + + +enum ScanContition { + EStateNormal, + EStateComment, + EStateSkiptoeol, + EStateString, +}; + + +typedef struct Scanner +{ + FILE *fp; + unsigned char *cur, *tok, *lim, *eof; + unsigned char buffer[BSIZE]; + unsigned char yych; + enum ScanContition cond; + int state; +} Scanner; + +size_t fill(Scanner *s, size_t len) +{ + size_t got = ~0, cnt; + + if (!s->eof && s->lim - s->tok < len) + { + if (s->tok > s->buffer) + { + cnt = s->tok - s->buffer; + memcpy(s->buffer, s->tok, s->lim - s->tok); + s->tok -= cnt; + s->cur -= cnt; + s->lim -= cnt; + cnt = &s->buffer[BSIZE] - s->lim; + } + else + { + cnt = BSIZE; + } + if ((got = fread(s->lim, 1, cnt, s->fp)) != cnt) + { + s->eof = &s->lim[got]; + } + s->lim += got; + } + if (s->eof && s->cur + len > s->eof) + { + return ~0; /* not enough input data */ + } + return got; +} + +size_t init(Scanner *s) +{ + s->cur = s->tok = s->lim = s->buffer; + s->eof = 0; + s->cond = EStateNormal; + s->state = -1; + + return fill(s, 0); +} + +void fputl(const char *s, size_t len, FILE *stream) +{ + while(len-- > 0) + { + fputc(*s++, stream); + } +} + +void scan(Scanner *s) +{ + s->tok = s->cur; + + static void *yystable[] = { + &&yyFillLabel0, + &&yyFillLabel1, + &&yyFillLabel2, + &&yyFillLabel3, + }; + + if(s->state < 0) goto yy0; + goto *yystable[s->state]; + for(;;) + { + s->tok = s->cur; + + { + + static void *yyctable[4] = { + &&yyc_Normal, + &&yyc_Comment, + &&yyc_Skiptoeol, + &&yyc_String, + }; +yy0: + goto *yyctable[s->cond]; +/* *********************************** */ +yyc_Comment: + + s->state = 0; + if((s->lim - s->cur) < 2) if(fill(s, 2) == ~0) break; +yyFillLabel0: + s->yych = *s->cur; + if(s->yych != '*') goto yy4; + ++s->cur; + if((s->yych = *s->cur) == '/') goto yy5; +yy3: + goto yyc_Comment; +yy4: + s->yych = *++s->cur; + goto yy3; +yy5: + ++s->cur; + s->cond = EStateNormal; + goto yyc_Normal; +/* *********************************** */ +yyc_Normal: + s->state = 1; + if((s->lim - s->cur) < 4) if(fill(s, 4) == ~0) break; +yyFillLabel1: + s->yych = *s->cur; + { + static void *yytarget[256] = { + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy13, &&yy15, &&yy15, &&yy15, &&yy15, &&yy12, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy11, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy9, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, + &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15, &&yy15 + }; + goto *yytarget[s->yych]; + } +yy9: + s->yych = *(s->tok = ++s->cur); + if(s->yych == '?') goto yy26; +yy10: + fputc(s->cur[-1], stdout); + continue; +yy11: + s->yych = *++s->cur; + if(s->yych == '*') goto yy24; + if(s->yych == '/') goto yy22; + goto yy10; +yy12: + s->yych = *(s->tok = ++s->cur); + if(s->yych == '"') goto yy16; + if(s->yych == '\\') goto yy18; + goto yy10; +yy13: + ++s->cur; + s->cond = EStateString; + fputc(s->cur[-1], stdout); + continue; +yy15: + s->yych = *++s->cur; + goto yy10; +yy16: + s->yych = *++s->cur; + if(s->yych == '\'') goto yy20; +yy17: + s->cur = s->tok; + goto yy10; +yy18: + s->yych = *++s->cur; + if(s->yych != '"') goto yy17; + s->yych = *++s->cur; + if(s->yych != '\'') goto yy17; +yy20: + ++s->cur; + fputl("'\"'", 3, stdout); + continue; +yy22: + ++s->cur; + s->cond = EStateSkiptoeol; + goto yyc_Skiptoeol; +yy24: + ++s->cur; + s->cond = EStateComment; + goto yyc_Comment; +yy26: + s->yych = *++s->cur; + { + static void *yytarget[256] = { + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy41, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy39, + &&yy27, &&yy29, &&yy17, &&yy17, &&yy17, &&yy43, &&yy17, &&yy37, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy31, &&yy35, &&yy33, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, + &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17, &&yy17 + }; + goto *yytarget[s->yych]; + } +yy27: + ++s->cur; + fputc('[', stdout); + continue; +yy29: + ++s->cur; + fputc(']', stdout); + continue; +yy31: + ++s->cur; + fputc('{', stdout); + continue; +yy33: + ++s->cur; + fputc('}', stdout); + continue; +yy35: + ++s->cur; + fputc('#', stdout); + continue; +yy37: + ++s->cur; + fputc('\\', stdout); + continue; +yy39: + ++s->cur; + fputc('^', stdout); + continue; +yy41: + ++s->cur; + fputc('|', stdout); + continue; +yy43: + ++s->cur; + fputc('~', stdout); + continue; +/* *********************************** */ +yyc_Skiptoeol: + s->state = 2; + if((s->lim - s->cur) < 5) if(fill(s, 5) == ~0) break; +yyFillLabel2: + s->yych = *s->cur; + { + static void *yytarget[256] = { + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy51, &&yy53, &&yy53, &&yy50, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy47, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy49, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, + &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53, &&yy53 + }; + goto *yytarget[s->yych]; + } +yy47: + s->yych = *(s->tok = ++s->cur); + if(s->yych == '?') goto yy60; +yy48: + goto yyc_Skiptoeol; +yy49: + s->yych = *(s->tok = ++s->cur); + if(s->yych == 0x0A) goto yy58; + if(s->yych == 0x0D) goto yy56; + goto yy48; +yy50: + s->yych = *++s->cur; + if(s->yych == 0x0A) goto yy54; + goto yy48; +yy51: + ++s->cur; + s->cond = EStateNormal; + fputc('\n', stdout); + continue; +yy53: + s->yych = *++s->cur; + goto yy48; +yy54: + ++s->cur; + s->cond = EStateNormal; + fputc('\r', stdout); + fputc('\n', stdout); + continue; +yy56: + s->yych = *++s->cur; + if(s->yych == 0x0A) goto yy58; +yy57: + s->cur = s->tok; + goto yy48; +yy58: + ++s->cur; + goto yyc_Skiptoeol; +yy60: + s->yych = *++s->cur; + if(s->yych != '/') goto yy57; + s->yych = *++s->cur; + if(s->yych == 0x0A) goto yy63; + if(s->yych != 0x0D) goto yy57; + s->yych = *++s->cur; + if(s->yych != 0x0A) goto yy57; +yy63: + ++s->cur; + goto yyc_Skiptoeol; +/* *********************************** */ +yyc_String: + s->state = 3; + if((s->lim - s->cur) < 2) if(fill(s, 2) == ~0) break; +yyFillLabel3: + s->yych = *s->cur; + if(s->yych == '"') goto yy69; + if(s->yych != '\\') goto yy71; + ++s->cur; + if((s->yych = *s->cur) != 0x0A) goto yy72; +yy68: + fputc(s->cur[-1], stdout); + continue; +yy69: + ++s->cur; + s->cond = EStateNormal; + fputc(s->cur[-1], stdout); + continue; +yy71: + s->yych = *++s->cur; + goto yy68; +yy72: + ++s->cur; + fputl((const char*)s->cur-2, 2, stdout); + continue; + } + + } +} + +int main(int argc, char **argv) +{ + Scanner in; + + if (argc != 2) + { + fprintf(stderr, "%s \n", argv[0]); + return 1;; + } + + memset((char*) &in, 0, sizeof(in)); + + if (!strcmp(argv[1], "-")) + { + in.fp = stdin; + } + else if ((in.fp = fopen(argv[1], "r")) == NULL) + { + fprintf(stderr, "Cannot open file '%s'\n", argv[1]); + return 1; + } + + if (init(&in) > 0) + { + scan(&in); + } + + if (in.fp != stdin) + { + fclose(in.fp); + } + return 0; +} diff --git a/re2c/test/condition_12.cgif.re b/re2c/test/condition_12.cgif.re new file mode 100755 index 00000000..d0715e40 --- /dev/null +++ b/re2c/test/condition_12.cgif.re @@ -0,0 +1,197 @@ +#include +#include +#include + +#define BSIZE 8192 + +/*!types:re2c */ + +typedef struct Scanner +{ + FILE *fp; + unsigned char *cur, *tok, *lim, *eof; + unsigned char buffer[BSIZE]; + unsigned char yych; + enum ScanContition cond; + int state; +} Scanner; + +size_t fill(Scanner *s, size_t len) +{ + size_t got = ~0, cnt; + + if (!s->eof && s->lim - s->tok < len) + { + if (s->tok > s->buffer) + { + cnt = s->tok - s->buffer; + memcpy(s->buffer, s->tok, s->lim - s->tok); + s->tok -= cnt; + s->cur -= cnt; + s->lim -= cnt; + cnt = &s->buffer[BSIZE] - s->lim; + } + else + { + cnt = BSIZE; + } + if ((got = fread(s->lim, 1, cnt, s->fp)) != cnt) + { + s->eof = &s->lim[got]; + } + s->lim += got; + } + if (s->eof && s->cur + len > s->eof) + { + return ~0; /* not enough input data */ + } + return got; +} + +size_t init(Scanner *s) +{ + s->cur = s->tok = s->lim = s->buffer; + s->eof = 0; + s->cond = EStateNormal; + s->state = -1; + + return fill(s, 0); +} + +void fputl(const char *s, size_t len, FILE *stream) +{ + while(len-- > 0) + { + fputc(*s++, stream); + } +} + +void scan(Scanner *s) +{ + s->tok = s->cur; +/*!re2c +re2c:define:YYGETSTATE = "s->state"; +re2c:define:YYGETSTATE:naked = 1; +re2c:define:YYCONDTYPE = ScanContition; +re2c:indent:top = 1; +*/ +/*!getstate:re2c */ + for(;;) + { + s->tok = s->cur; +/*!re2c + +re2c:define:YYCTYPE = "unsigned char"; +re2c:define:YYCURSOR = s->cur; +re2c:define:YYLIMIT = s->lim; +re2c:define:YYMARKER = s->tok; +re2c:define:YYFILL@len = #; +re2c:define:YYFILL:naked = 1; +re2c:define:YYFILL = "if(fill(s, #) == ~0) break;"; +re2c:define:YYSETSTATE@state = #; +re2c:define:YYSETSTATE = "s->state = #;"; +re2c:define:YYSETCONDITION = "s->cond = #;"; +re2c:define:YYSETCONDITION@cond = #; +re2c:define:YYGETCONDITION = s->cond; +re2c:define:YYGETCONDITION:naked = 1; +re2c:variable:yych = s->yych; +re2c:yych:emit = 0; +re2c:indent:top = 2; +re2c:condenumprefix = EState; + + "??(" := + fputc('[', stdout); + continue; + "??)" := + fputc(']', stdout); + continue; + "??<" := + fputc('{', stdout); + continue; + "??>" := + fputc('}', stdout); + continue; + "??=" := + fputc('#', stdout); + continue; + "??/" := + fputc('\\', stdout); + continue; + "??'" := + fputc('^', stdout); + continue; + "??!" := + fputc('|', stdout); + continue; + "??-" := + fputc('~', stdout); + continue; + "/*" :=> Comment + "//" :=> Skiptoeol + "'\\\"'"|"'\"'" := + fputl("'\"'", 3, stdout); + continue; + '"' => String := + fputc(s->cur[-1], stdout); + continue; + [^] := + fputc(s->cur[-1], stdout); + continue; + "*" "/" :=> Normal + [^] :=> Comment + "??/" "\r"? "\n" :=> Skiptoeol + "\\" "\r"? "\n" :=> Skiptoeol + "\r" "\n" => Normal := + fputc('\r', stdout); + fputc('\n', stdout); + continue; + "\n" => Normal := + fputc('\n', stdout); + continue; + [^] :=> Skiptoeol + '\\' . := + fputl((const char*)s->cur-2, 2, stdout); + continue; + '"' => Normal := + fputc(s->cur[-1], stdout); + continue; + [^] := + fputc(s->cur[-1], stdout); + continue; +*/ + } +} + +int main(int argc, char **argv) +{ + Scanner in; + + if (argc != 2) + { + fprintf(stderr, "%s \n", argv[0]); + return 1;; + } + + memset((char*) &in, 0, sizeof(in)); + + if (!strcmp(argv[1], "-")) + { + in.fp = stdin; + } + else if ((in.fp = fopen(argv[1], "r")) == NULL) + { + fprintf(stderr, "Cannot open file '%s'\n", argv[1]); + return 1; + } + + if (init(&in) > 0) + { + scan(&in); + } + + if (in.fp != stdin) + { + fclose(in.fp); + } + return 0; +} diff --git a/re2c/test/condition_13.cg.c b/re2c/test/condition_13.cg.c new file mode 100755 index 00000000..3b3ad1ee --- /dev/null +++ b/re2c/test/condition_13.cg.c @@ -0,0 +1,90 @@ +/* Generated by re2c */ +#line 1 "condition_13.cg.re" + +#line 5 "" +{ + YYCTYPE yych; + static void *yyctable[3] = { + &&yyc_0, + &&yyc_r1, + &&yyc_r2, + }; + goto *yyctable[YYGETCONDITION()]; +/* *********************************** */ +yyc_0: + + YYSETCONDITION(yycr1); +#line 3 "condition_13.cg.re" + goto yyc_r1; +#line 20 "" +/* *********************************** */ +yyc_r1: + if(YYLIMIT == YYCURSOR) YYFILL(1); + yych = *YYCURSOR; + if(yych <= '2') { + if(yych <= '0') goto yy5; + if(yych <= '1') goto yy8; + goto yy6; + } else { + if(yych <= '`') goto yy5; + if(yych <= 'a') goto yy10; + if(yych <= 'b') goto yy12; + } +yy5: +yy6: + ++YYCURSOR; + YYSETCONDITION(yycr1); +#line 5 "condition_13.cg.re" + goto yyc_r1; +#line 40 "" +yy8: + ++YYCURSOR; + YYSETCONDITION(yycr1); +#line 4 "condition_13.cg.re" + goto yyc_r1; +#line 46 "" +yy10: + ++YYCURSOR; + YYSETCONDITION(yycr2); +#line 6 "condition_13.cg.re" + goto yyc_r2; +#line 52 "" +yy12: + ++YYCURSOR; + YYSETCONDITION(yycr2); +#line 7 "condition_13.cg.re" + goto yyc_r2; +#line 58 "" +/* *********************************** */ +yyc_r2: + if(YYLIMIT == YYCURSOR) YYFILL(1); + yych = *YYCURSOR; + if(yych <= '2') { + if(yych <= '0') goto yy16; + if(yych <= '1') goto yy19; + goto yy17; + } else { + if(yych == 'b') goto yy21; + } +yy16: +yy17: + ++YYCURSOR; + YYSETCONDITION(yycr1); +#line 5 "condition_13.cg.re" + goto yyc_r1; +#line 76 "" +yy19: + ++YYCURSOR; + YYSETCONDITION(yycr1); +#line 4 "condition_13.cg.re" + goto yyc_r1; +#line 82 "" +yy21: + ++YYCURSOR; + YYSETCONDITION(yyc); +#line 7 "condition_13.cg.re" + goto yyc_; +#line 88 "" +} +#line 9 "condition_13.cg.re" + diff --git a/re2c/test/condition_13.cg.re b/re2c/test/condition_13.cg.re new file mode 100755 index 00000000..adf043e8 --- /dev/null +++ b/re2c/test/condition_13.cg.re @@ -0,0 +1,9 @@ +/*!re2c + +<> :=> r1 +<*> "1" :=> r1 +<*> "2" :=> r1 + "a" :=> r2 + "b" :=> r2 + +*/ diff --git a/re2c/token.h b/re2c/token.h index e0e5eae0..10f2c1c4 100644 --- a/re2c/token.h +++ b/re2c/token.h @@ -10,17 +10,35 @@ namespace re2c class Token { public: - Str text; - Str* newcond; - uint line; + const Str text; + const Str* newcond; + const uint line; + const bool autogen; + const bool condchange; public: Token(const SubStr&, uint); + Token(const Token*, uint, Str*, bool); Token(const Token& oth); ~Token(); }; -inline Token::Token(const SubStr& t, uint l) : text(t), newcond(NULL), line(l) +inline Token::Token(const SubStr& t, uint l) + : text(t) + , newcond(NULL) + , line(l) + , autogen(false) + , condchange(false) +{ + ; +} + +inline Token::Token(const Token* t, uint l, Str *c, bool chg) + : text(t ? t->text.to_string().c_str() : "") + , newcond(c) + , line(t ? t->line : l) + , autogen(t == NULL) + , condchange(chg) { ; } @@ -29,16 +47,15 @@ inline Token::Token(const Token& oth) : text(oth.text.to_string().c_str()) , newcond(oth.newcond ? new Str(*oth.newcond) : NULL) , line(oth.line) + , autogen(oth.autogen) + , condchange(oth.autogen) { ; } inline Token::~Token() { - if (newcond) - { - delete newcond; - } + delete newcond; } } // end namespace re2c