Skip to content

Commit 2ca4b31

Browse files
committed
Disallow var syntax in string interpolation
The var"##" syntax should be disabled in string interpolation.
1 parent b0ff444 commit 2ca4b31

File tree

2 files changed

+18
-6
lines changed

2 files changed

+18
-6
lines changed

src/julia-parser.scm

Lines changed: 12 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2134,11 +2134,11 @@
21342134
(let* ((p (ts:port s))
21352135
(c (peek-char p)))
21362136
(cond ((identifier-start-char? c)
2137-
(let* ((atom (parse-atom s))
2137+
(let* ((t (require-token s))
21382138
(c (peek-char p)))
21392139
(if (ends-interpolated-atom? c)
2140-
atom
2141-
(error (string "interpolated variable $" atom " ends with invalid character \"" c "\"; use \"$(" atom ")\" instead.")))))
2140+
(take-token s)
2141+
(error (string "interpolated variable $" t " ends with invalid character \"" c "\"; use \"$(" t ")\" instead.")))))
21422142
((eqv? c #\()
21432143
(read-char p)
21442144
(let ((ex (parse-eq* s))
@@ -2285,14 +2285,20 @@
22852285
(if (closing-token? t)
22862286
(error (string "unexpected \"" (take-token s) "\"")))))
22872287
(take-token s)
2288-
(if (and (eq? t 'var) (eqv? (peek-token s) #\") (not (ts:space? s)))
2288+
(if (and (eq? t 'var)
2289+
(if (or (ts:pbtok s) (ts:last-tok s))
2290+
(and (eqv? (peek-token s) #\") (not (ts:space? s)))
2291+
;; Hack: avoid peek-token if possible to preserve
2292+
;; (io.pos (ts:port s)) for non-greedy Meta.parse
2293+
(eqv? (peek-char (ts:port s)) #\")))
22892294
(begin
22902295
;; var"funky identifier" syntax
2291-
(take-token s)
2296+
(peek-token s)
2297+
(take-token s) ;; leading "
22922298
(let ((str (parse-raw-literal s #\"))
22932299
(nxt (peek-token s)))
22942300
(if (and (symbol? nxt) (not (operator? nxt)) (not (ts:space? s)))
2295-
(error (string "suffix not allowed after `var\"" str "\"`")))
2301+
(error (string "suffix not allowed after `var\"" str "\"`")))
22962302
(symbol str)))
22972303
t))
22982304

test/syntax.jl

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1922,3 +1922,9 @@ end
19221922
@test Base.remove_linenums!(Meta.parse("try a catch var\"#\" b end")) ==
19231923
Expr(:try, Expr(:block, :a), Symbol("#"), Expr(:block, :b))
19241924
@test Meta.parse("(var\"function\" = 1,)") == Expr(:tuple, Expr(:(=), Symbol("function"), 1))
1925+
# Non-standard identifiers require parens for string interpolation
1926+
@test Meta.parse("\"\$var\\\"#\\\"\"") == Expr(:string, :var, "\"#\"")
1927+
@test Meta.parse("\"\$(var\"#\")\"") == Expr(:string, Symbol("#"))
1928+
# Stream positioning after parsing var
1929+
@test Meta.parse("var'", 1, greedy=false) == (:var, 4)
1930+

0 commit comments

Comments
 (0)