Skip to content
Permalink

Comparing changes

Choose two branches to see what’s changed or to start a new pull request. If you need to, you can also or learn more about diff comparisons.

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also . Learn more about diff comparisons here.
base repository: crystal-lang/crystal
Failed to load repositories. Confirm that selected base ref is valid, then try again.
Loading
base: ed1e6e530b38
Choose a base ref
...
head repository: crystal-lang/crystal
Failed to load repositories. Confirm that selected head ref is valid, then try again.
Loading
compare: 16be884de9dc
Choose a head ref
  • 2 commits
  • 2 files changed
  • 1 contributor

Commits on Sep 7, 2017

  1. Copy the full SHA
    952d95f View commit details
  2. Copy the full SHA
    16be884 View commit details
Showing with 23 additions and 6 deletions.
  1. +5 −0 spec/compiler/parser/parser_spec.cr
  2. +18 −6 src/compiler/crystal/syntax/parser.cr
5 changes: 5 additions & 0 deletions spec/compiler/parser/parser_spec.cr
Original file line number Diff line number Diff line change
@@ -705,7 +705,10 @@ describe "Parser" do
it_parses "lib LibC\nalias Foo = Bar\nend", LibDef.new("LibC", [Alias.new("Foo", "Bar".path)] of ASTNode)
it_parses "lib LibC; struct Foo; include Bar; end; end", LibDef.new("LibC", [CStructOrUnionDef.new("Foo", Include.new("Bar".path))] of ASTNode)

it_parses "lib LibC\nfun SomeFun\nend", LibDef.new("LibC", [FunDef.new("SomeFun")] of ASTNode)

it_parses "fun foo(x : Int32) : Int64\nx\nend", FunDef.new("foo", [Arg.new("x", restriction: "Int32".path)], "Int64".path, body: "x".var)
assert_syntax_error "fun Foo : Int64\nend"

it_parses "lib LibC; {{ 1 }}; end", LibDef.new("LibC", body: [MacroExpression.new(1.int32)] of ASTNode)
it_parses "lib LibC; {% if 1 %}2{% end %}; end", LibDef.new("LibC", body: [MacroIf.new(1.int32, MacroLiteral.new("2"))] of ASTNode)
@@ -1297,6 +1300,8 @@ describe "Parser" do

it_parses "1 ** -x", Call.new(1.int32, "**", Call.new("x".call, "-"))

it_parses "foo.Bar", Call.new("foo".call, "Bar")

assert_syntax_error "return do\nend", "unexpected token: do"

%w(def macro class struct module fun alias abstract include extend lib).each do |keyword|
24 changes: 18 additions & 6 deletions src/compiler/crystal/syntax/parser.cr
Original file line number Diff line number Diff line change
@@ -550,7 +550,7 @@ module Crystal
end
end

AtomicWithMethodCheck = [:IDENT, :"+", :"-", :"*", :"/", :"%", :"|", :"&", :"^", :"**", :"<<", :"<", :"<=", :"==", :"!=", :"=~", :"!~", :">>", :">", :">=", :"<=>", :"===", :"[]", :"[]=", :"[]?", :"["]
AtomicWithMethodCheck = [:IDENT, :CONST, :"+", :"-", :"*", :"/", :"%", :"|", :"&", :"^", :"**", :"<<", :"<", :"<=", :"==", :"!=", :"=~", :"!~", :">>", :">", :">=", :"<=>", :"===", :"[]", :"[]=", :"[]?", :"["]

def parse_atomic_with_method
location = @token.location
@@ -619,7 +619,12 @@ module Crystal
elsif @token.type == :"["
return parse_atomic_method_suffix(atomic, location)
else
name = @token.type == :IDENT ? @token.value.to_s : @token.type.to_s
name = case @token.type
when :IDENT, :CONST
@token.value.to_s
else
@token.type.to_s
end
end_location = token_end_location

@wants_regex = false
@@ -1026,7 +1031,7 @@ module Crystal
when :fun
check_type_declaration do
check_not_inside_def("can't define fun inside def") do
parse_fun_def require_body: true
parse_fun_def top_level: true, require_body: true
end
end
when :alias
@@ -4864,7 +4869,7 @@ module Crystal
when :alias
parse_alias
when :fun
parse_fun_def
parse_fun_def(top_level: false)
when :type
parse_type_def
when :struct
@@ -4918,14 +4923,21 @@ module Crystal

IdentOrConst = [:IDENT, :CONST]

def parse_fun_def(require_body = false)
def parse_fun_def(top_level, require_body = false)
location = @token.location
doc = @token.doc

push_def if require_body

next_token_skip_space_or_newline
name = check_ident

name = if top_level
check_ident
else
check IdentOrConst
@token.value.to_s
end

next_token_skip_space_or_newline

if @token.type == :"="