mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
Fix wrong "void value expression" error
* parse.y (value_expr_check): if either of `then` or `else` statements is not a void value expression, the whole `if` is not also a void value expression. [Bug #15932]
This commit is contained in:
parent
09a846085c
commit
01b3a38043
2 changed files with 28 additions and 12 deletions
34
parse.y
34
parse.y
|
@ -10521,10 +10521,10 @@ node_assign(struct parser_params *p, NODE *lhs, NODE *rhs, const YYLTYPE *loc)
|
|||
return lhs;
|
||||
}
|
||||
|
||||
static int
|
||||
value_expr_gen(struct parser_params *p, NODE *node)
|
||||
static NODE *
|
||||
value_expr_check(struct parser_params *p, NODE *node)
|
||||
{
|
||||
int cond = 0;
|
||||
NODE *void_node = 0, *vn;
|
||||
|
||||
if (!node) {
|
||||
rb_warning0("empty expression");
|
||||
|
@ -10536,9 +10536,7 @@ value_expr_gen(struct parser_params *p, NODE *node)
|
|||
case NODE_NEXT:
|
||||
case NODE_REDO:
|
||||
case NODE_RETRY:
|
||||
if (!cond) yyerror1(&node->nd_loc, "void value expression");
|
||||
/* or "control never reach"? */
|
||||
return FALSE;
|
||||
return void_node ? void_node : node;
|
||||
|
||||
case NODE_BLOCK:
|
||||
while (node->nd_next) {
|
||||
|
@ -10561,14 +10559,15 @@ value_expr_gen(struct parser_params *p, NODE *node)
|
|||
node = node->nd_body;
|
||||
break;
|
||||
}
|
||||
if (!value_expr(node->nd_body)) return FALSE;
|
||||
vn = value_expr_check(p, node->nd_body);
|
||||
if (!vn) return NULL;
|
||||
if (!void_node) void_node = vn;
|
||||
node = node->nd_else;
|
||||
break;
|
||||
|
||||
case NODE_AND:
|
||||
case NODE_OR:
|
||||
cond = 1;
|
||||
node = node->nd_2nd;
|
||||
node = node->nd_1st;
|
||||
break;
|
||||
|
||||
case NODE_LASGN:
|
||||
|
@ -10576,16 +10575,27 @@ value_expr_gen(struct parser_params *p, NODE *node)
|
|||
case NODE_DASGN_CURR:
|
||||
case NODE_MASGN:
|
||||
mark_lvar_used(p, node);
|
||||
return TRUE;
|
||||
return NULL;
|
||||
|
||||
default:
|
||||
return TRUE;
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static int
|
||||
value_expr_gen(struct parser_params *p, NODE *node)
|
||||
{
|
||||
NODE *void_node = value_expr_check(p, node);
|
||||
if (void_node) {
|
||||
yyerror1(&void_node->nd_loc, "void value expression");
|
||||
/* or "control never reach"? */
|
||||
return FALSE;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
static void
|
||||
void_expr(struct parser_params *p, NODE *node)
|
||||
{
|
||||
|
|
|
@ -1388,6 +1388,12 @@ eom
|
|||
assert_syntax_error('a|>-b', /unexpected '-'/)
|
||||
end
|
||||
|
||||
def test_value_expr_in_condition
|
||||
mesg = /void value expression/
|
||||
assert_syntax_error("tap {a = (true ? next : break)}", mesg)
|
||||
assert_valid_syntax("tap {a = (true ? true : break)}")
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def not_label(x) @result = x; @not_label ||= nil end
|
||||
|
|
Loading…
Add table
Reference in a new issue