Skip to content

Commit

Permalink
Fix x @y and x @@y in def parameters when y is reserved (#12922)
Browse files Browse the repository at this point in the history
Fixes #12914
  • Loading branch information
HertzDevil authored Jan 11, 2023
1 parent 8a7da87 commit 3db4bdd
Show file tree
Hide file tree
Showing 3 changed files with 13 additions and 4 deletions.
2 changes: 2 additions & 0 deletions spec/compiler/formatter/formatter_spec.cr
Original file line number Diff line number Diff line change
Expand Up @@ -209,6 +209,8 @@ describe Crystal::Formatter do
assert_format "def foo ( &@block) \n end", "def foo(&@block)\nend"
assert_format "def foo ( @select) \n end", "def foo(@select)\nend"
assert_format "def foo ( @@select) \n end", "def foo(@@select)\nend"
assert_format "def foo ( bar @select) \n end", "def foo(bar @select)\nend"
assert_format "def foo ( bar @@select) \n end", "def foo(bar @@select)\nend"
assert_format "def foo(a, &@b)\nend"
assert_format "def foo ( x = 1 ) \n end", "def foo(x = 1)\nend"
assert_format "def foo ( x : Int32 ) \n end", "def foo(x : Int32)\nend"
Expand Down
2 changes: 2 additions & 0 deletions spec/compiler/parser/parser_spec.cr
Original file line number Diff line number Diff line change
Expand Up @@ -268,6 +268,8 @@ module Crystal
it_parses "def foo(#{kw} foo); end", Def.new("foo", [Arg.new("foo", external_name: kw.to_s)])
it_parses "def foo(@#{kw}); end", Def.new("foo", [Arg.new("__arg0", external_name: kw.to_s)], [Assign.new("@#{kw}".instance_var, "__arg0".var)] of ASTNode)
it_parses "def foo(@@#{kw}); end", Def.new("foo", [Arg.new("__arg0", external_name: kw.to_s)], [Assign.new("@@#{kw}".class_var, "__arg0".var)] of ASTNode)
it_parses "def foo(x @#{kw}); end", Def.new("foo", [Arg.new("__arg0", external_name: "x")], [Assign.new("@#{kw}".instance_var, "__arg0".var)] of ASTNode)
it_parses "def foo(x @@#{kw}); end", Def.new("foo", [Arg.new("__arg0", external_name: "x")], [Assign.new("@@#{kw}".class_var, "__arg0".var)] of ASTNode)

assert_syntax_error "foo { |#{kw}| }", "cannot use '#{kw}' as a block parameter name", 1, 8
assert_syntax_error "foo { |(#{kw})| }", "cannot use '#{kw}' as a block parameter name", 1, 9
Expand Down
13 changes: 9 additions & 4 deletions src/compiler/crystal/syntax/parser.cr
Original file line number Diff line number Diff line change
Expand Up @@ -4041,8 +4041,12 @@ module Crystal
# def method(select __arg0)
# @select = __arg0
# end
if !external_name && invalid_internal_name?(param_name)
param_name, external_name = temp_arg_name, param_name
#
# The external name defaults to the internal one unless otherwise
# specified (i.e. `def method(foo @select)`).
if invalid_internal_name?(param_name)
external_name ||= param_name
param_name = temp_arg_name
end

ivar = InstanceVar.new(@token.value.to_s).at(location)
Expand All @@ -4062,8 +4066,9 @@ module Crystal
end

# Same case as :INSTANCE_VAR for things like @select
if !external_name && invalid_internal_name?(param_name)
param_name, external_name = temp_arg_name, param_name
if invalid_internal_name?(param_name)
external_name ||= param_name
param_name = temp_arg_name
end

cvar = ClassVar.new(@token.value.to_s).at(location)
Expand Down

0 comments on commit 3db4bdd

Please sign in to comment.