From 47cdda370e55debe40d72c21fa520e32a3d00ac2 Mon Sep 17 00:00:00 2001 From: "Yukihiro \"Matz\" Matsumoto" Date: Thu, 3 Oct 2019 07:52:31 +0900 Subject: Need to reorder local variables defined in `opt`; fix #4746 For example, local variables in the following def: ```ruby def foo(a = (not_set = true), &block) ... end ``` should be `a, block, not_set`, but were `a, not_set, block`. --- mrbgems/mruby-compiler/core/parse.y | 17 +++++++++++++++-- 1 file changed, 15 insertions(+), 2 deletions(-) diff --git a/mrbgems/mruby-compiler/core/parse.y b/mrbgems/mruby-compiler/core/parse.y index 4abe1c506..f7ae3913f 100644 --- a/mrbgems/mruby-compiler/core/parse.y +++ b/mrbgems/mruby-compiler/core/parse.y @@ -763,6 +763,16 @@ new_args(parser_state *p, node *m, node *opt, mrb_sym rest, node *m2, node *tail n = cons(m2, tail); n = cons(nsym(rest), n); n = cons(opt, n); + while (opt) { + /* opt: (sym . (opt . lv)) -> (sym . opt) */ + node *lv = opt->car->cdr->cdr; + while (lv) { + local_add_f(p, sym(lv->car)); + lv = lv->cdr; + } + opt->car->cdr = opt->car->cdr->car; + opt = opt->cdr; + } return cons(m, n); } @@ -3502,6 +3512,7 @@ f_arg : f_arg_item f_opt_asgn : tIDENTIFIER '=' { local_add_f(p, $1); + local_nest(p); $$ = $1; } ; @@ -3509,14 +3520,16 @@ f_opt_asgn : tIDENTIFIER '=' f_opt : f_opt_asgn arg { void_expr_error(p, $2); - $$ = cons(nsym($1), $2); + $$ = cons(nsym($1), cons($2, locals_node(p))); + local_unnest(p); } ; f_block_opt : f_opt_asgn primary_value { void_expr_error(p, $2); - $$ = cons(nsym($1), $2); + $$ = cons(nsym($1), cons($2, locals_node(p))); + local_unnest(p); } ; -- cgit v1.2.3