]> granicus.if.org Git - re2c/commitdiff
- Add support for ':=>' style rules.
authorhelly <helly@642ea486-5414-0410-9d7f-a0204ed87703>
Sun, 20 Jan 2008 11:59:12 +0000 (11:59 +0000)
committerhelly <helly@642ea486-5414-0410-9d7f-a0204ed87703>
Sun, 20 Jan 2008 11:59:12 +0000 (11:59 +0000)
- Fix issue with star rules that use '=>'.

16 files changed:
re2c/CHANGELOG
re2c/actions.cc
re2c/bootstrap/parser.cc
re2c/bootstrap/scanner.cc
re2c/bootstrap/y.tab.h
re2c/code.cc
re2c/htdocs/index.html
re2c/htdocs/manual.html
re2c/parser.y
re2c/scanner.re
re2c/test/condition_11.cg.c
re2c/test/condition_12.cgif.c [new file with mode: 0755]
re2c/test/condition_12.cgif.re [new file with mode: 0755]
re2c/test/condition_13.cg.c [new file with mode: 0755]
re2c/test/condition_13.cg.re [new file with mode: 0755]
re2c/token.h

index 91cfefee319d496943a153aa75ee65d4867639fa..21c3a635cd8e07c2c038a311b185232e1195a089 100644 (file)
@@ -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)
 ---------------------------
index 6a8d675410e1bda20b08cd6e8bb137053af22eeb..40ff33566c46c44080d13f4ac73b3f0820feea71 100644 (file)
@@ -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)
index 5a4590233bd1b897f7f0354d28e5c7a8a894859c..c5f41f2cd20c2fb0dc0b66db804840e28dbc3aeb 100644 (file)
@@ -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" {
index 98ac6ed8b8b0dd69b661bed1b7bfc9e8c74d7951..07cf0f1c2dd0b014978a7cbe0b23bd8f4bbae233 100644 (file)
@@ -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 <stdlib.h>
 #include <string.h>
@@ -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;
 }
 
 }
index f711722bec10ab88772fca946fb7ab9a391a9656..cdafad0e74725fbbd88a00ad2a5bc5340ce901ac 100644 (file)
@@ -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;
index 2fae957c44b07128b342fcb778f0b60151299105..b710013327c064644ddabe6449b188937344c0db 100644 (file)
@@ -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;
 }
index 2df5a5463cf4e06c350454852943e0237e7d3822..762359ca21dd335b41281fdbef3f59a13a1f8cfa 100755 (executable)
@@ -82,6 +82,8 @@ fixes which were incorporated. <a href=
 <h1>Changelog</h1>
 <h2>2007-??-??: 0.13.2</h2>
 <li>Added support for ':=' style rules.</li>
+<li>Add support for ':=>' style rules.</li>
+<li>Fix issue with star rules that use '=>'.</li>
 <ul>
 </ul>
 <h2>2007-08-24: 0.13.1</h2>
index 720d2af1e5e62e319f05cb9a0ff03c3039205899..d02a263b4ab0b67da60ec00d722c4ae7d28dfb2f 100755 (executable)
@@ -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;}
 */
 }
 </pre>
@@ -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 '<b>:=</b>'.
+code can be started with a curly brace of the sequence '<b>:=</b>'. 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 <b>re2c</b> block.
 </p>
 <dl compact="compact">
-<dd>&lt;<i>condition-list</i>&gt; <i>regular-expression</i> =&gt; <i>condition</i> { <i>C/C++ code</i> }</dd>
-<dd>&lt;<i>*</i>&gt; <i>regular-expression</i> =&gt; <i>condition</i> { <i>C/C++ code</i> }</dd>
 <dd>&lt;<i>condition-list</i>&gt; <i>regular-expression</i> { <i>C/C++ code</i> }</dd>
+<dd>&lt;<i>condition-list</i>&gt; <i>regular-expression</i> := <i>C/C++ code</i></dd>
+<dd>&lt;<i>condition-list</i>&gt; <i>regular-expression</i> =&gt; <i>condition</i> { <i>C/C++ code</i> }</dd>
+<dd>&lt;<i>condition-list</i>&gt; <i>regular-expression</i> =&gt; <i>condition</i> := <i>C/C++ code</i></dd>
+<dd>&lt;<i>condition-list</i>&gt; <i>regular-expression</i> :=&gt; <i>condition</i></dd>
 <dd>&lt;<i>*</i>&gt; <i>regular-expression</i> { <i>C/C++ code</i> }</dd>
+<dd>&lt;<i>*</i>&gt; <i>regular-expression</i> := <i>C/C++ code</i></dd>
+<dd>&lt;<i>*</i>&gt; <i>regular-expression</i> =&gt; <i>condition</i> { <i>C/C++ code</i> }</dd>
+<dd>&lt;<i>*</i>&gt; <i>regular-expression</i> =&gt; <i>condition</i> := <i>C/C++ code</i></dd>
+<dd>&lt;<i>*</i>&gt; <i>regular-expression</i> :=&gt; <i>condition</i></dd>
 <dd>&lt;&gt; { <i>C/C++ code</i> }</dd>
+<dd>&lt;&gt; := <i>C/C++ code</i></dd>
+<dd>&lt;&gt; =&gt; <i>condition</i> { <i>C/C++ code</i> }</dd>
+<dd>&lt;&gt; =&gt; <i>condition</i> := <i>C/C++ code</i></dd>
+<dd>&lt;&gt; :=&gt; <i>condition</i></dd>
 </dl>
 <p>Named definitions are of the form:</p>
 <dl compact="compact">
index 20fd467df823a3299074ce30efb05ab63ece82dc..1fe93e0743acb6b50431254a085169a918c39edd 100644 (file)
@@ -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:
index 0e7e86e83c0a66c0582623614eb40cc5f33f03cd..07f6b59993e1a8cad4023d2aa4a00951ce3f2b6a 100644 (file)
@@ -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
                                        {
index 75d18efe0241fe7dbe8f813a175f0ab958284c39..eca563bb26edcda115baf4e51bb53e702eb693ad 100755 (executable)
 /* *********************************** */
 yyc_0:
 
-       YYSETCONDITION(yycr1);
 #line 3 "condition_11.cg.re"
        { return NULL; }
-#line 20 "<stdout>"
+#line 19 "<stdout>"
 /* *********************************** */
 yyc_r1:
        if(YYLIMIT == YYCURSOR) YYFILL(1);
@@ -35,24 +34,24 @@ yy6:
        ++YYCURSOR;
 #line 5 "condition_11.cg.re"
        { return "2"; }
-#line 39 "<stdout>"
+#line 38 "<stdout>"
 yy8:
        ++YYCURSOR;
 #line 4 "condition_11.cg.re"
        { return "1"; }
-#line 44 "<stdout>"
+#line 43 "<stdout>"
 yy10:
        ++YYCURSOR;
        YYSETCONDITION(yycr2);
 #line 6 "condition_11.cg.re"
        { return "a"; }
-#line 50 "<stdout>"
+#line 49 "<stdout>"
 yy12:
        ++YYCURSOR;
        YYSETCONDITION(yycr2);
 #line 7 "condition_11.cg.re"
        { return "b"; }
-#line 56 "<stdout>"
+#line 55 "<stdout>"
 /* *********************************** */
 yyc_r2:
        if(YYLIMIT == YYCURSOR) YYFILL(1);
@@ -69,18 +68,18 @@ yy17:
        ++YYCURSOR;
 #line 5 "condition_11.cg.re"
        { return "2"; }
-#line 73 "<stdout>"
+#line 72 "<stdout>"
 yy19:
        ++YYCURSOR;
 #line 4 "condition_11.cg.re"
        { return "1"; }
-#line 78 "<stdout>"
+#line 77 "<stdout>"
 yy21:
        ++YYCURSOR;
        YYSETCONDITION(yyc);
 #line 7 "condition_11.cg.re"
        { return "b"; }
-#line 84 "<stdout>"
+#line 83 "<stdout>"
 }
 #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 (executable)
index 0000000..c180072
--- /dev/null
@@ -0,0 +1,441 @@
+/* Generated by re2c */
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#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 <file>\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 (executable)
index 0000000..d0715e4
--- /dev/null
@@ -0,0 +1,197 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#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;
+
+<Normal>       "??(" :=
+                       fputc('[', stdout);
+                       continue;
+<Normal>       "??)" :=
+                       fputc(']', stdout);
+                       continue;
+<Normal>       "??<" :=
+                       fputc('{', stdout);
+                       continue;
+<Normal>       "??>" :=
+                       fputc('}', stdout);
+                       continue;
+<Normal>       "??=" :=
+                       fputc('#', stdout);
+                       continue;
+<Normal>       "??/" :=
+                       fputc('\\', stdout);
+                       continue;
+<Normal>       "??'" :=
+                       fputc('^', stdout);
+                       continue;
+<Normal>       "??!" :=
+                       fputc('|', stdout);
+                       continue;
+<Normal>       "??-" :=
+                       fputc('~', stdout);
+                       continue;
+<Normal>       "/*" :=> Comment
+<Normal>       "//" :=> Skiptoeol
+<Normal>       "'\\\"'"|"'\"'" :=
+                       fputl("'\"'", 3, stdout);
+                       continue;
+<Normal>       '"' => String :=
+                       fputc(s->cur[-1], stdout);
+                       continue;
+<Normal>       [^] :=
+                       fputc(s->cur[-1], stdout);
+                       continue;
+<Comment>      "*" "/" :=> Normal
+<Comment>      [^] :=> Comment
+<Skiptoeol>    "??/" "\r"? "\n" :=> Skiptoeol
+<Skiptoeol>    "\\" "\r"? "\n" :=> Skiptoeol
+<Skiptoeol>    "\r" "\n" => Normal :=
+                       fputc('\r', stdout);
+                       fputc('\n', stdout);
+                       continue;
+<Skiptoeol>    "\n" => Normal :=
+                       fputc('\n', stdout);
+                       continue;
+<Skiptoeol>    [^] :=> Skiptoeol
+<String>       '\\' . :=
+                       fputl((const char*)s->cur-2, 2, stdout);
+                       continue;
+<String>       '"' => Normal :=
+                       fputc(s->cur[-1], stdout);
+                       continue;
+<String>       [^] :=
+                       fputc(s->cur[-1], stdout);
+                       continue;
+*/
+       }
+}
+
+int main(int argc, char **argv)
+{
+       Scanner in;
+
+       if (argc != 2)
+       {
+               fprintf(stderr, "%s <file>\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 (executable)
index 0000000..3b3ad1e
--- /dev/null
@@ -0,0 +1,90 @@
+/* Generated by re2c */
+#line 1 "condition_13.cg.re"
+
+#line 5 "<stdout>"
+{
+       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 "<stdout>"
+/* *********************************** */
+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 "<stdout>"
+yy8:
+       ++YYCURSOR;
+       YYSETCONDITION(yycr1);
+#line 4 "condition_13.cg.re"
+       goto yyc_r1;
+#line 46 "<stdout>"
+yy10:
+       ++YYCURSOR;
+       YYSETCONDITION(yycr2);
+#line 6 "condition_13.cg.re"
+       goto yyc_r2;
+#line 52 "<stdout>"
+yy12:
+       ++YYCURSOR;
+       YYSETCONDITION(yycr2);
+#line 7 "condition_13.cg.re"
+       goto yyc_r2;
+#line 58 "<stdout>"
+/* *********************************** */
+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 "<stdout>"
+yy19:
+       ++YYCURSOR;
+       YYSETCONDITION(yycr1);
+#line 4 "condition_13.cg.re"
+       goto yyc_r1;
+#line 82 "<stdout>"
+yy21:
+       ++YYCURSOR;
+       YYSETCONDITION(yyc);
+#line 7 "condition_13.cg.re"
+       goto yyc_;
+#line 88 "<stdout>"
+}
+#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 (executable)
index 0000000..adf043e
--- /dev/null
@@ -0,0 +1,9 @@
+/*!re2c
+
+<>                     :=> r1
+<*>            "1"     :=> r1
+<*>            "2"     :=> r1
+<r1>   "a" :=> r2
+<r1,r2>        "b" :=> r2
+
+*/
index e0e5eae073e3c5c778db19b7ff89d0ddfda81b0a..10f2c1c40c0fe3fef16ede80613338691f05e912 100644 (file)
@@ -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