From f168dbd9ef3d27ec629d323f8a0834d63b5d7baa Mon Sep 17 00:00:00 2001 From: nobu Date: Tue, 17 Apr 2018 01:22:26 +0000 Subject: [PATCH] parse.y: fix cmdarg in command_args * parse.y (call_args): fix invalid CMDARG state after command_args followed by tLBRACE_ARG. [ruby-core:86551] [Bug #14690] From: Ilya Bylich git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@63168 b2dd03c8-39d4-4d8f-98ff-823fe69b080e --- parse.y | 13 +++++++++++++ test/ruby/test_parse.rb | 4 ++++ 2 files changed, 17 insertions(+) diff --git a/parse.y b/parse.y index 21cb2884f7..655cd85031 100644 --- a/parse.y +++ b/parse.y @@ -2170,7 +2170,20 @@ command_args : { } call_args { + /* call_args can be followed by tLBRACE_ARG (that does CMDARG_PUSH(0) in the lexer) + * but the push must be done after CMDARG_POP() in the parser. + * So this code does CMDARG_POP() to pop 0 pushed by tLBRACE_ARG, + * CMDARG_POP() to pop 1 pushed by command_args, + * and CMDARG_PUSH(0) to restore back the flag set by tLBRACE_ARG. + */ + int lookahead = 0; + switch (yychar) { + case tLBRACE_ARG: + lookahead = 1; + } + if (lookahead) CMDARG_POP(); CMDARG_POP(); + if (lookahead) CMDARG_PUSH(0); $$ = $2; } ; diff --git a/test/ruby/test_parse.rb b/test/ruby/test_parse.rb index b05dbe2a0f..6160aa1452 100644 --- a/test/ruby/test_parse.rb +++ b/test/ruby/test_parse.rb @@ -1196,6 +1196,10 @@ x = __ENCODING__ end end + def test_cdmarg_after_command_args_and_tlbrace_arg + assert_valid_syntax('let () { m(a) do; end }') + end + =begin def test_past_scope_variable assert_warning(/past scope/) {catch {|tag| eval("BEGIN{throw tag}; tap {a = 1}; a")}}