diff options
author | David Tolnay <dtolnay@gmail.com> | 2015-07-18 23:44:06 -0700 |
---|---|---|
committer | David Tolnay <dtolnay@gmail.com> | 2015-07-19 09:43:10 -0700 |
commit | f5a7bba986d82e0dfc5fd7bce2b8ed78a5b970b5 (patch) | |
tree | a44b961104d70aad703d508278a835f798c5702b /parser.y | |
parent | 66ef8e2c243207bb4edd88c409ce90fc95e0dffe (diff) |
Resolve remaining shift/reduce conflicts involving '?'
By lowering the precedence of rules that should never use
the generic Exp '?' rule.
Diffstat (limited to 'parser.y')
-rw-r--r-- | parser.y | 30 |
1 files changed, 14 insertions, 16 deletions
@@ -90,8 +90,9 @@ struct lexer_param; %token QQSTRING_INTERP_END %token QQSTRING_END -/* see Exp '?' rule */ -%expect 9 +/* Instead of raising this, find a way to use precedence to resolve + * shift-reduce conflicts. */ +%expect 0 %precedence FUNCDEF %right '|' @@ -103,6 +104,8 @@ struct lexer_param; %nonassoc NEQ EQ '<' '>' LESSEQ GREATEREQ %left '+' '-' %left '*' '/' '%' +%precedence NONOPT /* non-optional; rules for which a specialized + '?' rule should be preferred over Exp '?' */ %precedence '?' %precedence "try" %precedence "catch" @@ -355,11 +358,6 @@ Term "as" Pattern '|' Exp { jv_free(v); } | -// This rule conflicts with all the other rules using the '?' operator. -// It doesn't matter which bison prefers: all of them result in the same -// syntax and semantics, but the more specific rules optimize better -// because they use opcodes specifically made for the purpose. We -// expect 9 such conflicts. Exp '?' { $$ = gen_try($1, gen_op_simple(BACKTRACK)); } | @@ -636,16 +634,16 @@ Term '.' String '?' { '.' String '?' { $$ = gen_index_opt(gen_noop(), $2); } | -Term FIELD { +Term FIELD %prec NONOPT { $$ = gen_index($1, gen_const($2)); } | -FIELD { +FIELD %prec NONOPT { $$ = gen_index(gen_noop(), gen_const($1)); } | -Term '.' String { +Term '.' String %prec NONOPT { $$ = gen_index($1, $3); } | -'.' String { +'.' String %prec NONOPT { $$ = gen_index(gen_noop(), $2); } | '.' error { @@ -661,13 +659,13 @@ Term '.' String { Term '[' Exp ']' '?' { $$ = gen_index_opt($1, $3); } | -Term '[' Exp ']' { +Term '[' Exp ']' %prec NONOPT { $$ = gen_index($1, $3); } | Term '[' ']' '?' { $$ = block_join($1, gen_op_simple(EACH_OPT)); } | -Term '[' ']' { +Term '[' ']' %prec NONOPT { $$ = block_join($1, gen_op_simple(EACH)); } | Term '[' Exp ':' Exp ']' '?' { @@ -679,13 +677,13 @@ Term '[' Exp ':' ']' '?' { Term '[' ':' Exp ']' '?' { $$ = gen_slice_index($1, gen_const(jv_null()), $4, INDEX_OPT); } | -Term '[' Exp ':' Exp ']' { +Term '[' Exp ':' Exp ']' %prec NONOPT { $$ = gen_slice_index($1, $3, $5, INDEX); } | -Term '[' Exp ':' ']' { +Term '[' Exp ':' ']' %prec NONOPT { $$ = gen_slice_index($1, $3, gen_const(jv_null()), INDEX); } | -Term '[' ':' Exp ']' { +Term '[' ':' Exp ']' %prec NONOPT { $$ = gen_slice_index($1, gen_const(jv_null()), $4, INDEX); } | LITERAL { |