summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/grammar.hpp2
-rw-r--r--src/output.cpp2
-rw-r--r--src/output_lr0.cpp13
-rw-r--r--src/output_slr.cpp13
-rw-r--r--src/parse.cpp645
-rw-r--r--src/parse.y121
6 files changed, 520 insertions, 276 deletions
diff --git a/src/grammar.hpp b/src/grammar.hpp
index e603d00..b54b46d 100644
--- a/src/grammar.hpp
+++ b/src/grammar.hpp
@@ -39,6 +39,8 @@ struct grammar_t {
std::map<std::string, std::string> nonterm_types;
std::map<symbol_t, std::pair<std::string, std::string>> term_types;
+ std::map<symbol_t, std::string> destructors;
+
std::string header_block;
std::string source_block;
diff --git a/src/output.cpp b/src/output.cpp
index 1503c38..fee9267 100644
--- a/src/output.cpp
+++ b/src/output.cpp
@@ -307,6 +307,8 @@ void output_t::emit_source() {
std::fprintf(source_file, ", %s %s", arg.first.c_str(), arg.second.c_str());
std::fprintf(source_file, ") {\n");
+ std::fprintf(source_file, "\t%ssymbol_value_t result;\n\n", prefix());
+
std::fprintf(source_file, "\twhile (1) {\n");
std::fprintf(source_file, "\t\tswitch (parser->stack[parser->top].state) {\n");
diff --git a/src/output_lr0.cpp b/src/output_lr0.cpp
index 62c5966..5d0c882 100644
--- a/src/output_lr0.cpp
+++ b/src/output_lr0.cpp
@@ -63,7 +63,7 @@ void output_lr0_t::emit_state_reduce(const item_t &item, int rule_id) {
std::fprintf(source_file, "\t\t\t");
if (!type.empty())
- std::fprintf(source_file, "parser->stack[parser->top].value.symbol_%s = ", item.get_lhs().c_str());
+ std::fprintf(source_file, "result.symbol_%s = ", item.get_lhs().c_str());
std::fprintf(source_file, "%sreduce_%i(", prefix(), rule_id);
bool empty = true;
@@ -90,6 +90,17 @@ void output_lr0_t::emit_state_reduce(const item_t &item, int rule_id) {
}
std::fprintf(source_file, ");\n");
+
+ for (unsigned i = 0; i < rhs.size(); i++) {
+ auto it = generator->get_grammar().destructors.find(rhs[i]);
+ if (it == generator->get_grammar().destructors.end())
+ continue;
+
+ std::fprintf(source_file, "\t\t\t%s(parser->stack[parser->top + %u].value.%s);\n", it->second.c_str(), i, symbol_values[rhs[i]].c_str());
+ }
+
+ if (!type.empty())
+ std::fprintf(source_file, "\t\t\tparser->stack[parser->top].value.symbol_%s = result.symbol_%s;\n", item.get_lhs().c_str(), item.get_lhs().c_str());
}
emit_gotos(item.get_lhs());
diff --git a/src/output_slr.cpp b/src/output_slr.cpp
index 1acd951..d2b9817 100644
--- a/src/output_slr.cpp
+++ b/src/output_slr.cpp
@@ -60,7 +60,7 @@ void output_slr_t::emit_state_reduce_code(const item_t &item, int rule_id) {
std::fprintf(source_file, "\t\t\t\t");
if (!type.empty())
- std::fprintf(source_file, "parser->stack[parser->top].value.symbol_%s = ", item.get_lhs().c_str());
+ std::fprintf(source_file, "result.symbol_%s = ", item.get_lhs().c_str());
std::fprintf(source_file, "%sreduce_%i(", prefix(), rule_id);
bool empty = true;
@@ -87,6 +87,17 @@ void output_slr_t::emit_state_reduce_code(const item_t &item, int rule_id) {
}
std::fprintf(source_file, ");\n");
+
+ for (unsigned i = 0; i < rhs.size(); i++) {
+ auto it = generator->get_grammar().destructors.find(rhs[i]);
+ if (it == generator->get_grammar().destructors.end())
+ continue;
+
+ std::fprintf(source_file, "\t\t\t\t%s(parser->stack[parser->top + %u].value.%s);\n", it->second.c_str(), i, symbol_values[rhs[i]].c_str());
+ }
+
+ if (!type.empty())
+ std::fprintf(source_file, "\t\t\t\tparser->stack[parser->top].value.symbol_%s = result.symbol_%s;\n", item.get_lhs().c_str(), item.get_lhs().c_str());
}
emit_gotos(item.get_lhs());
diff --git a/src/parse.cpp b/src/parse.cpp
index faf9618..35b6f8f 100644
--- a/src/parse.cpp
+++ b/src/parse.cpp
@@ -1,5 +1,19 @@
#include "parse.hpp"
+
+static inline void free_string(std::string *v) {
+ delete v;
+}
+
+static inline void free_symbol(solar::symbol_t *v) {
+ delete v;
+}
+
+static inline void free_rule(solar::rule_t *v) {
+ delete v;
+}
+
+
typedef union parse_symbol_value {
parse_token_value_t token;
std::string * symbol_action;
@@ -32,138 +46,116 @@ void parse_free(parse_context_t *parser, void (*free_func)(void *)) {
free_func(parser);
}
-static inline void parse_reduce_3(solar::rule_t * rule, __attribute__((unused)) solar::grammar_t * grammar) {
- if (grammar->rules.empty()) {
- solar::item_t init("");
- init.get_rhs().push_back(solar::symbol_t::make_nonterm(rule->item.get_lhs().c_str()));
- grammar->rules.emplace_back(solar::rule_t {std::move(init), std::vector<std::string>(), std::string()});
- }
-
- grammar->rules.push_back(*rule);
- delete rule;
-}
-
-static inline void parse_reduce_4(std::string * nonterm, std::string * type, __attribute__((unused)) solar::grammar_t * grammar) {
+static inline void parse_reduce_3(std::string * nonterm, std::string * type, __attribute__((unused)) solar::grammar_t * grammar) {
grammar->nonterm_types.insert(std::make_pair(*nonterm, *type));
-
- delete nonterm;
- delete type;
}
-static inline void parse_reduce_5(solar::symbol_t * term, std::string * type, std::string * name, __attribute__((unused)) solar::grammar_t * grammar) {
+static inline void parse_reduce_4(solar::symbol_t * term, std::string * type, std::string * name, __attribute__((unused)) solar::grammar_t * grammar) {
grammar->term_types.insert(std::make_pair(*term, std::make_pair(*type, *name)));
+}
- delete term;
- delete type;
- delete name;
+static inline void parse_reduce_5(solar::symbol_t * sym, std::string * name, __attribute__((unused)) solar::grammar_t * grammar) {
+ grammar->destructors.insert(std::make_pair(*sym, *name));
}
static inline void parse_reduce_6(std::string * block, __attribute__((unused)) solar::grammar_t * grammar) {
grammar->source_block = *block;
- delete block;
}
static inline void parse_reduce_7(std::string * block, __attribute__((unused)) solar::grammar_t * grammar) {
grammar->header_block = *block;
- delete block;
}
static inline void parse_reduce_8(std::string * type, std::string * name, __attribute__((unused)) solar::grammar_t * grammar) {
grammar->extra_args.push_back(std::make_pair(*type, *name));
+}
+
+static inline void parse_reduce_9(solar::rule_t * rule, __attribute__((unused)) solar::grammar_t * grammar) {
+ if (grammar->rules.empty()) {
+ solar::item_t init("");
+ init.get_rhs().push_back(solar::symbol_t::make_nonterm(rule->item.get_lhs().c_str()));
+ grammar->rules.emplace_back(solar::rule_t {std::move(init), std::vector<std::string>(), std::string()});
+ }
- delete type;
- delete name;
+ grammar->rules.push_back(*rule);
}
-static inline solar::rule_t * parse_reduce_9(std::string * lhs, std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * rhs, std::string * action, __attribute__((unused)) solar::grammar_t * grammar) {
+static inline solar::rule_t * parse_reduce_10(std::string * lhs, std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * rhs, std::string * action, __attribute__((unused)) solar::grammar_t * grammar) {
auto *ret = new solar::rule_t {solar::item_t(*lhs, rhs->first), rhs->second, *action};
-
- delete lhs;
delete rhs;
- delete action;
-
return ret;
}
-static inline std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * parse_reduce_10(__attribute__((unused)) solar::grammar_t * grammar) {
+static inline std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * parse_reduce_11(__attribute__((unused)) solar::grammar_t * grammar) {
return new std::pair<std::vector<solar::symbol_t>, std::vector<std::string>>();
}
-static inline std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * parse_reduce_11(std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * rhs, solar::symbol_t * sym, __attribute__((unused)) solar::grammar_t * grammar) {
+static inline std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * parse_reduce_12(std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * rhs, solar::symbol_t * sym, __attribute__((unused)) solar::grammar_t * grammar) {
rhs->first.push_back(*sym);
rhs->second.emplace_back();
- delete sym;
return rhs;
}
-static inline std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * parse_reduce_12(std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * rhs, solar::symbol_t * sym, std::string * var, __attribute__((unused)) solar::grammar_t * grammar) {
+static inline std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * parse_reduce_13(std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * rhs, solar::symbol_t * sym, std::string * var, __attribute__((unused)) solar::grammar_t * grammar) {
rhs->first.push_back(*sym);
rhs->second.push_back(*var);
- delete sym;
- delete var;
-
return rhs;
}
-static inline std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * parse_reduce_13(std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * rhs, std::string * str, __attribute__((unused)) solar::grammar_t * grammar) {
+static inline std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * parse_reduce_14(std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> * rhs, std::string * str, __attribute__((unused)) solar::grammar_t * grammar) {
for (char c : *str) {
rhs->first.push_back(solar::symbol_t::make_char(c));
rhs->second.emplace_back();
}
- delete str;
-
return rhs;
}
-static inline std::string * parse_reduce_14(__attribute__((unused)) solar::grammar_t * grammar) {
+static inline std::string * parse_reduce_15(__attribute__((unused)) solar::grammar_t * grammar) {
return new std::string;
}
-static inline std::string * parse_reduce_15(std::string * v, __attribute__((unused)) solar::grammar_t * grammar) {
- return v;
-}
-
static inline std::string * parse_reduce_16(std::string * v, __attribute__((unused)) solar::grammar_t * grammar) {
- *v = "\n\treturn " + *v + ";\n";
- return v;
+ return new std::string(*v);
}
-static inline solar::symbol_t * parse_reduce_17(solar::symbol_t * v, __attribute__((unused)) solar::grammar_t * grammar) {
- return v;
+static inline std::string * parse_reduce_17(std::string * v, __attribute__((unused)) solar::grammar_t * grammar) {
+ return new std::string("\n\treturn " + *v + ";\n");
}
-static inline solar::symbol_t * parse_reduce_18(std::string * v, __attribute__((unused)) solar::grammar_t * grammar) {
- solar::symbol_t *ret = new solar::symbol_t(solar::symbol_t::make_nonterm(*v));
- delete v;
- return ret;
+static inline solar::symbol_t * parse_reduce_18(solar::symbol_t * v, __attribute__((unused)) solar::grammar_t * grammar) {
+ return new solar::symbol_t(*v);
}
static inline solar::symbol_t * parse_reduce_19(std::string * v, __attribute__((unused)) solar::grammar_t * grammar) {
- solar::symbol_t *ret = new solar::symbol_t(solar::symbol_t::make_term(*v));
- delete v;
- return ret;
+ return new solar::symbol_t(solar::symbol_t::make_nonterm(*v));
}
-static inline solar::symbol_t * parse_reduce_20(char v, __attribute__((unused)) solar::grammar_t * grammar) {
- return new solar::symbol_t(solar::symbol_t::make_char(v));
+static inline solar::symbol_t * parse_reduce_20(std::string * v, __attribute__((unused)) solar::grammar_t * grammar) {
+ return new solar::symbol_t(solar::symbol_t::make_term(*v));
}
-static inline std::string * parse_reduce_21(std::string * v, __attribute__((unused)) solar::grammar_t * grammar) {
- return v;
+static inline solar::symbol_t * parse_reduce_21(char v, __attribute__((unused)) solar::grammar_t * grammar) {
+ return new solar::symbol_t(solar::symbol_t::make_char(v));
}
static inline std::string * parse_reduce_22(std::string * v, __attribute__((unused)) solar::grammar_t * grammar) {
- return v;
+ return new std::string(*v);
}
static inline std::string * parse_reduce_23(std::string * v, __attribute__((unused)) solar::grammar_t * grammar) {
- return v;
+ return new std::string(*v);
+}
+
+static inline std::string * parse_reduce_24(std::string * v, __attribute__((unused)) solar::grammar_t * grammar) {
+ return new std::string(*v);
}
static int parse_do_push(parse_context_t *parser, int token, __attribute__((unused)) solar::grammar_t * grammar) {
+ parse_symbol_value_t result;
+
while (1) {
switch (parser->stack[parser->top].state) {
case 0:
@@ -203,7 +195,8 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
switch (token) {
default:
parser->top -= 1;
- parse_reduce_3(parser->stack[parser->top + 0].value.symbol_rule, grammar);
+ parse_reduce_9(parser->stack[parser->top + 0].value.symbol_rule, grammar);
+ free_rule(parser->stack[parser->top + 0].value.symbol_rule);
parser->stack[++parser->top].state = 2;
}
break;
@@ -221,22 +214,26 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
case 5:
switch (token) {
- case 'e':
+ case 'd':
parser->stack[++parser->top].state = 7;
return 1;
- case 'h':
+ case 'e':
parser->stack[++parser->top].state = 8;
return 1;
- case 's':
+ case 'h':
parser->stack[++parser->top].state = 9;
return 1;
- case 't':
+ case 's':
parser->stack[++parser->top].state = 10;
return 1;
+ case 't':
+ parser->stack[++parser->top].state = 11;
+ return 1;
+
default:
return -1;
}
@@ -245,7 +242,7 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
case 6:
switch (token) {
case '=':
- parser->stack[++parser->top].state = 11;
+ parser->stack[++parser->top].state = 12;
return 1;
default:
@@ -255,8 +252,8 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
case 7:
switch (token) {
- case 'x':
- parser->stack[++parser->top].state = 12;
+ case 'e':
+ parser->stack[++parser->top].state = 13;
return 1;
default:
@@ -266,8 +263,8 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
case 8:
switch (token) {
- case 'e':
- parser->stack[++parser->top].state = 13;
+ case 'x':
+ parser->stack[++parser->top].state = 14;
return 1;
default:
@@ -277,8 +274,8 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
case 9:
switch (token) {
- case 'o':
- parser->stack[++parser->top].state = 14;
+ case 'e':
+ parser->stack[++parser->top].state = 15;
return 1;
default:
@@ -288,8 +285,8 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
case 10:
switch (token) {
- case 'y':
- parser->stack[++parser->top].state = 15;
+ case 'o':
+ parser->stack[++parser->top].state = 16;
return 1;
default:
@@ -299,16 +296,39 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
case 11:
switch (token) {
+ case 'y':
+ parser->stack[++parser->top].state = 17;
+ return 1;
+
default:
- parser->stack[parser->top].value.symbol_rhs = parse_reduce_10(grammar);
- parser->stack[++parser->top].state = 16;
+ return -1;
}
break;
case 12:
switch (token) {
+ default:
+ result.symbol_rhs = parse_reduce_11(grammar);
+ parser->stack[parser->top].value.symbol_rhs = result.symbol_rhs;
+ parser->stack[++parser->top].state = 18;
+ }
+ break;
+
+ case 13:
+ switch (token) {
+ case 's':
+ parser->stack[++parser->top].state = 19;
+ return 1;
+
+ default:
+ return -1;
+ }
+ break;
+
+ case 14:
+ switch (token) {
case 't':
- parser->stack[++parser->top].state = 17;
+ parser->stack[++parser->top].state = 20;
return 1;
default:
@@ -316,10 +336,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 13:
+ case 15:
switch (token) {
case 'a':
- parser->stack[++parser->top].state = 18;
+ parser->stack[++parser->top].state = 21;
return 1;
default:
@@ -327,10 +347,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 14:
+ case 16:
switch (token) {
case 'u':
- parser->stack[++parser->top].state = 19;
+ parser->stack[++parser->top].state = 22;
return 1;
default:
@@ -338,10 +358,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 15:
+ case 17:
switch (token) {
case 'p':
- parser->stack[++parser->top].state = 20;
+ parser->stack[++parser->top].state = 23;
return 1;
default:
@@ -349,34 +369,34 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 16:
+ case 18:
switch (token) {
case TOK_BLOCK:
- parser->stack[++parser->top].state = 24;
+ parser->stack[++parser->top].state = 27;
return 1;
case TOK_CHAR:
- parser->stack[++parser->top].state = 25;
+ parser->stack[++parser->top].state = 28;
return 1;
case TOK_SQBLOCK:
- parser->stack[++parser->top].state = 26;
+ parser->stack[++parser->top].state = 29;
return 1;
case TOK_STRING:
- parser->stack[++parser->top].state = 27;
+ parser->stack[++parser->top].state = 30;
return 1;
case TOK_SYMBOL_LC:
- parser->stack[++parser->top].state = 28;
+ parser->stack[++parser->top].state = 31;
return 1;
case TOK_SYMBOL_UC:
- parser->stack[++parser->top].state = 29;
+ parser->stack[++parser->top].state = 32;
return 1;
case ';':
- parser->stack[++parser->top].state = 30;
+ parser->stack[++parser->top].state = 33;
return 1;
default:
@@ -384,10 +404,21 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 17:
+ case 19:
+ switch (token) {
+ case 't':
+ parser->stack[++parser->top].state = 34;
+ return 1;
+
+ default:
+ return -1;
+ }
+ break;
+
+ case 20:
switch (token) {
case 'r':
- parser->stack[++parser->top].state = 31;
+ parser->stack[++parser->top].state = 35;
return 1;
default:
@@ -395,10 +426,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 18:
+ case 21:
switch (token) {
case 'd':
- parser->stack[++parser->top].state = 32;
+ parser->stack[++parser->top].state = 36;
return 1;
default:
@@ -406,10 +437,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 19:
+ case 22:
switch (token) {
case 'r':
- parser->stack[++parser->top].state = 33;
+ parser->stack[++parser->top].state = 37;
return 1;
default:
@@ -417,10 +448,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 20:
+ case 23:
switch (token) {
case 'e':
- parser->stack[++parser->top].state = 34;
+ parser->stack[++parser->top].state = 38;
return 1;
default:
@@ -428,122 +459,172 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 21:
+ case 24:
switch (token) {
default:
parser->top -= 5;
- parser->stack[parser->top].value.symbol_rule = parse_reduce_9(parser->stack[parser->top + 0].value.token.str, parser->stack[parser->top + 3].value.symbol_rhs, parser->stack[parser->top + 4].value.symbol_action, grammar);
+ result.symbol_rule = parse_reduce_10(parser->stack[parser->top + 0].value.token.str, parser->stack[parser->top + 3].value.symbol_rhs, parser->stack[parser->top + 4].value.symbol_action, grammar);
+ free_string(parser->stack[parser->top + 0].value.token.str);
+ free_string(parser->stack[parser->top + 4].value.symbol_action);
+ parser->stack[parser->top].value.symbol_rule = result.symbol_rule;
parser->stack[++parser->top].state = 3;
}
break;
- case 22:
+ case 25:
switch (token) {
case '(':
- parser->stack[++parser->top].state = 35;
+ parser->stack[++parser->top].state = 39;
return 1;
default:
parser->top -= 2;
- parser->stack[parser->top].value.symbol_rhs = parse_reduce_11(parser->stack[parser->top + 0].value.symbol_rhs, parser->stack[parser->top + 1].value.symbol_symbol, grammar);
- parser->stack[++parser->top].state = 16;
+ result.symbol_rhs = parse_reduce_12(parser->stack[parser->top + 0].value.symbol_rhs, parser->stack[parser->top + 1].value.symbol_symbol, grammar);
+ free_symbol(parser->stack[parser->top + 1].value.symbol_symbol);
+ parser->stack[parser->top].value.symbol_rhs = result.symbol_rhs;
+ parser->stack[++parser->top].state = 18;
}
break;
- case 23:
+ case 26:
switch (token) {
default:
parser->top -= 1;
- parser->stack[parser->top].value.symbol_symbol = parse_reduce_17(parser->stack[parser->top + 0].value.symbol_term, grammar);
- parser->stack[++parser->top].state = 22;
+ result.symbol_symbol = parse_reduce_18(parser->stack[parser->top + 0].value.symbol_term, grammar);
+ free_symbol(parser->stack[parser->top + 0].value.symbol_term);
+ parser->stack[parser->top].value.symbol_symbol = result.symbol_symbol;
+ switch (parser->stack[parser->top].state) {
+ case 18:
+ parser->stack[++parser->top].state = 25;
+ break;
+
+ case 66:
+ parser->stack[++parser->top].state = 68;
+ break;
+
+ }
}
break;
- case 24:
+ case 27:
switch (token) {
default:
parser->top -= 1;
- parser->stack[parser->top].value.symbol_action = parse_reduce_15(parser->stack[parser->top + 0].value.token.str, grammar);
- parser->stack[++parser->top].state = 21;
+ result.symbol_action = parse_reduce_16(parser->stack[parser->top + 0].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 0].value.token.str);
+ parser->stack[parser->top].value.symbol_action = result.symbol_action;
+ parser->stack[++parser->top].state = 24;
}
break;
- case 25:
+ case 28:
switch (token) {
default:
parser->top -= 1;
- parser->stack[parser->top].value.symbol_term = parse_reduce_20(parser->stack[parser->top + 0].value.token.c, grammar);
+ result.symbol_term = parse_reduce_21(parser->stack[parser->top + 0].value.token.c, grammar);
+ parser->stack[parser->top].value.symbol_term = result.symbol_term;
switch (parser->stack[parser->top].state) {
- case 16:
- parser->stack[++parser->top].state = 23;
+ case 18:
+ case 66:
+ parser->stack[++parser->top].state = 26;
break;
- case 34:
- parser->stack[++parser->top].state = 39;
+ case 38:
+ parser->stack[++parser->top].state = 44;
break;
}
}
break;
- case 26:
+ case 29:
switch (token) {
default:
parser->top -= 1;
- parser->stack[parser->top].value.symbol_action = parse_reduce_16(parser->stack[parser->top + 0].value.token.str, grammar);
- parser->stack[++parser->top].state = 21;
+ result.symbol_action = parse_reduce_17(parser->stack[parser->top + 0].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 0].value.token.str);
+ parser->stack[parser->top].value.symbol_action = result.symbol_action;
+ parser->stack[++parser->top].state = 24;
}
break;
- case 27:
+ case 30:
switch (token) {
default:
parser->top -= 2;
- parser->stack[parser->top].value.symbol_rhs = parse_reduce_13(parser->stack[parser->top + 0].value.symbol_rhs, parser->stack[parser->top + 1].value.token.str, grammar);
- parser->stack[++parser->top].state = 16;
+ result.symbol_rhs = parse_reduce_14(parser->stack[parser->top + 0].value.symbol_rhs, parser->stack[parser->top + 1].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 1].value.token.str);
+ parser->stack[parser->top].value.symbol_rhs = result.symbol_rhs;
+ parser->stack[++parser->top].state = 18;
}
break;
- case 28:
+ case 31:
switch (token) {
default:
parser->top -= 1;
- parser->stack[parser->top].value.symbol_symbol = parse_reduce_18(parser->stack[parser->top + 0].value.token.str, grammar);
- parser->stack[++parser->top].state = 22;
+ result.symbol_symbol = parse_reduce_19(parser->stack[parser->top + 0].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 0].value.token.str);
+ parser->stack[parser->top].value.symbol_symbol = result.symbol_symbol;
+ switch (parser->stack[parser->top].state) {
+ case 18:
+ parser->stack[++parser->top].state = 25;
+ break;
+
+ case 66:
+ parser->stack[++parser->top].state = 68;
+ break;
+
+ }
}
break;
- case 29:
+ case 32:
switch (token) {
default:
parser->top -= 1;
- parser->stack[parser->top].value.symbol_term = parse_reduce_19(parser->stack[parser->top + 0].value.token.str, grammar);
+ result.symbol_term = parse_reduce_20(parser->stack[parser->top + 0].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 0].value.token.str);
+ parser->stack[parser->top].value.symbol_term = result.symbol_term;
switch (parser->stack[parser->top].state) {
- case 16:
- parser->stack[++parser->top].state = 23;
+ case 18:
+ case 66:
+ parser->stack[++parser->top].state = 26;
break;
- case 34:
- parser->stack[++parser->top].state = 39;
+ case 38:
+ parser->stack[++parser->top].state = 44;
break;
}
}
break;
- case 30:
+ case 33:
switch (token) {
default:
parser->top -= 1;
- parser->stack[parser->top].value.symbol_action = parse_reduce_14(grammar);
- parser->stack[++parser->top].state = 21;
+ result.symbol_action = parse_reduce_15(grammar);
+ parser->stack[parser->top].value.symbol_action = result.symbol_action;
+ parser->stack[++parser->top].state = 24;
}
break;
- case 31:
+ case 34:
+ switch (token) {
+ case 'r':
+ parser->stack[++parser->top].state = 40;
+ return 1;
+
+ default:
+ return -1;
+ }
+ break;
+
+ case 35:
switch (token) {
case 'a':
- parser->stack[++parser->top].state = 36;
+ parser->stack[++parser->top].state = 41;
return 1;
default:
@@ -551,10 +632,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 32:
+ case 36:
switch (token) {
case 'e':
- parser->stack[++parser->top].state = 37;
+ parser->stack[++parser->top].state = 42;
return 1;
default:
@@ -562,10 +643,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 33:
+ case 37:
switch (token) {
case 'c':
- parser->stack[++parser->top].state = 38;
+ parser->stack[++parser->top].state = 43;
return 1;
default:
@@ -573,18 +654,18 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 34:
+ case 38:
switch (token) {
case TOK_CHAR:
- parser->stack[++parser->top].state = 25;
+ parser->stack[++parser->top].state = 28;
return 1;
case TOK_SYMBOL_UC:
- parser->stack[++parser->top].state = 29;
+ parser->stack[++parser->top].state = 32;
return 1;
case TOK_SYMBOL_LC:
- parser->stack[++parser->top].state = 40;
+ parser->stack[++parser->top].state = 45;
return 1;
default:
@@ -592,18 +673,18 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 35:
+ case 39:
switch (token) {
case TOK_SYMBOL:
- parser->stack[++parser->top].state = 42;
+ parser->stack[++parser->top].state = 47;
return 1;
case TOK_SYMBOL_LC:
- parser->stack[++parser->top].state = 43;
+ parser->stack[++parser->top].state = 48;
return 1;
case TOK_SYMBOL_UC:
- parser->stack[++parser->top].state = 44;
+ parser->stack[++parser->top].state = 49;
return 1;
default:
@@ -611,10 +692,21 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 36:
+ case 40:
+ switch (token) {
+ case 'u':
+ parser->stack[++parser->top].state = 50;
+ return 1;
+
+ default:
+ return -1;
+ }
+ break;
+
+ case 41:
switch (token) {
case '_':
- parser->stack[++parser->top].state = 45;
+ parser->stack[++parser->top].state = 51;
return 1;
default:
@@ -622,10 +714,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 37:
+ case 42:
switch (token) {
case 'r':
- parser->stack[++parser->top].state = 46;
+ parser->stack[++parser->top].state = 52;
return 1;
default:
@@ -633,10 +725,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 38:
+ case 43:
switch (token) {
case 'e':
- parser->stack[++parser->top].state = 47;
+ parser->stack[++parser->top].state = 53;
return 1;
default:
@@ -644,10 +736,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 39:
+ case 44:
switch (token) {
case TOK_BLOCK:
- parser->stack[++parser->top].state = 48;
+ parser->stack[++parser->top].state = 54;
return 1;
default:
@@ -655,10 +747,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 40:
+ case 45:
switch (token) {
case TOK_BLOCK:
- parser->stack[++parser->top].state = 49;
+ parser->stack[++parser->top].state = 55;
return 1;
default:
@@ -666,10 +758,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 41:
+ case 46:
switch (token) {
case ')':
- parser->stack[++parser->top].state = 50;
+ parser->stack[++parser->top].state = 56;
return 1;
default:
@@ -677,76 +769,105 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 42:
+ case 47:
switch (token) {
default:
parser->top -= 1;
- parser->stack[parser->top].value.symbol_varname = parse_reduce_23(parser->stack[parser->top + 0].value.token.str, grammar);
+ result.symbol_varname = parse_reduce_24(parser->stack[parser->top + 0].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 0].value.token.str);
+ parser->stack[parser->top].value.symbol_varname = result.symbol_varname;
switch (parser->stack[parser->top].state) {
- case 35:
- parser->stack[++parser->top].state = 41;
+ case 39:
+ parser->stack[++parser->top].state = 46;
break;
- case 48:
- parser->stack[++parser->top].state = 54;
+ case 54:
+ parser->stack[++parser->top].state = 61;
break;
- case 57:
- parser->stack[++parser->top].state = 58;
+ case 67:
+ parser->stack[++parser->top].state = 69;
+ break;
+
+ case 68:
+ parser->stack[++parser->top].state = 70;
break;
}
}
break;
- case 43:
+ case 48:
switch (token) {
default:
parser->top -= 1;
- parser->stack[parser->top].value.symbol_varname = parse_reduce_21(parser->stack[parser->top + 0].value.token.str, grammar);
+ result.symbol_varname = parse_reduce_22(parser->stack[parser->top + 0].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 0].value.token.str);
+ parser->stack[parser->top].value.symbol_varname = result.symbol_varname;
switch (parser->stack[parser->top].state) {
- case 35:
- parser->stack[++parser->top].state = 41;
+ case 39:
+ parser->stack[++parser->top].state = 46;
+ break;
+
+ case 54:
+ parser->stack[++parser->top].state = 61;
break;
- case 48:
- parser->stack[++parser->top].state = 54;
+ case 67:
+ parser->stack[++parser->top].state = 69;
break;
- case 57:
- parser->stack[++parser->top].state = 58;
+ case 68:
+ parser->stack[++parser->top].state = 70;
break;
}
}
break;
- case 44:
+ case 49:
switch (token) {
default:
parser->top -= 1;
- parser->stack[parser->top].value.symbol_varname = parse_reduce_22(parser->stack[parser->top + 0].value.token.str, grammar);
+ result.symbol_varname = parse_reduce_23(parser->stack[parser->top + 0].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 0].value.token.str);
+ parser->stack[parser->top].value.symbol_varname = result.symbol_varname;
switch (parser->stack[parser->top].state) {
- case 35:
- parser->stack[++parser->top].state = 41;
+ case 39:
+ parser->stack[++parser->top].state = 46;
+ break;
+
+ case 54:
+ parser->stack[++parser->top].state = 61;
break;
- case 48:
- parser->stack[++parser->top].state = 54;
+ case 67:
+ parser->stack[++parser->top].state = 69;
break;
- case 57:
- parser->stack[++parser->top].state = 58;
+ case 68:
+ parser->stack[++parser->top].state = 70;
break;
}
}
break;
- case 45:
+ case 50:
+ switch (token) {
+ case 'c':
+ parser->stack[++parser->top].state = 57;
+ return 1;
+
+ default:
+ return -1;
+ }
+ break;
+
+ case 51:
switch (token) {
case 'a':
- parser->stack[++parser->top].state = 51;
+ parser->stack[++parser->top].state = 58;
return 1;
default:
@@ -754,10 +875,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 46:
+ case 52:
switch (token) {
case TOK_BLOCK:
- parser->stack[++parser->top].state = 52;
+ parser->stack[++parser->top].state = 59;
return 1;
default:
@@ -765,10 +886,10 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 47:
+ case 53:
switch (token) {
case TOK_BLOCK:
- parser->stack[++parser->top].state = 53;
+ parser->stack[++parser->top].state = 60;
return 1;
default:
@@ -776,18 +897,18 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 48:
+ case 54:
switch (token) {
case TOK_SYMBOL:
- parser->stack[++parser->top].state = 42;
+ parser->stack[++parser->top].state = 47;
return 1;
case TOK_SYMBOL_LC:
- parser->stack[++parser->top].state = 43;
+ parser->stack[++parser->top].state = 48;
return 1;
case TOK_SYMBOL_UC:
- parser->stack[++parser->top].state = 44;
+ parser->stack[++parser->top].state = 49;
return 1;
default:
@@ -795,28 +916,44 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 49:
+ case 55:
switch (token) {
default:
parser->top -= 7;
- parse_reduce_4(parser->stack[parser->top + 5].value.token.str, parser->stack[parser->top + 6].value.token.str, grammar);
+ parse_reduce_3(parser->stack[parser->top + 5].value.token.str, parser->stack[parser->top + 6].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 5].value.token.str);
+ free_string(parser->stack[parser->top + 6].value.token.str);
parser->stack[++parser->top].state = 2;
}
break;
- case 50:
+ case 56:
switch (token) {
default:
parser->top -= 5;
- parser->stack[parser->top].value.symbol_rhs = parse_reduce_12(parser->stack[parser->top + 0].value.symbol_rhs, parser->stack[parser->top + 1].value.symbol_symbol, parser->stack[parser->top + 3].value.symbol_varname, grammar);
- parser->stack[++parser->top].state = 16;
+ result.symbol_rhs = parse_reduce_13(parser->stack[parser->top + 0].value.symbol_rhs, parser->stack[parser->top + 1].value.symbol_symbol, parser->stack[parser->top + 3].value.symbol_varname, grammar);
+ free_symbol(parser->stack[parser->top + 1].value.symbol_symbol);
+ free_string(parser->stack[parser->top + 3].value.symbol_varname);
+ parser->stack[parser->top].value.symbol_rhs = result.symbol_rhs;
+ parser->stack[++parser->top].state = 18;
}
break;
- case 51:
+ case 57:
+ switch (token) {
+ case 't':
+ parser->stack[++parser->top].state = 62;
+ return 1;
+
+ default:
+ return -1;
+ }
+ break;
+
+ case 58:
switch (token) {
case 'r':
- parser->stack[++parser->top].state = 55;
+ parser->stack[++parser->top].state = 63;
return 1;
default:
@@ -824,37 +961,53 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 52:
+ case 59:
switch (token) {
default:
parser->top -= 8;
parse_reduce_7(parser->stack[parser->top + 7].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 7].value.token.str);
parser->stack[++parser->top].state = 2;
}
break;
- case 53:
+ case 60:
switch (token) {
default:
parser->top -= 8;
parse_reduce_6(parser->stack[parser->top + 7].value.token.str, grammar);
+ free_string(parser->stack[parser->top + 7].value.token.str);
parser->stack[++parser->top].state = 2;
}
break;
- case 54:
+ case 61:
switch (token) {
default:
parser->top -= 8;
- parse_reduce_5(parser->stack[parser->top + 5].value.symbol_term, parser->stack[parser->top + 6].value.token.str, parser->stack[parser->top + 7].value.symbol_varname, grammar);
+ parse_reduce_4(parser->stack[parser->top + 5].value.symbol_term, parser->stack[parser->top + 6].value.token.str, parser->stack[parser->top + 7].value.symbol_varname, grammar);
+ free_symbol(parser->stack[parser->top + 5].value.symbol_term);
+ free_string(parser->stack[parser->top + 6].value.token.str);
+ free_string(parser->stack[parser->top + 7].value.symbol_varname);
parser->stack[++parser->top].state = 2;
}
break;
- case 55:
+ case 62:
+ switch (token) {
+ case 'o':
+ parser->stack[++parser->top].state = 64;
+ return 1;
+
+ default:
+ return -1;
+ }
+ break;
+
+ case 63:
switch (token) {
case 'g':
- parser->stack[++parser->top].state = 56;
+ parser->stack[++parser->top].state = 65;
return 1;
default:
@@ -862,10 +1015,21 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 56:
+ case 64:
+ switch (token) {
+ case 'r':
+ parser->stack[++parser->top].state = 66;
+ return 1;
+
+ default:
+ return -1;
+ }
+ break;
+
+ case 65:
switch (token) {
case TOK_BLOCK:
- parser->stack[++parser->top].state = 57;
+ parser->stack[++parser->top].state = 67;
return 1;
default:
@@ -873,18 +1037,37 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 57:
+ case 66:
+ switch (token) {
+ case TOK_CHAR:
+ parser->stack[++parser->top].state = 28;
+ return 1;
+
+ case TOK_SYMBOL_LC:
+ parser->stack[++parser->top].state = 31;
+ return 1;
+
+ case TOK_SYMBOL_UC:
+ parser->stack[++parser->top].state = 32;
+ return 1;
+
+ default:
+ return -1;
+ }
+ break;
+
+ case 67:
switch (token) {
case TOK_SYMBOL:
- parser->stack[++parser->top].state = 42;
+ parser->stack[++parser->top].state = 47;
return 1;
case TOK_SYMBOL_LC:
- parser->stack[++parser->top].state = 43;
+ parser->stack[++parser->top].state = 48;
return 1;
case TOK_SYMBOL_UC:
- parser->stack[++parser->top].state = 44;
+ parser->stack[++parser->top].state = 49;
return 1;
default:
@@ -892,11 +1075,43 @@ static int parse_do_push(parse_context_t *parser, int token, __attribute__((unus
}
break;
- case 58:
+ case 68:
+ switch (token) {
+ case TOK_SYMBOL:
+ parser->stack[++parser->top].state = 47;
+ return 1;
+
+ case TOK_SYMBOL_LC:
+ parser->stack[++parser->top].state = 48;
+ return 1;
+
+ case TOK_SYMBOL_UC:
+ parser->stack[++parser->top].state = 49;
+ return 1;
+
+ default:
+ return -1;
+ }
+ break;
+
+ case 69:
switch (token) {
default:
parser->top -= 12;
parse_reduce_8(parser->stack[parser->top + 10].value.token.str, parser->stack[parser->top + 11].value.symbol_varname, grammar);
+ free_string(parser->stack[parser->top + 10].value.token.str);
+ free_string(parser->stack[parser->top + 11].value.symbol_varname);
+ parser->stack[++parser->top].state = 2;
+ }
+ break;
+
+ case 70:
+ switch (token) {
+ default:
+ parser->top -= 13;
+ parse_reduce_5(parser->stack[parser->top + 11].value.symbol_symbol, parser->stack[parser->top + 12].value.symbol_varname, grammar);
+ free_symbol(parser->stack[parser->top + 11].value.symbol_symbol);
+ free_string(parser->stack[parser->top + 12].value.symbol_varname);
parser->stack[++parser->top].state = 2;
}
break;
diff --git a/src/parse.y b/src/parse.y
index ed946e0..dba747e 100644
--- a/src/parse.y
+++ b/src/parse.y
@@ -1,22 +1,60 @@
+%header {
+#include "grammar.hpp"
+}
+
+%source {
+static inline void free_string(std::string *v) {
+ delete v;
+}
+
+static inline void free_symbol(solar::symbol_t *v) {
+ delete v;
+}
+
+static inline void free_rule(solar::rule_t *v) {
+ delete v;
+}
+}
+
+
%type SYMBOL {std::string *} str
+%destructor SYMBOL free_string
+
%type SYMBOL_UC {std::string *} str
+%destructor SYMBOL_UC free_string
+
%type SYMBOL_LC {std::string *} str
+%destructor SYMBOL_LC free_string
+
%type BLOCK {std::string *} str
+%destructor BLOCK free_string
+
%type SQBLOCK {std::string *} str
+%destructor SQBLOCK free_string
+
%type STRING {std::string *} str
+%destructor STRING free_string
+
%type CHAR {char} c
+
%type rule {solar::rule_t *}
+%destructor rule free_rule
+
%type rhs {std::pair<std::vector<solar::symbol_t>, std::vector<std::string>> *}
+
%type action {std::string *}
+%destructor action free_string
+
%type symbol {solar::symbol_t *}
+%destructor symbol free_symbol
+
%type term {solar::symbol_t *}
-%type varname {std::string *}
+%destructor term free_symbol
+%type varname {std::string *}
+%destructor varname free_string
-%header {
-#include "grammar.hpp"
-}
%extra_arg {__attribute__((unused)) solar::grammar_t *} grammar
@@ -24,57 +62,45 @@
grammar |=;
grammar |= grammar directive;
-directive |= rule(rule) {
- if (grammar->rules.empty()) {
- solar::item_t init("");
- init.get_rhs().push_back(solar::symbol_t::make_nonterm(rule->item.get_lhs().c_str()));
- grammar->rules.emplace_back(solar::rule_t {std::move(init), std::vector<std::string>(), std::string()});
- }
-
- grammar->rules.push_back(*rule);
- delete rule;
-}
directive |= "%type" SYMBOL_LC(nonterm) BLOCK(type) {
grammar->nonterm_types.insert(std::make_pair(*nonterm, *type));
-
- delete nonterm;
- delete type;
}
directive |= "%type" term(term) BLOCK(type) varname(name) {
grammar->term_types.insert(std::make_pair(*term, std::make_pair(*type, *name)));
+}
- delete term;
- delete type;
- delete name;
+directive |= "%destructor" symbol(sym) varname(name) {
+ grammar->destructors.insert(std::make_pair(*sym, *name));
}
directive |= "%source" BLOCK(block) {
grammar->source_block = *block;
- delete block;
}
directive |= "%header" BLOCK(block) {
grammar->header_block = *block;
- delete block;
}
directive |= "%extra_arg" BLOCK(type) varname(name) {
grammar->extra_args.push_back(std::make_pair(*type, *name));
+}
- delete type;
- delete name;
+directive |= rule(rule) {
+ if (grammar->rules.empty()) {
+ solar::item_t init("");
+ init.get_rhs().push_back(solar::symbol_t::make_nonterm(rule->item.get_lhs().c_str()));
+ grammar->rules.emplace_back(solar::rule_t {std::move(init), std::vector<std::string>(), std::string()});
+ }
+
+ grammar->rules.push_back(*rule);
}
rule |= SYMBOL_LC(lhs) "|=" rhs(rhs) action(action) {
auto *ret = new solar::rule_t {solar::item_t(*lhs, rhs->first), rhs->second, *action};
-
- delete lhs;
delete rhs;
- delete action;
-
return ret;
}
@@ -84,7 +110,6 @@ rhs |= [new std::pair<std::vector<solar::symbol_t>, std::vector<std::string>>()]
rhs |= rhs(rhs) symbol(sym) {
rhs->first.push_back(*sym);
rhs->second.emplace_back();
- delete sym;
return rhs;
}
@@ -93,9 +118,6 @@ rhs |= rhs(rhs) symbol(sym) '(' varname(var) ')' {
rhs->first.push_back(*sym);
rhs->second.push_back(*var);
- delete sym;
- delete var;
-
return rhs;
}
@@ -105,40 +127,21 @@ rhs |= rhs(rhs) STRING(str) {
rhs->second.emplace_back();
}
- delete str;
-
return rhs;
}
action |= ';' [new std::string]
+action |= BLOCK(v) [new std::string(*v)]
+action |= SQBLOCK(v) [new std::string("\n\treturn " + *v + ";\n")]
-action |= BLOCK(v) [v]
-action |= SQBLOCK(v) {
- *v = "\n\treturn " + *v + ";\n";
- return v;
-}
-
-
-symbol |= term(v) [v]
-
-symbol |= SYMBOL_LC(v) {
- solar::symbol_t *ret = new solar::symbol_t(solar::symbol_t::make_nonterm(*v));
- delete v;
- return ret;
-}
-
-
-term |= SYMBOL_UC(v) {
- solar::symbol_t *ret = new solar::symbol_t(solar::symbol_t::make_term(*v));
- delete v;
- return ret;
-}
+symbol |= term(v) [new solar::symbol_t(*v)]
+symbol |= SYMBOL_LC(v) [new solar::symbol_t(solar::symbol_t::make_nonterm(*v))]
+term |= SYMBOL_UC(v) [new solar::symbol_t(solar::symbol_t::make_term(*v))]
term |= CHAR(v) [new solar::symbol_t(solar::symbol_t::make_char(v))]
-
-varname |= SYMBOL_LC(v) [v]
-varname |= SYMBOL_UC(v) [v]
-varname |= SYMBOL(v) [v]
+varname |= SYMBOL_LC(v) [new std::string(*v)]
+varname |= SYMBOL_UC(v) [new std::string(*v)]
+varname |= SYMBOL(v)[new std::string(*v)]