src/ir/dfa/find_state.h \
src/ir/dfa/tagpool.h \
src/ir/nfa/nfa.h \
+ src/ir/re/re.h \
src/ir/regexp/encoding/case.h \
src/ir/regexp/encoding/enc.h \
src/ir/regexp/encoding/range_suffix.h \
src/conf/msg.cc \
src/conf/opt.cc \
src/conf/warn.cc \
- src/ir/nfa/counters.cc \
src/ir/nfa/dump.cc \
- src/ir/nfa/init_rules.cc \
- src/ir/nfa/nfa.cc \
- src/ir/nfa/regexps2nfa.cc \
+ src/ir/nfa/estimate_size.cc \
+ src/ir/nfa/re_to_nfa.cc \
+ src/ir/re/ast_to_re.cc \
+ src/ir/re/default_tags.cc \
+ src/ir/re/fixed_tags.cc \
src/ir/adfa/adfa.cc \
src/ir/adfa/dump.cc \
src/ir/adfa/prepare.cc \
-/* Generated by re2c 0.16 on Mon Feb 13 14:29:09 2017 */
+/* Generated by re2c 0.16 on Sat Feb 25 16:26:09 2017 */
#line 1 "../src/parse/lex.re"
#include "src/util/c99_stdint.h"
#include <stddef.h>
0, 199, 199, 201, 202, 203, 207, 214, 219, 222,
226, 226, 229, 233, 237, 244, 251, 258, 263, 265,
271, 278, 279, 285, 291, 298, 299, 304, 308, 315,
- 319, 326, 330, 337, 341, 358, 377, 378, 382, 383,
- 384, 388, 397, 401
+ 319, 326, 330, 337, 338, 344, 349, 350, 354, 355,
+ 356, 360, 369, 373
};
#endif
break;
- case 33:
-
- {
- (yyval.regexp) = (yyvsp[0].regexp);
- }
-
- break;
-
case 34:
{
- // see note [Kleene star is expressed in terms of plus]
- switch((yyvsp[0].op))
- {
- case '*':
- (yyval.regexp) = RegExp::make_alt(RegExp::make_iter((yyvsp[-1].regexp)),
- RegExp::make_nil());
- break;
- case '+':
- (yyval.regexp) = RegExp::make_iter((yyvsp[-1].regexp));
- break;
- case '?':
- (yyval.regexp) = mkAlt((yyvsp[-1].regexp), RegExp::make_nil());
- break;
- }
+ switch((yyvsp[0].op)) {
+ case '*': (yyval.regexp) = RegExp::make_iter((yyvsp[-1].regexp), 0, RegExp::MANY); break;
+ case '+': (yyval.regexp) = RegExp::make_iter((yyvsp[-1].regexp), 1, RegExp::MANY); break;
+ case '?': (yyval.regexp) = RegExp::make_iter((yyvsp[-1].regexp), 0, 1); break;
}
+ }
break;
case 35:
{
- if ((yyvsp[0].extop).max == std::numeric_limits<uint32_t>::max())
- {
- (yyval.regexp) = repeat_from ((yyvsp[-1].regexp), (yyvsp[0].extop).min);
- }
- else if ((yyvsp[0].extop).min == (yyvsp[0].extop).max)
- {
- (yyval.regexp) = repeat ((yyvsp[-1].regexp), (yyvsp[0].extop).min);
- }
- else
- {
- (yyval.regexp) = repeat_from_to ((yyvsp[-1].regexp), (yyvsp[0].extop).min, (yyvsp[0].extop).max);
- }
- (yyval.regexp) = (yyval.regexp) ? (yyval.regexp) : RegExp::make_nil();
- }
+ (yyval.regexp) = RegExp::make_iter((yyvsp[-1].regexp), (yyvsp[0].extop).min, (yyvsp[0].extop).max);
+ }
break;
cs.push_back(*i);
}
- nfa_t nfa(rules, opts->input_api);
+ RESpec re(rules);
+ find_fixed_tags(re, opts);
+ insert_default_tags(re);
+
+ nfa_t nfa(re);
if (opts->dump_nfa) dump_nfa(nfa);
dfa_t dfa(nfa, cs, opts, cond, warn);
const std::vector<Tag> &tags, const std::valarray<Rule> &rules,
const std::string &cond, Warn &warn)
{
- const size_t ntag = tags.size();
- for (size_t t = 0; t < ntag; ++t) {
- const size_t m = nondet[t];
- if (m > 1) {
- const Tag &tag = tags[t];
- const uint32_t line = rules[tag.rule].code->fline;
- warn.nondeterministic_tags(line, cond, tag.name, m);
+ const size_t nrule = rules.size();
+ for (size_t r = 0; r < nrule; ++r) {
+ const Rule &rule = rules[r];
+ for (size_t t = rule.ltag; t < rule.htag; ++t) {
+ const size_t m = nondet[t];
+ if (m > 1) {
+ const Tag &tag = tags[t];
+ const uint32_t line = rule.code->fline;
+ warn.nondeterministic_tags(line, cond, tag.name, m);
+ }
}
}
}
+++ /dev/null
-#include "src/ir/nfa/nfa.h"
-
-namespace re2c {
-
-static size_t count(const RegExp *re, size_t &ntags)
-{
- switch (re->type) {
- case RegExp::NIL:
- return 0;
- case RegExp::SYM:
- return 1;
- case RegExp::ALT: {
- const size_t n = ntags;
- return count(re->alt.re1, ntags)
- + count(re->alt.re2, ntags)
- + 1 /* alternative */
- + (ntags - n + 1); /* default tags */
- }
- case RegExp::CAT:
- return count(re->cat.re1, ntags)
- + count(re->cat.re2, ntags);
- case RegExp::ITER:
- return count(re->iter, ntags)
- + 1;
- case RegExp::TAG:
- ++ntags;
- return 1;
- default:
- assert(false);
- }
-}
-
-size_t counters(const std::vector<RegExpRule> ®exps, size_t &ntags)
-{
- const size_t nregexps = regexps.size();
- size_t size = nregexps - 1;
- for (size_t i = 0; i < nregexps; ++i) {
- size += count(regexps[i].re, ntags) + 1;
- }
- return size;
-}
-
-} // namespace re2c
--- /dev/null
+#include "src/ir/nfa/nfa.h"
+
+namespace re2c {
+
+static size_t estimate(const RE *re)
+{
+ switch (re->type) {
+ default: assert(false);
+ case RE::NIL: return 0;
+ case RE::SYM: return 1;
+ case RE::TAG: return 1;
+ case RE::ALT:
+ return estimate(re->alt.re1)
+ + estimate(re->alt.re2)
+ + 1;
+ case RE::CAT:
+ return estimate(re->cat.re1)
+ + estimate(re->cat.re2);
+ case RE::ITER:
+ return estimate(re->iter)
+ + 1;
+ case RE::REPEAT:
+ return estimate(re->repeat.re) * (re->repeat.upto + 1)
+ + re->repeat.upto;
+ }
+}
+
+size_t estimate_size(const std::vector<RE*> &res)
+{
+ const size_t nre = res.size();
+ size_t size = nre - 1;
+ for (size_t i = 0; i < nre; ++i) {
+ size += estimate(res[i]) + 1;
+ }
+ return size;
+}
+
+} // namespace re2c
+++ /dev/null
-#include <stdlib.h>
-
-#include "src/conf/msg.h"
-#include "src/ir/nfa/nfa.h"
-
-namespace re2c {
-
-static void assert_tags_used_once(const Rule &rule,
- const std::vector<Tag> &tags)
-{
- std::set<std::string> names;
- const std::string *name = NULL;
-
- for (size_t t = rule.ltag; t < rule.htag; ++t) {
- name = tags[t].name;
- if (name && !names.insert(*name).second) {
- error("line %u: tag '%s' is used multiple times in the same rule",
- rule.code->fline, name->c_str());
- exit(1);
- }
- }
-}
-
-void init_rules(const std::vector<RegExpRule> ®exps,
- std::valarray<Rule> &rules, const std::vector<Tag> &tags)
-{
- const size_t
- nr = rules.size(),
- nt = tags.size();
-
- for (size_t r = 0, t = 0; r < nr; ++r) {
- Rule &rule = rules[r];
- rule.code = regexps[r].code;
-
- rule.ltag = t;
- for (; t < nt && tags[t].rule == r; ++t);
- rule.htag = t;
-
- rule.ttag = rule.htag;
- if (rule.ltag < rule.ttag && tags[rule.ttag - 1].name == NULL) --rule.ttag;
-
- assert_tags_used_once(rule, tags);
- }
-}
-
-} // namespace re2c
+++ /dev/null
-#include "src/ir/nfa/nfa.h"
-
-namespace re2c {
-
-nfa_t::nfa_t(const std::vector<RegExpRule> ®exps, input_api_t input)
- : max_size(0)
- , size(0)
- , states(NULL)
- , rules(*new std::valarray<Rule>(regexps.size()))
- , tags(*new std::vector<Tag>())
- , root(NULL)
-{
- size_t ntags = 0;
- max_size = counters(regexps, ntags);
-
- states = new nfa_state_t[max_size];
- regexps2nfa(regexps, *this, input);
-
- init_rules(regexps, rules, tags);
-}
-
-nfa_t::~nfa_t()
-{
- delete[] states;
-}
-
-} // namespace re2c
#include <vector>
#include "src/codegen/input_api.h"
+#include "src/ir/re/re.h"
#include "src/ir/regexp/regexp.h"
#include "src/ir/rule.h"
#include "src/ir/tag.h"
std::vector<Tag> &tags;
nfa_state_t *root;
- nfa_t(const std::vector<RegExpRule> &rs, input_api_t input);
+ nfa_t(const RESpec &spec);
~nfa_t();
FORBID_COPY(nfa_t);
};
-size_t counters(const std::vector<RegExpRule> ®exps, size_t &ntags);
-void regexps2nfa(const std::vector<RegExpRule> ®exps, nfa_t &nfa, input_api_t input);
-bool nullable_rule(const RegExpRule &rule);
-void init_rules(const std::vector<RegExpRule> ®exps, std::valarray<Rule> &rules,
- const std::vector<Tag> &tags);
+size_t estimate_size(const std::vector<RE*> &res);
void dump_nfa(const nfa_t &nfa);
} // namespace re2c
--- /dev/null
+#include "src/ir/nfa/nfa.h"
+
+namespace re2c {
+
+static nfa_state_t *re_to_nfa(nfa_t &nfa, size_t nrule, const RE *re, nfa_state_t *t)
+{
+ nfa_state_t *s = NULL;
+ switch (re->type) {
+ case RE::NIL:
+ s = t;
+ break;
+ case RE::SYM:
+ s = &nfa.states[nfa.size++];
+ s->make_ran(nrule, t, re->sym);
+ break;
+ case RE::ALT: {
+ nfa_state_t
+ *s1 = re_to_nfa(nfa, nrule, re->alt.re1, t),
+ *s2 = re_to_nfa(nfa, nrule, re->alt.re2, t);
+ s = &nfa.states[nfa.size++];
+ s->make_alt(nrule, s1, s2);
+ break;
+ }
+ case RE::CAT:
+ s = re_to_nfa(nfa, nrule, re->cat.re2, t);
+ s = re_to_nfa(nfa, nrule, re->cat.re1, s);
+ break;
+ case RE::ITER: {
+ // see note [Kleene star is expressed in terms of plus]
+ nfa_state_t *q = &nfa.states[nfa.size++];
+ s = re_to_nfa(nfa, nrule, re->iter, q);
+ q->make_alt(nrule, s, t);
+ break;
+ }
+ case RE::REPEAT:
+ s = re_to_nfa(nfa, nrule, re->repeat.re, t);
+ for (uint32_t i = 0; i < re->repeat.upto; ++i) {
+ nfa_state_t *q = &nfa.states[nfa.size++];
+ q->make_alt(nrule, s, t);
+ s = re_to_nfa(nfa, nrule, re->repeat.re, q);
+ }
+ break;
+ case RE::TAG:
+ if (fixed(nfa.tags[re->tag.idx])) {
+ s = t;
+ } else {
+ s = &nfa.states[nfa.size++];
+ s->make_tag(nrule, t, re->tag.idx, re->tag.bottom);
+ }
+ break;
+ }
+ return s;
+}
+
+nfa_t::nfa_t(const RESpec &spec)
+ : max_size(estimate_size(spec.res))
+ , size(0)
+ , states(new nfa_state_t[max_size])
+ , rules(spec.rules)
+ , tags(spec.tags)
+ , root(NULL)
+{
+ const size_t nre = spec.res.size();
+
+ if (nre == 0) return;
+
+ for (size_t i = 0; i < nre; ++i) {
+ nfa_state_t *s = &states[size++];
+ s->make_fin(i);
+ s = re_to_nfa(*this, i, spec.res[i], s);
+
+ if (root) {
+ nfa_state_t *t = &states[size++];
+ t->make_alt(i, root, s);
+ root = t;
+ } else {
+ root = s;
+ }
+ }
+}
+
+nfa_t::~nfa_t()
+{
+ delete[] states;
+}
+
+} // namespace re2c
+++ /dev/null
-#include <limits>
-
-#include "src/ir/nfa/nfa.h"
-
-namespace re2c {
-
-/* note [fixed and variable tags]
- *
- * If distance between two tags is constant (equal for all strings that
- * match the given regexp), then lexer only needs to track one of them:
- * the second tag equals the first tag plus static offset.
- *
- * However, this optimization is applied only to tags in top-level
- * concatenation, because other tags may be uninitialized and we don't
- * want to mess with conditional calculation of fixed tags.
- *
- * Furthermore, fixed tags are fobidden with generic API because it cannot
- * express fixed offsets.
- */
-
-// We have to insert default tags during NFA construction: before it,
-// we have AST and which is immutable (it may be shared by different
-// regexps); after it, we have NFA where join points of alternatives
-// are lost.
-// We also compute fixed / variable tags during NFA construction, because
-// the order of regexp traversal determines the order in which tags are
-// assigned indices. Splitting this in two passes would require maintaining
-// exactly the same order of traversal, which is fragile.
-static nfa_state_t *regexp2nfa(nfa_t &nfa, size_t nrule, size_t &dist,
- size_t &base, bool toplevel, const RegExp *re, nfa_state_t *t)
-{
- nfa_state_t *s = NULL;
- switch (re->type) {
- case RegExp::NIL:
- s = t;
- break;
- case RegExp::SYM:
- s = &nfa.states[nfa.size++];
- s->make_ran(nrule, t, re->sym);
-
- if (dist != Tag::VARDIST) ++dist;
- break;
- case RegExp::ALT: {
- nfa_state_t *s1, *s2, *t0, *t1, *t2, *q;
- size_t d1 = dist, d2 = dist, i = nfa.tags.size();
-
- t0 = &nfa.states[nfa.size++];
- s1 = regexp2nfa(nfa, nrule, d1, base, false, re->alt.re1, t0);
- for (t2 = t; i < nfa.tags.size(); ++i) {
- q = &nfa.states[nfa.size++];
- q->make_tag(nrule, t2, i, true);
- t2 = q;
- }
-
- s2 = regexp2nfa(nfa, nrule, d2, base, false, re->alt.re2, t2);
- for (t1 = t; i < nfa.tags.size(); ++i) {
- q = &nfa.states[nfa.size++];
- q->make_tag(nrule, t1, i, true);
- t1 = q;
- }
- t0->make_nil(nrule, t1);
-
- s = &nfa.states[nfa.size++];
- s->make_alt(nrule, s1, s2);
-
- dist = (d1 == d2) ? d1 : Tag::VARDIST;
- break;
- }
- case RegExp::CAT:
- s = regexp2nfa(nfa, nrule, dist, base, toplevel, re->cat.re2, t);
- s = regexp2nfa(nfa, nrule, dist, base, toplevel, re->cat.re1, s);
- break;
- case RegExp::ITER: {
- // see note [Kleene star is expressed in terms of plus]
- nfa_state_t *q = &nfa.states[nfa.size++];
- s = regexp2nfa(nfa, nrule, dist, base, false, re->iter, q);
- q->make_alt(nrule, s, t);
-
- dist = Tag::VARDIST;
- break;
- }
- case RegExp::TAG: {
- const std::string *name = re->tag;
- if (toplevel && dist != Tag::VARDIST) {
- Tag fix = {name, nrule, base, dist};
- nfa.tags.push_back(fix);
- s = t;
- } else {
- const size_t ntag = nfa.tags.size();
- Tag var = {name, nrule, ntag, Tag::VARDIST};
- nfa.tags.push_back(var);
- if (toplevel) {
- base = ntag;
- dist = 0;
- }
- s = &nfa.states[nfa.size++];
- s->make_tag(nrule, t, ntag, false);
- }
- if (name == NULL) dist = 0;
- break;
- }
- }
- return s;
-}
-
-static nfa_state_t *regexp2nfa_rule(nfa_t &nfa, size_t nrule,
- const RegExp *re, input_api_t input)
-{
- const bool generic = input == INPUT_CUSTOM;
- size_t base = Tag::RIGHTMOST, dist = 0;
-
- nfa_state_t *s = &nfa.states[nfa.size++];
- s->make_fin(nrule);
-
- return regexp2nfa(nfa, nrule, dist, base, !generic, re, s);
-}
-
-void regexps2nfa(const std::vector<RegExpRule> ®exps,
- nfa_t &nfa, input_api_t input)
-{
- const size_t nregexps = regexps.size();
-
- if (nregexps == 0) {
- return;
- }
-
- nfa_state_t *s = regexp2nfa_rule(nfa, 0, regexps[0].re, input);
- for (size_t i = 1; i < nregexps; ++i) {
- nfa_state_t *t = &nfa.states[nfa.size++];
- t->make_alt(i, s, regexp2nfa_rule(nfa, i, regexps[i].re, input));
- s = t;
- }
- nfa.root = s;
-}
-
-} // namespace re2c
--- /dev/null
+#include "src/conf/msg.h"
+#include "src/ir/re/re.h"
+
+namespace re2c {
+
+/* note [Kleene star is expressed in terms of plus]
+ *
+ * In literature Kleene star 'r*' (zero or more repetitions of 'r')
+ * is the basic operation. In practice it is more convenient to use
+ * 'r+' (one or more repetitions of 'r'), because expansion 'r+ ::= r r*'
+ * duplicates 'r', while expansion 'r* = r+ | <empty>' allows to
+ * avoid duplication. This is more efficient in general and crucial
+ * in cases when duplication of 'r' is forbidden (e.g. if 'r' has tags).
+ */
+
+/*
+ * note [counted repetition expansion]
+ *
+ * r{0} ;;= <empty regexp>
+ * r{n} ::= r{n-1} r
+ * r{n,m} ::= r{n} (r{0} | ... | r{m-n})
+ * r{n,} ::= r{n} r*
+ */
+
+static RE *ast_to_re(RESpec &spec, const RegExp *ast)
+{
+ RE::alc_t &alc = spec.alc;
+ switch (ast->type) {
+ default: assert(false);
+ case RegExp::NIL:
+ return re_nil(alc);
+ case RegExp::SYM:
+ return re_sym(alc, ast->sym);
+ case RegExp::ALT: {
+ RE *x = ast_to_re(spec, ast->alt.re1);
+ RE *y = ast_to_re(spec, ast->alt.re2);
+ return re_alt(alc, x, y);
+ }
+ case RegExp::CAT: {
+ RE *x = ast_to_re(spec, ast->cat.re1);
+ RE *y = ast_to_re(spec, ast->cat.re2);
+ return re_cat(alc, x, y);
+ }
+ case RegExp::TAG: {
+ const size_t ntag = spec.tags.size();
+ Tag tag = {ast->tag, ntag, Tag::VARDIST};
+ spec.tags.push_back(tag);
+ return re_tag(alc, ntag, false);
+ }
+ case RegExp::ITER: {
+ const uint32_t
+ n = ast->iter.min,
+ m = ast->iter.max;
+ const RegExp *x = ast->iter.re;
+
+ if (n == 0 && m == 0) {
+ return re_nil(alc);
+ }
+
+ RE *y = ast_to_re(spec, x);
+ if (m == RegExp::MANY) {
+ y = re_iter(alc, y);
+ } else if (n == 0) {
+ y = re_repeat(alc, y, m - 1);
+ } else if (m > n) {
+ y = re_repeat(alc, y, m - n);
+ }
+ if (n == 0) {
+ y = re_alt(alc, y, re_nil(alc));
+ } else {
+ for (uint32_t i = 1; i < n; ++i) {
+ y = re_cat(alc, ast_to_re(spec, x), y);
+ }
+ }
+ return y;
+ }
+ }
+}
+
+static void assert_tags_used_once(const Rule &rule, const std::vector<Tag> &tags)
+{
+ std::set<std::string> names;
+ const std::string *name = NULL;
+
+ for (size_t t = rule.ltag; t < rule.htag; ++t) {
+ name = tags[t].name;
+ if (name && !names.insert(*name).second) {
+ error("line %u: tag '%s' is used multiple times in the same rule",
+ rule.code->fline, name->c_str());
+ exit(1);
+ }
+ }
+}
+
+static void init_rule(Rule &rule, const Code *code, const std::vector<Tag> &tags, size_t ltag)
+{
+ rule.code = code;
+ rule.ltag = ltag;
+ rule.htag = tags.size();
+ for (rule.ttag = ltag; rule.ttag < rule.htag && tags[rule.ttag].name; ++rule.ttag);
+ assert_tags_used_once(rule, tags);
+}
+
+RESpec::RESpec(const std::vector<RegExpRule> &ast)
+ : alc()
+ , res()
+ , tags(*new std::vector<Tag>)
+ , rules(*new std::valarray<Rule>(ast.size()))
+{
+ for (size_t i = 0, t; i < ast.size(); ++i) {
+ t = tags.size();
+ res.push_back(ast_to_re(*this, ast[i].re));
+ init_rule(rules[i], ast[i].code, tags, t);
+ }
+}
+
+} // namespace re2c
--- /dev/null
+#include "src/ir/re/re.h"
+
+namespace re2c {
+
+static void insert_default_tags(RESpec &spec, RE *re, size_t &tidx)
+{
+ RE::alc_t &alc = spec.alc;
+ switch (re->type) {
+ case RE::NIL: break;
+ case RE::SYM: break;
+ case RE::ALT: {
+ size_t i = tidx;
+ RE *x = re_nil(alc), *y = re_nil(alc);
+ insert_default_tags(spec, re->alt.re1, tidx);
+ for (; i < tidx; ++i) {
+ x = re_cat(alc, x, re_tag(alc, i, true));
+ }
+ insert_default_tags(spec, re->alt.re2, tidx);
+ for (; i < tidx; ++i) {
+ y = re_cat(alc, y, re_tag(alc, i, true));
+ }
+ re->alt.re1 = re_cat(alc, re->alt.re1, y);
+ re->alt.re2 = re_cat(alc, re->alt.re2, x);
+ break;
+ }
+ case RE::CAT:
+ insert_default_tags(spec, re->cat.re1, tidx);
+ insert_default_tags(spec, re->cat.re2, tidx);
+ break;
+ case RE::ITER:
+ insert_default_tags(spec, re->iter, tidx);
+ break;
+ case RE::REPEAT:
+ insert_default_tags(spec, re->repeat.re, tidx);
+ break;
+ case RE::TAG:
+ assert(re->tag.idx == tidx);
+ ++tidx;
+ break;
+ }
+}
+
+void insert_default_tags(RESpec &spec)
+{
+ size_t tidx = 0;
+ std::vector<RE*>::iterator
+ i = spec.res.begin(),
+ e = spec.res.end();
+ for (; i != e; ++i) {
+ insert_default_tags(spec, *i, tidx);
+ }
+}
+
+} // namespace re2c
--- /dev/null
+#include "src/ir/re/re.h"
+
+namespace re2c {
+
+/* note [fixed and variable tags]
+ *
+ * If distance between two tags is constant (equal for all strings that
+ * match the given regexp), then lexer only needs to track one of them:
+ * the second tag equals the first tag plus static offset.
+ *
+ * However, this optimization is applied only to tags in top-level
+ * concatenation, because other tags may be uninitialized and we don't
+ * want to mess with conditional calculation of fixed tags.
+ *
+ * Furthermore, fixed tags are fobidden with generic API because it cannot
+ * express fixed offsets.
+ */
+
+static void find_fixed_tags(RE *re, std::vector<Tag> &tags,
+ size_t &dist, size_t &base, bool toplevel)
+{
+ switch (re->type) {
+ case RE::NIL: break;
+ case RE::SYM:
+ if (dist != Tag::VARDIST) ++dist;
+ break;
+ case RE::ALT: {
+ size_t d1 = dist, d2 = dist;
+ find_fixed_tags(re->alt.re1, tags, d1, base, false);
+ find_fixed_tags(re->alt.re2, tags, d2, base, false);
+ dist = (d1 == d2) ? d1 : Tag::VARDIST;
+ break;
+ }
+ case RE::CAT:
+ find_fixed_tags(re->cat.re2, tags, dist, base, toplevel);
+ find_fixed_tags(re->cat.re1, tags, dist, base, toplevel);
+ break;
+ case RE::ITER:
+ find_fixed_tags(re->iter, tags, dist, base, false);
+ dist = Tag::VARDIST;
+ break;
+ case RE::REPEAT:
+ find_fixed_tags(re->repeat.re, tags, dist, base, false);
+ dist = Tag::VARDIST;
+ break;
+ case RE::TAG:
+ if (toplevel && dist != Tag::VARDIST) {
+ Tag &tag = tags[re->tag.idx];
+ tag.base = base;
+ tag.dist = dist;
+ } else {
+ if (toplevel) {
+ base = re->tag.idx;
+ dist = 0;
+ }
+ }
+ if (tags[re->tag.idx].name == NULL) dist = 0;
+ break;
+ }
+}
+
+void find_fixed_tags(RESpec &spec, const opt_t *opts)
+{
+ const bool generic = opts->input_api == INPUT_CUSTOM;
+ std::vector<RE*>::iterator
+ i = spec.res.begin(),
+ e = spec.res.end();
+ for (; i != e; ++i) {
+ size_t base = Tag::RIGHTMOST, dist = 0;
+ find_fixed_tags(*i, spec.tags, dist, base, !generic);
+ }
+}
+
+} // namespace re2c
--- /dev/null
+#ifndef _RE2C_IR_RE_RE_
+#define _RE2C_IR_RE_RE_
+
+#include "src/util/c99_stdint.h"
+
+#include "src/conf/opt.h"
+#include "src/ir/rule.h"
+#include "src/ir/regexp/regexp.h"
+#include "src/util/range.h"
+#include "src/util/slab_allocator.h"
+
+namespace re2c
+{
+
+struct RE
+{
+ typedef slab_allocator_t<~0u, 4096> alc_t;
+ enum type_t {NIL, SYM, ALT, CAT, ITER, REPEAT, TAG} type;
+ union {
+ const Range *sym;
+ struct {
+ RE *re1;
+ RE *re2;
+ } alt;
+ struct {
+ RE *re1;
+ RE *re2;
+ } cat;
+ RE *iter;
+ struct {
+ RE *re;
+ uint32_t upto;
+ } repeat;
+ struct {
+ size_t idx;
+ bool bottom;
+ } tag;
+ };
+};
+
+struct RESpec
+{
+ RE::alc_t alc;
+ std::vector<RE*> res;
+ std::vector<Tag> &tags;
+ std::valarray<Rule> &rules;
+
+ explicit RESpec(const std::vector<RegExpRule> &ast);
+};
+
+void find_fixed_tags(RESpec &spec, const opt_t *opts);
+void insert_default_tags(RESpec &spec);
+
+inline RE *re_nil(RE::alc_t &alc)
+{
+ RE *x = alc.alloct<RE>(1);
+ x->type = RE::NIL;
+ return x;
+}
+
+inline RE *re_sym(RE::alc_t &alc, const Range *r)
+{
+ RE *x = alc.alloct<RE>(1);
+ x->type = RE::SYM;
+ x->sym = r;
+ return x;
+}
+
+inline RE *re_alt(RE::alc_t &alc, RE *x, RE *y)
+{
+ RE *z = alc.alloct<RE>(1);
+ z->type = RE::ALT;
+ z->alt.re1 = x;
+ z->alt.re2 = y;
+ return z;
+}
+
+inline RE *re_cat(RE::alc_t &alc, RE *x, RE *y)
+{
+ RE *z = alc.alloct<RE>(1);
+ z->type = RE::CAT;
+ z->cat.re1 = x;
+ z->cat.re2 = y;
+ return z;
+}
+
+inline RE *re_iter(RE::alc_t &alc, RE *x)
+{
+ RE *y = alc.alloct<RE>(1);
+ y->type = RE::ITER;
+ y->iter = x;
+ return y;
+}
+
+inline RE *re_repeat(RE::alc_t &alc, RE *x, uint32_t n)
+{
+ RE *y = alc.alloct<RE>(1);
+ y->type = RE::REPEAT;
+ y->repeat.re = x;
+ y->repeat.upto = n;
+ return y;
+}
+
+inline RE *re_tag(RE::alc_t &alc, size_t i, bool b)
+{
+ RE *x = alc.alloct<RE>(1);
+ x->type = RE::TAG;
+ x->tag.idx = i;
+ x->tag.bottom = b;
+ return x;
+}
+
+} // namespace re2c
+
+#endif // _RE2C_IR_RE_RE_
switch (re->type) {
default: assert(false);
case RegExp::NIL: return true;
- case RegExp::SYM:
- case RegExp::ITER: return false;
+ case RegExp::SYM: return false;
+ case RegExp::ITER:
+ return re->iter.min == 0
+ || nullable(re->iter.re, trail);
case RegExp::TAG:
if (re->tag == NULL) {
trail = true;
free_list<RegExp*> RegExp::flist;
+const uint32_t RegExp::MANY = std::numeric_limits<uint32_t>::max();
+
const RegExp *doAlt(const RegExp *re1, const RegExp *re2)
{
if (!re1) {
opts->encoding.nCodeUnits()));
}
-/*
- * note [counted repetition expansion]
- *
- * r{0} ;;= <empty regexp>
- * r{n} ::= r{n-1} r
- * r{n,m} ::= r{n} (r{0} | ... | r{m-n})
- * r{n,} ::= r{n} r*
- */
-
-// see note [counted repetition expansion]
-const RegExp *repeat(const RegExp *re, uint32_t n)
-{
- const RegExp *r = NULL;
- for (uint32_t i = 0; i < n; ++i) {
- r = doCat(r, re);
- }
- return r;
-}
-
-// see note [counted repetition expansion]
-const RegExp *repeat_from_to(const RegExp *re, uint32_t n, uint32_t m)
-{
- const RegExp *r1 = repeat(re, n);
- const RegExp *r2 = NULL;
- for (uint32_t i = n; i < m; ++i) {
- r2 = mkAlt(doCat(re, r2), RegExp::make_nil());
- }
- return doCat(r1, r2);
-}
-
-// see note [counted repetition expansion]
-const RegExp *repeat_from(const RegExp *re, uint32_t n)
-{
- // see note [Kleene star is expressed in terms of plus]
- return doCat(repeat(re, n),
- RegExp::make_alt(RegExp::make_iter(re), RegExp::make_nil()));
-}
-
} // namespace re2c
struct RegExp
{
static free_list<RegExp*> flist;
- static const size_t NO_TAG;
+ static const uint32_t MANY;
enum type_t {NIL, SYM, ALT, CAT, ITER, TAG} type;
union
const RegExp *re1;
const RegExp *re2;
} cat;
- const RegExp *iter;
+ struct
+ {
+ const RegExp *re;
+ uint32_t min;
+ uint32_t max;
+ } iter;
const std::string *tag;
};
re->cat.re2 = r2;
return re;
}
- static const RegExp *make_iter(const RegExp *r)
+ static const RegExp *make_iter(const RegExp *r, uint32_t n, uint32_t m)
{
RegExp *re = new RegExp(ITER);
- re->iter = r;
+ re->iter.re = r;
+ re->iter.min = n;
+ re->iter.max = m;
return re;
}
static const RegExp *make_tag(const std::string *t)
const RegExp *mkAlt(const RegExp *re1, const RegExp *re2);
const RegExp *doAlt(const RegExp *re1, const RegExp *re2);
const RegExp *doCat(const RegExp *re1, const RegExp *re2);
-const RegExp *repeat(const RegExp *re, uint32_t n);
-const RegExp *repeat_from_to(const RegExp *re, uint32_t n, uint32_t m);
-const RegExp *repeat_from(const RegExp *re, uint32_t n);
void warn_nullable(const std::vector<RegExpRule> ®exps,
const std::string &cond, Warn &warn);
split(re->cat.re2, cs);
break;
case RegExp::ITER:
- split(re->iter, cs);
+ split(re->iter.re, cs);
break;
}
}
static const size_t VARDIST;
const std::string *name;
- size_t rule;
size_t base;
size_t dist;
};
}
;
-factor:
- primary
- {
- $$ = $1;
- }
- | primary closes
- {
- // see note [Kleene star is expressed in terms of plus]
- switch($2)
- {
- case '*':
- $$ = RegExp::make_alt(RegExp::make_iter($1),
- RegExp::make_nil());
- break;
- case '+':
- $$ = RegExp::make_iter($1);
- break;
- case '?':
- $$ = mkAlt($1, RegExp::make_nil());
- break;
- }
- }
- | primary TOKEN_CLOSESIZE
- {
- if ($2.max == std::numeric_limits<uint32_t>::max())
- {
- $$ = repeat_from ($1, $2.min);
- }
- else if ($2.min == $2.max)
- {
- $$ = repeat ($1, $2.min);
- }
- else
- {
- $$ = repeat_from_to ($1, $2.min, $2.max);
- }
- $$ = $$ ? $$ : RegExp::make_nil();
+factor
+ : primary
+ | primary closes {
+ switch($2) {
+ case '*': $$ = RegExp::make_iter($1, 0, RegExp::MANY); break;
+ case '+': $$ = RegExp::make_iter($1, 1, RegExp::MANY); break;
+ case '?': $$ = RegExp::make_iter($1, 0, 1); break;
}
-;
+ } | primary TOKEN_CLOSESIZE {
+ $$ = RegExp::make_iter($1, $2.min, $2.max);
+ };
closes
: close
case '7':
case '8':
case '9':
- ZZBT (zz_4);
+ ZZBT (zz_1);
goto yy4;
default: goto yy2;
}
yych = YYPEEK ();
switch (yych) {
case '.':
- ZZBT (zz_3);
+ ZZBT (zz_2);
goto yy5;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- ZZBT (zz_3);
+ ZZBT (zz_2);
goto yy5;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- ZZBT (zz_2);
+ ZZBT (zz_3);
goto yy10;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- ZZBT (zz_3);
+ ZZBT (zz_2);
goto yy5;
default: goto yy6;
}
yych = YYPEEK ();
switch (yych) {
case '.':
- ZZBT (zz_2);
+ ZZBT (zz_3);
goto yy10;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- ZZBT (zz_1);
+ ZZBT (zz_4);
goto yy14;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- ZZBT (zz_2);
+ ZZBT (zz_3);
goto yy10;
default: goto yy6;
}
yych = YYPEEK ();
switch (yych) {
case '.':
- ZZBT (zz_1);
+ ZZBT (zz_4);
goto yy14;
case '0':
case '1':
default: goto yy17;
}
yy17:
- ZZCT (p3, zz_1);
- ZZCT (p2, zz_2);
- ZZCT (p1, zz_3);
- ZZCT (p0, zz_4);
+ ZZCT (p0, zz_1);
+ ZZCT (p1, zz_2);
+ ZZCT (p2, zz_3);
+ ZZCT (p3, zz_4);
{
printf("%u.%u.%u.%u\n",
parse_oct(p0, p1),
yych = YYPEEK ();
switch (yych) {
case '.':
- ZZBT (zz_1);
+ ZZBT (zz_4);
goto yy14;
default: goto yy6;
}
case '7':
case '8':
case '9':
- zz_4 = YYCURSOR;
+ zz_1 = YYCURSOR;
goto yy4;
default: goto yy2;
}
yych = *(YYMARKER = ++YYCURSOR);
switch (yych) {
case '.':
- zz_3 = YYCURSOR;
+ zz_2 = YYCURSOR;
goto yy5;
case '0':
case '1':
yych = *++YYCURSOR;
switch (yych) {
case '.':
- zz_3 = YYCURSOR;
+ zz_2 = YYCURSOR;
goto yy5;
case '0':
case '1':
yych = *++YYCURSOR;
switch (yych) {
case '.':
- zz_2 = YYCURSOR;
+ zz_3 = YYCURSOR;
goto yy10;
case '0':
case '1':
yych = *++YYCURSOR;
switch (yych) {
case '.':
- zz_3 = YYCURSOR;
+ zz_2 = YYCURSOR;
goto yy5;
default: goto yy6;
}
yych = *++YYCURSOR;
switch (yych) {
case '.':
- zz_2 = YYCURSOR;
+ zz_3 = YYCURSOR;
goto yy10;
case '0':
case '1':
yych = *++YYCURSOR;
switch (yych) {
case '.':
- zz_1 = YYCURSOR;
+ zz_4 = YYCURSOR;
goto yy14;
case '0':
case '1':
yych = *++YYCURSOR;
switch (yych) {
case '.':
- zz_2 = YYCURSOR;
+ zz_3 = YYCURSOR;
goto yy10;
default: goto yy6;
}
yych = *++YYCURSOR;
switch (yych) {
case '.':
- zz_1 = YYCURSOR;
+ zz_4 = YYCURSOR;
goto yy14;
case '0':
case '1':
default: goto yy17;
}
yy17:
- p3 = zz_1;
- p2 = zz_2;
- p1 = zz_3;
- p0 = zz_4;
+ p0 = zz_1;
+ p1 = zz_2;
+ p2 = zz_3;
+ p3 = zz_4;
{
printf("%u.%u.%u.%u\n",
parse_oct(p0, p1),
yych = *++YYCURSOR;
switch (yych) {
case '.':
- zz_1 = YYCURSOR;
+ zz_4 = YYCURSOR;
goto yy14;
default: goto yy6;
}
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (in.yyt3);
+ YYBACKUPTAG (in.yyt1);
goto yy7;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (in.yyt3);
+ YYBACKUPTAG (in.yyt1);
goto yy7;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (in.yyt3);
+ YYBACKUPTAG (in.yyt1);
goto yy7;
default: goto yy8;
}
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (in.yyt1);
+ YYBACKUPTAG (in.yyt3);
goto yy16;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (in.yyt1);
+ YYBACKUPTAG (in.yyt3);
goto yy16;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (in.yyt1);
+ YYBACKUPTAG (in.yyt3);
goto yy16;
default: goto yy8;
}
yy20:
YYSKIP ();
- YYCOPYTAG (p3, in.yyt1);
+ YYCOPYTAG (p1, in.yyt1);
YYCOPYTAG (p2, in.yyt2);
- YYCOPYTAG (p1, in.yyt3);
+ YYCOPYTAG (p3, in.yyt3);
{
printf("> %u.%u.%u.%u\n",
parse_oct(in.tok, p1),
yych = *(in.mar = ++in.cur);
switch (yych) {
case '.':
- in.yyt3 = in.cur;
+ in.yyt1 = in.cur;
goto yy7;
case '0':
case '1':
yych = *++in.cur;
switch (yych) {
case '.':
- in.yyt3 = in.cur;
+ in.yyt1 = in.cur;
goto yy7;
case '0':
case '1':
yych = *++in.cur;
switch (yych) {
case '.':
- in.yyt3 = in.cur;
+ in.yyt1 = in.cur;
goto yy7;
default: goto yy8;
}
yych = *++in.cur;
switch (yych) {
case '.':
- in.yyt1 = in.cur;
+ in.yyt3 = in.cur;
goto yy16;
case '0':
case '1':
yych = *++in.cur;
switch (yych) {
case '.':
- in.yyt1 = in.cur;
+ in.yyt3 = in.cur;
goto yy16;
case '0':
case '1':
yych = *++in.cur;
switch (yych) {
case '.':
- in.yyt1 = in.cur;
+ in.yyt3 = in.cur;
goto yy16;
default: goto yy8;
}
yy20:
++in.cur;
- p3 = in.yyt1;
+ p1 = in.yyt1;
p2 = in.yyt2;
- p1 = in.yyt3;
+ p3 = in.yyt3;
{
printf("> %u.%u.%u.%u\n",
parse_oct(in.tok, p1),
case '7':
case '8':
case '9':
- YYBACKUPTAG (tags.yyt4);
+ YYBACKUPTAG (tags.yyt1);
goto yy4;
default: goto yy2;
}
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (tags.yyt3);
+ YYBACKUPTAG (tags.yyt2);
goto yy5;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (tags.yyt3);
+ YYBACKUPTAG (tags.yyt2);
goto yy5;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (tags.yyt2);
+ YYBACKUPTAG (tags.yyt3);
goto yy10;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (tags.yyt3);
+ YYBACKUPTAG (tags.yyt2);
goto yy5;
default: goto yy6;
}
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (tags.yyt2);
+ YYBACKUPTAG (tags.yyt3);
goto yy10;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (tags.yyt1);
+ YYBACKUPTAG (tags.yyt4);
goto yy14;
case '0':
case '1':
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (tags.yyt2);
+ YYBACKUPTAG (tags.yyt3);
goto yy10;
default: goto yy6;
}
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (tags.yyt1);
+ YYBACKUPTAG (tags.yyt4);
goto yy14;
case '0':
case '1':
default: goto yy17;
}
yy17:
- YYCOPYTAG (p3, tags.yyt1);
- YYCOPYTAG (p2, tags.yyt2);
- YYCOPYTAG (p1, tags.yyt3);
- YYCOPYTAG (p0, tags.yyt4);
+ YYCOPYTAG (p0, tags.yyt1);
+ YYCOPYTAG (p1, tags.yyt2);
+ YYCOPYTAG (p2, tags.yyt3);
+ YYCOPYTAG (p3, tags.yyt4);
{
printf("%u.%u.%u.%u\n",
parse_oct(p0, p1),
yych = YYPEEK ();
switch (yych) {
case '.':
- YYBACKUPTAG (tags.yyt1);
+ YYBACKUPTAG (tags.yyt4);
goto yy14;
default: goto yy6;
}
case '7':
case '8':
case '9':
- tags.yyt4 = YYCURSOR;
+ tags.yyt1 = YYCURSOR;
goto yy4;
default: goto yy2;
}
yych = *(YYMARKER = ++YYCURSOR);
switch (yych) {
case '.':
- tags.yyt3 = YYCURSOR;
+ tags.yyt2 = YYCURSOR;
goto yy5;
case '0':
case '1':
yych = *++YYCURSOR;
switch (yych) {
case '.':
- tags.yyt3 = YYCURSOR;
+ tags.yyt2 = YYCURSOR;
goto yy5;
case '0':
case '1':
yych = *++YYCURSOR;
switch (yych) {
case '.':
- tags.yyt2 = YYCURSOR;
+ tags.yyt3 = YYCURSOR;
goto yy10;
case '0':
case '1':
yych = *++YYCURSOR;
switch (yych) {
case '.':
- tags.yyt3 = YYCURSOR;
+ tags.yyt2 = YYCURSOR;
goto yy5;
default: goto yy6;
}
yych = *++YYCURSOR;
switch (yych) {
case '.':
- tags.yyt2 = YYCURSOR;
+ tags.yyt3 = YYCURSOR;
goto yy10;
case '0':
case '1':
yych = *++YYCURSOR;
switch (yych) {
case '.':
- tags.yyt1 = YYCURSOR;
+ tags.yyt4 = YYCURSOR;
goto yy14;
case '0':
case '1':
yych = *++YYCURSOR;
switch (yych) {
case '.':
- tags.yyt2 = YYCURSOR;
+ tags.yyt3 = YYCURSOR;
goto yy10;
default: goto yy6;
}
yych = *++YYCURSOR;
switch (yych) {
case '.':
- tags.yyt1 = YYCURSOR;
+ tags.yyt4 = YYCURSOR;
goto yy14;
case '0':
case '1':
default: goto yy17;
}
yy17:
- p3 = tags.yyt1;
- p2 = tags.yyt2;
- p1 = tags.yyt3;
- p0 = tags.yyt4;
+ p0 = tags.yyt1;
+ p1 = tags.yyt2;
+ p2 = tags.yyt3;
+ p3 = tags.yyt4;
{
printf("%u.%u.%u.%u\n",
parse_oct(p0, p1),
yych = *++YYCURSOR;
switch (yych) {
case '.':
- tags.yyt1 = YYCURSOR;
+ tags.yyt4 = YYCURSOR;
goto yy14;
default: goto yy6;
}
yych = *++YYCURSOR;
switch (yych) {
case 'c':
- yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy5;
case 'd':
- yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy7;
default: goto yy3;
}
switch (yych) {
case 'a': goto yy9;
default:
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy6;
}
yy6:
- q = yyt1;
- p = yyt2;
+ p = yyt1;
+ q = yyt2;
{ p q }
yy7:
yyaccept = 1;
switch (yych) {
case 'a': goto yy11;
default:
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy8;
}
yy8:
- s = yyt1;
- r = yyt2;
+ r = yyt1;
+ s = yyt2;
{ r s }
yy9:
++YYCURSOR;
yych = *YYCURSOR;
switch (yych) {
case 'c':
- yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy5;
default: goto yy10;
}
yy10:
YYCURSOR = YYMARKER;
if (yyaccept == 0) {
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy6;
} else {
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy8;
}
yy11:
yych = *YYCURSOR;
switch (yych) {
case 'd':
- yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy7;
default: goto yy10;
}
yych = *++YYCURSOR;
switch (yych) {
case 'b':
- yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy6;
case 'c':
yyt1 = yyt2 = YYCURSOR;
goto yy5;
}
yy5:
- YYCURSOR = yyt1;
- p = yyt2;
+ p = yyt1;
+ YYCURSOR = yyt2;
{ 1 p }
yy6:
++YYCURSOR;
switch (yych) {
case 'b': goto yy6;
case 'c':
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy8;
case 'd':
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy11;
default:
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy5;
}
yy8:
default: goto yy10;
}
yy10:
- YYCURSOR = yyt1;
- p = yyt2;
+ p = yyt1;
+ YYCURSOR = yyt2;
{ 2 p }
yy11:
++YYCURSOR;
yych = *++YYCURSOR;
switch (yych) {
case 'b':
- yyt1 = yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy19;
case 'c':
yyt1 = yyt2 = YYCURSOR;
switch (yych) {
case 'b': goto yy19;
case 'c':
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy21;
default: goto yy18;
}
default: goto yy23;
}
yy23:
- YYCURSOR = yyt1;
- p = yyt2;
+ p = yyt1;
+ YYCURSOR = yyt2;
{ 2 p }
}
default: goto yy35;
}
yy35:
- YYCURSOR = yyt2;
p = yyt1;
+ YYCURSOR = yyt2;
{ 2 p }
}
default: goto yy47;
}
yy47:
- YYCURSOR = yyt2;
p = yyt1;
+ YYCURSOR = yyt2;
{ 2 p }
}
switch (yych) {
case 'a': goto yy3;
case 'b':
- yyt3 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy4;
case 'c':
- yyt2 = yyt3 = YYCURSOR;
+ yyt1 = yyt2 = YYCURSOR;
goto yy5;
default:
yyt1 = yyt2 = yyt3 = YYCURSOR;
goto yy2;
}
yy2:
- z = yyt1;
+ p = yyt1;
q = yyt2;
- p = yyt3;
+ z = yyt3;
{}
yy3:
yych = *++YYCURSOR;
switch (yych) {
case 'b':
- yyt3 = NULL;
+ yyt1 = NULL;
goto yy4;
case 'c':
- yyt3 = NULL;
+ yyt1 = NULL;
yyt2 = YYCURSOR;
goto yy5;
default:
- yyt3 = NULL;
- yyt1 = yyt2 = YYCURSOR;
+ yyt1 = NULL;
+ yyt2 = yyt3 = YYCURSOR;
goto yy2;
}
yy4:
goto yy5;
default:
yyt2 = NULL;
- yyt1 = YYCURSOR;
+ yyt3 = YYCURSOR;
goto yy2;
}
yy5:
++YYCURSOR;
- yyt1 = NULL;
+ yyt3 = NULL;
goto yy2;
}
}
yy19:
++YYCURSOR;
- p4 = YYCURSOR - 5;
- p3 = YYCURSOR - 9;
- p2 = YYCURSOR - 12;
- p1 = YYCURSOR - 14;
p0 = YYCURSOR - 15;
+ p1 = YYCURSOR - 14;
+ p2 = YYCURSOR - 12;
+ p3 = YYCURSOR - 9;
+ p4 = YYCURSOR - 5;
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%.*s'\n",
p1 - p0, p0,
yych = YYPEEK ();
switch (yych) {
case '0':
- YYBACKUPTAG (yyt5);
+ YYBACKUPTAG (yyt1);
goto yy4;
default: goto yy2;
}
yych = YYPEEK ();
switch (yych) {
case '1':
- YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt2);
goto yy5;
default: goto yy3;
}
yych = YYPEEK ();
switch (yych) {
case '3':
- YYBACKUPTAG (yyt2);
+ YYBACKUPTAG (yyt4);
goto yy11;
default: goto yy6;
}
yych = YYPEEK ();
switch (yych) {
case '4':
- YYBACKUPTAG (yyt1);
+ YYBACKUPTAG (yyt5);
goto yy15;
default: goto yy6;
}
}
yy19:
YYSKIP ();
- YYRESTORETAG (yyt1);
- YYCOPYTAG (p3, yyt2);
+ YYCOPYTAG (p0, yyt1);
+ YYCOPYTAG (p1, yyt2);
YYCOPYTAG (p2, yyt3);
- YYCOPYTAG (p1, yyt4);
- YYCOPYTAG (p0, yyt5);
+ YYCOPYTAG (p3, yyt4);
+ YYRESTORETAG (yyt5);
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%s'\n",
p1 - p0, p0,
}
yy19:
++YYCURSOR;
- YYCURSOR -= 5;
- p3 = YYCURSOR - 4;
- p2 = YYCURSOR - 7;
- p1 = YYCURSOR - 9;
p0 = YYCURSOR - 10;
+ p1 = YYCURSOR - 9;
+ p2 = YYCURSOR - 7;
+ p3 = YYCURSOR - 4;
+ YYCURSOR -= 5;
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%s'\n",
p1 - p0, p0,
yych = *YYCURSOR;
switch (yych) {
case '0':
- yyt5 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy4;
case '1':
- yyt4 = yyt5 = YYCURSOR;
+ yyt1 = yyt2 = YYCURSOR;
goto yy7;
case '2':
- yyt3 = yyt4 = yyt5 = YYCURSOR;
+ yyt1 = yyt2 = yyt3 = YYCURSOR;
goto yy9;
case '3':
- yyt2 = yyt3 = yyt4 = yyt5 = YYCURSOR;
+ yyt1 = yyt2 = yyt3 = yyt4 = YYCURSOR;
goto yy11;
case '4':
yyt1 = yyt2 = yyt3 = yyt4 = yyt5 = YYCURSOR;
switch (yych) {
case '0': goto yy4;
case '1':
- yyt4 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy7;
case '2':
- yyt3 = yyt4 = YYCURSOR;
+ yyt2 = yyt3 = YYCURSOR;
goto yy9;
case '3':
yyt2 = yyt3 = yyt4 = YYCURSOR;
goto yy11;
case '4':
- yyt1 = yyt2 = yyt3 = yyt4 = YYCURSOR;
+ yyt2 = yyt3 = yyt4 = yyt5 = YYCURSOR;
goto yy13;
default:
- yyt1 = yyt2 = yyt3 = yyt4 = YYCURSOR;
+ yyt2 = yyt3 = yyt4 = yyt5 = YYCURSOR;
goto yy6;
}
yy6:
- p4 = yyt1;
- p3 = yyt2;
+ p0 = yyt1;
+ p1 = yyt2;
p2 = yyt3;
- p1 = yyt4;
- p0 = yyt5;
+ p3 = yyt4;
+ p4 = yyt5;
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%.*s'\n",
p1 - p0, p0,
yyt3 = YYCURSOR;
goto yy9;
case '3':
- yyt2 = yyt3 = YYCURSOR;
+ yyt3 = yyt4 = YYCURSOR;
goto yy11;
case '4':
- yyt1 = yyt2 = yyt3 = YYCURSOR;
+ yyt3 = yyt4 = yyt5 = YYCURSOR;
goto yy13;
default:
- yyt1 = yyt2 = yyt3 = YYCURSOR;
+ yyt3 = yyt4 = yyt5 = YYCURSOR;
goto yy6;
}
yy9:
switch (yych) {
case '2': goto yy9;
case '3':
- yyt2 = YYCURSOR;
+ yyt4 = YYCURSOR;
goto yy11;
case '4':
- yyt1 = yyt2 = YYCURSOR;
+ yyt4 = yyt5 = YYCURSOR;
goto yy13;
default:
- yyt1 = yyt2 = YYCURSOR;
+ yyt4 = yyt5 = YYCURSOR;
goto yy6;
}
yy11:
switch (yych) {
case '3': goto yy11;
case '4':
- yyt1 = YYCURSOR;
+ yyt5 = YYCURSOR;
goto yy13;
default:
- yyt1 = YYCURSOR;
+ yyt5 = YYCURSOR;
goto yy6;
}
yy13:
yych = YYPEEK ();
switch (yych) {
case '0':
- YYBACKUPTAG (yyt5);
+ YYBACKUPTAG (yyt1);
goto yy4;
case '1':
- YYBACKUPTAG (yyt4);
- YYBACKUPTAG (yyt5);
+ YYBACKUPTAG (yyt1);
+ YYBACKUPTAG (yyt2);
goto yy7;
case '2':
+ YYBACKUPTAG (yyt1);
+ YYBACKUPTAG (yyt2);
YYBACKUPTAG (yyt3);
- YYBACKUPTAG (yyt4);
- YYBACKUPTAG (yyt5);
goto yy9;
case '3':
+ YYBACKUPTAG (yyt1);
YYBACKUPTAG (yyt2);
YYBACKUPTAG (yyt3);
YYBACKUPTAG (yyt4);
- YYBACKUPTAG (yyt5);
goto yy11;
case '4':
YYBACKUPTAG (yyt1);
switch (yych) {
case '0': goto yy4;
case '1':
- YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt2);
goto yy7;
case '2':
+ YYBACKUPTAG (yyt2);
YYBACKUPTAG (yyt3);
- YYBACKUPTAG (yyt4);
goto yy9;
case '3':
YYBACKUPTAG (yyt2);
YYBACKUPTAG (yyt4);
goto yy11;
case '4':
- YYBACKUPTAG (yyt1);
YYBACKUPTAG (yyt2);
YYBACKUPTAG (yyt3);
YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt5);
goto yy13;
default:
- YYBACKUPTAG (yyt1);
YYBACKUPTAG (yyt2);
YYBACKUPTAG (yyt3);
YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt5);
goto yy6;
}
yy6:
- YYRESTORETAG (yyt1);
- YYCOPYTAG (p3, yyt2);
+ YYCOPYTAG (p0, yyt1);
+ YYCOPYTAG (p1, yyt2);
YYCOPYTAG (p2, yyt3);
- YYCOPYTAG (p1, yyt4);
- YYCOPYTAG (p0, yyt5);
+ YYCOPYTAG (p3, yyt4);
+ YYRESTORETAG (yyt5);
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%s'\n",
p1 - p0, p0,
YYBACKUPTAG (yyt3);
goto yy9;
case '3':
- YYBACKUPTAG (yyt2);
YYBACKUPTAG (yyt3);
+ YYBACKUPTAG (yyt4);
goto yy11;
case '4':
- YYBACKUPTAG (yyt1);
- YYBACKUPTAG (yyt2);
YYBACKUPTAG (yyt3);
+ YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt5);
goto yy13;
default:
- YYBACKUPTAG (yyt1);
- YYBACKUPTAG (yyt2);
YYBACKUPTAG (yyt3);
+ YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt5);
goto yy6;
}
yy9:
switch (yych) {
case '2': goto yy9;
case '3':
- YYBACKUPTAG (yyt2);
+ YYBACKUPTAG (yyt4);
goto yy11;
case '4':
- YYBACKUPTAG (yyt1);
- YYBACKUPTAG (yyt2);
+ YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt5);
goto yy13;
default:
- YYBACKUPTAG (yyt1);
- YYBACKUPTAG (yyt2);
+ YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt5);
goto yy6;
}
yy11:
switch (yych) {
case '3': goto yy11;
case '4':
- YYBACKUPTAG (yyt1);
+ YYBACKUPTAG (yyt5);
goto yy13;
default:
- YYBACKUPTAG (yyt1);
+ YYBACKUPTAG (yyt5);
goto yy6;
}
yy13:
yych = *YYCURSOR;
switch (yych) {
case '0':
- yyt5 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy4;
case '1':
- yyt4 = yyt5 = YYCURSOR;
+ yyt1 = yyt2 = YYCURSOR;
goto yy7;
case '2':
- yyt3 = yyt4 = yyt5 = YYCURSOR;
+ yyt1 = yyt2 = yyt3 = YYCURSOR;
goto yy9;
case '3':
- yyt2 = yyt3 = yyt4 = yyt5 = YYCURSOR;
+ yyt1 = yyt2 = yyt3 = yyt4 = YYCURSOR;
goto yy11;
case '4':
yyt1 = yyt2 = yyt3 = yyt4 = yyt5 = YYCURSOR;
switch (yych) {
case '0': goto yy4;
case '1':
- yyt4 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy7;
case '2':
- yyt3 = yyt4 = YYCURSOR;
+ yyt2 = yyt3 = YYCURSOR;
goto yy9;
case '3':
yyt2 = yyt3 = yyt4 = YYCURSOR;
goto yy11;
case '4':
- yyt1 = yyt2 = yyt3 = yyt4 = YYCURSOR;
+ yyt2 = yyt3 = yyt4 = yyt5 = YYCURSOR;
goto yy13;
default:
- yyt1 = yyt2 = yyt3 = yyt4 = YYCURSOR;
+ yyt2 = yyt3 = yyt4 = yyt5 = YYCURSOR;
goto yy6;
}
yy6:
- YYCURSOR = yyt1;
- p3 = yyt2;
+ p0 = yyt1;
+ p1 = yyt2;
p2 = yyt3;
- p1 = yyt4;
- p0 = yyt5;
+ p3 = yyt4;
+ YYCURSOR = yyt5;
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%s'\n",
p1 - p0, p0,
yyt3 = YYCURSOR;
goto yy9;
case '3':
- yyt2 = yyt3 = YYCURSOR;
+ yyt3 = yyt4 = YYCURSOR;
goto yy11;
case '4':
- yyt1 = yyt2 = yyt3 = YYCURSOR;
+ yyt3 = yyt4 = yyt5 = YYCURSOR;
goto yy13;
default:
- yyt1 = yyt2 = yyt3 = YYCURSOR;
+ yyt3 = yyt4 = yyt5 = YYCURSOR;
goto yy6;
}
yy9:
switch (yych) {
case '2': goto yy9;
case '3':
- yyt2 = YYCURSOR;
+ yyt4 = YYCURSOR;
goto yy11;
case '4':
- yyt1 = yyt2 = YYCURSOR;
+ yyt4 = yyt5 = YYCURSOR;
goto yy13;
default:
- yyt1 = yyt2 = YYCURSOR;
+ yyt4 = yyt5 = YYCURSOR;
goto yy6;
}
yy11:
switch (yych) {
case '3': goto yy11;
case '4':
- yyt1 = YYCURSOR;
+ yyt5 = YYCURSOR;
goto yy13;
default:
- yyt1 = YYCURSOR;
+ yyt5 = YYCURSOR;
goto yy6;
}
yy13:
yych = *(YYMARKER = ++YYCURSOR);
switch (yych) {
case '1':
- yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy5;
case '2':
- yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy8;
default: goto yy3;
}
yych = *++YYCURSOR;
switch (yych) {
case '3':
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy9;
case '4':
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy11;
default: goto yy7;
}
}
yy11:
++YYCURSOR;
- p3 = yyt1;
- p1 = yyt2;
+ p1 = yyt1;
+ p3 = yyt2;
+ p0 = yyt1 - 1;
+ p2 = yyt2 - 1;
p4 = YYCURSOR - 1;
- p2 = yyt1 - 1;
- p0 = yyt2 - 1;
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%.*s'\n",
p1 - p0, p0,
yych = YYPEEK ();
switch (yych) {
case '0':
- YYBACKUPTAG (yyt5);
+ YYBACKUPTAG (yyt1);
goto yy4;
default: goto yy2;
}
yych = YYPEEK ();
switch (yych) {
case '1':
- YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt2);
goto yy5;
case '2':
+ YYBACKUPTAG (yyt2);
YYBACKUPTAG (yyt3);
- YYBACKUPTAG (yyt4);
goto yy8;
default: goto yy3;
}
yych = YYPEEK ();
switch (yych) {
case '3':
- YYBACKUPTAG (yyt2);
+ YYBACKUPTAG (yyt4);
goto yy9;
case '4':
- YYBACKUPTAG (yyt1);
- YYBACKUPTAG (yyt2);
+ YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt5);
goto yy11;
default: goto yy7;
}
switch (yych) {
case '3': goto yy9;
case '4':
- YYBACKUPTAG (yyt1);
+ YYBACKUPTAG (yyt5);
goto yy11;
default: goto yy7;
}
yy11:
YYSKIP ();
- YYRESTORETAG (yyt1);
- YYCOPYTAG (p3, yyt2);
+ YYCOPYTAG (p0, yyt1);
+ YYCOPYTAG (p1, yyt2);
YYCOPYTAG (p2, yyt3);
- YYCOPYTAG (p1, yyt4);
- YYCOPYTAG (p0, yyt5);
+ YYCOPYTAG (p3, yyt4);
+ YYRESTORETAG (yyt5);
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%s'\n",
p1 - p0, p0,
yych = *(YYMARKER = ++YYCURSOR);
switch (yych) {
case '1':
- yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy5;
case '2':
- yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy8;
default: goto yy3;
}
yych = *++YYCURSOR;
switch (yych) {
case '3':
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy9;
case '4':
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy11;
default: goto yy7;
}
}
yy11:
++YYCURSOR;
- p3 = yyt1;
- p1 = yyt2;
+ p1 = yyt1;
+ p3 = yyt2;
+ p0 = yyt1 - 1;
+ p2 = yyt2 - 1;
YYCURSOR -= 1;
- p2 = yyt1 - 1;
- p0 = yyt2 - 1;
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%s'\n",
p1 - p0, p0,
yych = *YYCURSOR;
switch (yych) {
case '0':
- yyt3 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy4;
case '1':
- yyt3 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy5;
default: goto yy2;
}
}
yy12:
yych = *++YYCURSOR;
- yyt1 = YYCURSOR;
+ yyt3 = YYCURSOR;
goto yy15;
yy13:
- p4 = yyt1;
+ p0 = yyt1;
p2 = yyt2;
- p0 = yyt3;
- p3 = yyt1 - 1;
+ p4 = yyt3;
p1 = yyt2 - 1;
+ p3 = yyt3 - 1;
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%.*s'\n",
p1 - p0, p0,
yych = YYPEEK ();
switch (yych) {
case '0':
- YYBACKUPTAG (yyt5);
+ YYBACKUPTAG (yyt2);
goto yy4;
case '1':
YYBACKUPTAG (yyt1);
- YYBACKUPTAG (yyt5);
+ YYBACKUPTAG (yyt2);
goto yy5;
default: goto yy2;
}
yych = YYPEEK ();
switch (yych) {
case '2':
- YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt3);
goto yy10;
case '3':
YYBACKUPTAG (yyt3);
yych = YYPEEK ();
switch (yych) {
case '2':
- YYBACKUPTAG (yyt4);
+ YYBACKUPTAG (yyt3);
goto yy10;
case '3':
YYBACKUPTAG (yyt3);
switch (yych) {
case '2': goto yy10;
case '3':
- YYBACKUPTAG (yyt3);
+ YYBACKUPTAG (yyt4);
goto yy12;
default: goto yy8;
}
yy12:
YYSKIP ();
yych = YYPEEK ();
- YYBACKUPTAG (yyt2);
+ YYBACKUPTAG (yyt5);
goto yy15;
yy13:
- YYRESTORETAG (yyt2);
- YYCOPYTAG (p3, yyt3);
- YYCOPYTAG (p2, yyt4);
+ YYCOPYTAG (p0, yyt2);
YYCOPYTAG (p1, yyt1);
- YYCOPYTAG (p0, yyt5);
+ YYCOPYTAG (p2, yyt3);
+ YYCOPYTAG (p3, yyt4);
+ YYRESTORETAG (yyt5);
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%s'\n",
p1 - p0, p0,
yych = *YYCURSOR;
switch (yych) {
case '0':
- yyt3 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy4;
case '1':
- yyt3 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy5;
default: goto yy2;
}
}
yy12:
yych = *++YYCURSOR;
- yyt1 = YYCURSOR;
+ yyt3 = YYCURSOR;
goto yy15;
yy13:
- YYCURSOR = yyt1;
+ p0 = yyt1;
p2 = yyt2;
- p0 = yyt3;
- p3 = yyt1 - 1;
+ YYCURSOR = yyt3;
p1 = yyt2 - 1;
+ p3 = yyt3 - 1;
{
printf("'%.*s', '%.*s', '%.*s', '%.*s', '%s'\n",
p1 - p0, p0,
goto yy2;
}
yy2:
- q = yyt1;
- p = yyt2;
+ p = yyt1;
+ q = yyt2;
{}
yy3:
++YYCURSOR;
yych = *YYCURSOR;
switch (yych) {
case 'b':
- yyt4 = NULL;
- yyt3 = YYCURSOR;
+ yyt3 = NULL;
+ yyt4 = YYCURSOR;
goto yy5;
default: goto yy4;
}
goto yy2;
}
yy2:
- YYCOPYTAG (b, yyt2);
YYCOPYTAG (a, yyt1);
+ YYCOPYTAG (b, yyt2);
{}
}
switch (yych) {
case 'a': goto yy1;
case 'b':
- yyt2 = YYCURSOR;
+ yyt1 = YYCURSOR;
goto yy4;
case 'c':
yyt1 = yyt2 = YYCURSOR;
goto yy3;
}
yy3:
- p = yyt1;
- YYCURSOR = yyt2;
+ YYCURSOR = yyt1;
+ p = yyt2;
{}
yy4:
++YYCURSOR;
switch (yych) {
case 'b': goto yy4;
case 'c':
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy6;
default:
- yyt1 = YYCURSOR;
+ yyt2 = YYCURSOR;
goto yy3;
}
yy6:
goto yy3;
}
yy2:
- s = yyt4;
r = yyt1;
+ s = yyt4;
{}
yy3:
yyaccept = 1;
goto yy8;
}
yy7:
- y = yyt2;
- q = yyt3;
p = yyt1;
+ q = yyt2;
+ y = yyt3;
{}
yy8:
yyaccept = 3;
switch (yych) {
case 'a': goto yy17;
case 'b':
- yyt3 = NULL;
- yyt2 = YYCURSOR;
+ yyt2 = NULL;
+ yyt3 = YYCURSOR;
goto yy18;
default:
- yyt3 = NULL;
- yyt2 = YYCURSOR;
+ yyt2 = NULL;
+ yyt3 = YYCURSOR;
goto yy15;
}
yy14:
switch (yych) {
case 'a': goto yy5;
case 'b':
- yyt3 = NULL;
- yyt2 = YYCURSOR;
+ yyt2 = NULL;
+ yyt3 = YYCURSOR;
goto yy18;
default:
- yyt3 = NULL;
- yyt2 = YYCURSOR;
+ yyt2 = NULL;
+ yyt3 = YYCURSOR;
goto yy15;
}
}
re2c: warning: line 7: rule matches empty string [-Wmatch-empty-string]
-re2c: warning: line 6: tag 'y' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
-re2c: warning: line 6: tag 'q' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
re2c: warning: line 6: tag 'p' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
-re2c: warning: line 7: tag 's' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
+re2c: warning: line 6: tag 'q' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
+re2c: warning: line 6: tag 'y' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
re2c: warning: line 7: tag 'r' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
+re2c: warning: line 7: tag 's' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
default: goto yy4;
}
yy4:
- z = yyt1;
- y = yyt1;
- x = yyt1;
- w = yyt1;
- v = yyt1;
u = yyt1;
+ v = yyt1;
+ w = yyt1;
+ x = yyt1;
+ y = yyt1;
+ z = yyt1;
{}
yy5:
++YYCURSOR;
}
re2c: warning: line 6: rule matches empty string [-Wmatch-empty-string]
-re2c: warning: line 5: tag 'z' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
-re2c: warning: line 5: tag 'y' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
-re2c: warning: line 5: tag 'x' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
-re2c: warning: line 5: tag 'w' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
-re2c: warning: line 5: tag 'v' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
re2c: warning: line 5: tag 'u' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
+re2c: warning: line 5: tag 'v' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
+re2c: warning: line 5: tag 'w' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
+re2c: warning: line 5: tag 'x' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
+re2c: warning: line 5: tag 'y' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]
+re2c: warning: line 5: tag 'z' is non-deterministic and induces 2 parallel instances [-Wnondeterministic-tags]