Skip to content

Commit f762e76

Browse files
authored
Add parens node in special cases :(=) and :(::) (#237)
1 parent c808a70 commit f762e76

File tree

2 files changed

+24
-27
lines changed

2 files changed

+24
-27
lines changed

src/parser.jl

Lines changed: 21 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -3023,18 +3023,17 @@ function parse_paren(ps::ParseState, check_identifiers=true)
30233023
emit(ps, mark, K"tuple", PARENS_FLAG)
30243024
elseif is_syntactic_operator(k)
30253025
# allow :(=) etc in unchecked contexts, eg quotes
3026-
# :(=) ==> (quote =)
3027-
if check_identifiers && !is_valid_identifier(k)
3028-
bump(ps, error="invalid identifier")
3029-
else
3030-
bump(ps)
3031-
end
3026+
# :(=) ==> (quote (parens =))
3027+
parse_atom(ps, check_identifiers)
30323028
bump_closing_token(ps, K")")
3033-
elseif !check_identifiers && k == K"::" && peek(ps, 2, skip_newlines=true) == K")"
3029+
emit(ps, mark, K"parens")
3030+
elseif !check_identifiers && k == K"::" &&
3031+
peek(ps, 2, skip_newlines=true) == K")"
30343032
# allow :(::) as a special case
3035-
# :(::) ==> (quote ::)
3033+
# :(::) ==> (quote (parens ::))
30363034
bump(ps)
30373035
bump(ps, TRIVIA_FLAG, skip_newlines=true)
3036+
emit(ps, mark, K"parens")
30383037
else
30393038
# Deal with all other cases of tuple or block syntax via the generic
30403039
# parse_brackets
@@ -3393,7 +3392,11 @@ function parse_atom(ps::ParseState, check_identifiers=true)
33933392
mark = position(ps)
33943393
leading_kind = peek(ps)
33953394
# todo: Reorder to put most likely tokens first?
3396-
if leading_kind == K"'"
3395+
if is_error(leading_kind)
3396+
# Errors for bad tokens are emitted in validate_tokens() rather than
3397+
# here.
3398+
bump(ps)
3399+
elseif leading_kind == K"'"
33973400
# char literal
33983401
bump(ps, TRIVIA_FLAG)
33993402
k = peek(ps)
@@ -3436,27 +3439,24 @@ function parse_atom(ps::ParseState, check_identifiers=true)
34363439
# :\nfoo ==> (quote (error-t) foo)
34373440
bump_trivia(ps, TRIVIA_FLAG, skip_newlines=true,
34383441
error="whitespace not allowed after `:` used for quoting")
3439-
# Heuristic recovery
3440-
bump(ps)
3441-
else
3442-
# Being inside quote makes keywords into identifiers at the
3443-
# first level of nesting
3444-
# :end ==> (quote end)
3445-
# :(end) ==> (quote (parens (error-t)))
3446-
# Being inside quote makes end non-special again (issue #27690)
3447-
# a[:(end)] ==> (ref a (quote (error-t end)))
3448-
parse_atom(ParseState(ps, end_symbol=false), false)
34493442
end
3443+
# Being inside quote makes keywords into identifiers at the
3444+
# first level of nesting
3445+
# :end ==> (quote end)
3446+
# :(end) ==> (quote (parens (error-t)))
3447+
# Being inside quote makes end non-special again (issue #27690)
3448+
# a[:(end)] ==> (ref a (quote (error-t end)))
3449+
parse_atom(ParseState(ps, end_symbol=false), false)
34503450
emit(ps, mark, K"quote")
3451-
elseif leading_kind == K"=" && is_plain_equals(peek_token(ps))
3451+
elseif check_identifiers && leading_kind == K"=" && is_plain_equals(peek_token(ps))
34523452
# = ==> (error =)
34533453
bump(ps, error="unexpected `=`")
34543454
elseif leading_kind == K"Identifier"
34553455
# xx ==> xx
34563456
# x₁ ==> x₁
34573457
bump(ps)
34583458
elseif is_operator(leading_kind)
3459-
if check_identifiers && is_syntactic_operator(leading_kind)
3459+
if check_identifiers && !is_valid_identifier(leading_kind)
34603460
# += ==> (error +=)
34613461
# .+= ==> (error .+=)
34623462
bump(ps, error="invalid identifier")
@@ -3558,10 +3558,6 @@ function parse_atom(ps::ParseState, check_identifiers=true)
35583558
"premature end of input" :
35593559
"unexpected closing token"
35603560
bump_invisible(ps, K"error", error=msg)
3561-
elseif is_error(leading_kind)
3562-
# Errors for bad tokens are emitted in validate_tokens() rather than
3563-
# here.
3564-
bump(ps)
35653561
else
35663562
bump(ps, error="invalid syntax atom")
35673563
end

test/parser.jl

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -783,8 +783,9 @@ tests = [
783783
"[x=1, y=2]" => "(vect (= x 1) (= y 2))"
784784
"[x=1, ; y=2]" => "(vect (= x 1) (parameters (= y 2)))"
785785
# parse_paren
786-
":(=)" => "(quote =)"
787-
":(::)" => "(quote ::)"
786+
":(=)" => "(quote (parens =))"
787+
":(::)" => "(quote (parens ::))"
788+
":(::\n)" => "(quote (parens ::))"
788789
"(function f \n end)" => "(parens (function f))"
789790
# braces
790791
"{x y}" => "(bracescat (row x y))"

0 commit comments

Comments
 (0)