diff options
-rw-r--r-- | compiler/src/dotty/tools/dotc/parsing/Parsers.scala | 14 | ||||
-rw-r--r-- | compiler/src/dotty/tools/dotc/parsing/Scanners.scala | 2 | ||||
-rw-r--r-- | tests/neg/i1779.scala | 13 | ||||
-rw-r--r-- | tests/run/i1779.check | 1 | ||||
-rw-r--r-- | tests/run/i1779.scala | 13 |
5 files changed, 37 insertions, 6 deletions
diff --git a/compiler/src/dotty/tools/dotc/parsing/Parsers.scala b/compiler/src/dotty/tools/dotc/parsing/Parsers.scala index 51dafc928..704f399ca 100644 --- a/compiler/src/dotty/tools/dotc/parsing/Parsers.scala +++ b/compiler/src/dotty/tools/dotc/parsing/Parsers.scala @@ -597,7 +597,7 @@ object Parsers { val isNegated = negOffset < in.offset atPos(negOffset) { if (in.token == SYMBOLLIT) atPos(in.skipToken()) { SymbolLit(in.strVal) } - else if (in.token == INTERPOLATIONID) interpolatedString() + else if (in.token == INTERPOLATIONID) interpolatedString(inPattern) else finish(in.token match { case CHARLIT => in.charVal case INTLIT => in.intVal(isNegated).toInt @@ -621,10 +621,14 @@ object Parsers { in.nextToken() while (in.token == STRINGPART) { segmentBuf += Thicket( - literal(), + literal(inPattern = inPattern), atPos(in.offset) { if (in.token == IDENTIFIER) termIdent() + else if (in.token == USCORE && inPattern) { + in.nextToken() + Ident(nme.WILDCARD) + } else if (in.token == THIS) { in.nextToken() This(EmptyTypeIdent) @@ -633,12 +637,12 @@ object Parsers { if (inPattern) Block(Nil, inBraces(pattern())) else expr() else { - ctx.error(InterpolatedStringError()) + ctx.error(InterpolatedStringError(), source atPos Position(in.offset)) EmptyTree } }) } - if (in.token == STRINGLIT) segmentBuf += literal() + if (in.token == STRINGLIT) segmentBuf += literal(inPattern = inPattern) InterpolatedString(interpolator, segmentBuf.toList) } @@ -1444,7 +1448,7 @@ object Parsers { case XMLSTART => xmlLiteralPattern() case _ => - if (isLiteral) literal() + if (isLiteral) literal(inPattern = true) else { syntaxErrorOrIncomplete(IllegalStartOfSimplePattern()) errorTermTree diff --git a/compiler/src/dotty/tools/dotc/parsing/Scanners.scala b/compiler/src/dotty/tools/dotc/parsing/Scanners.scala index 60003d098..101be167e 100644 --- a/compiler/src/dotty/tools/dotc/parsing/Scanners.scala +++ b/compiler/src/dotty/tools/dotc/parsing/Scanners.scala @@ -758,7 +758,7 @@ object Scanners { finishStringPart() nextRawChar() next.token = LBRACE - } else if (Character.isUnicodeIdentifierStart(ch)) { + } else if (Character.isUnicodeIdentifierStart(ch) || ch == '_') { finishStringPart() do { putChar(ch) diff --git a/tests/neg/i1779.scala b/tests/neg/i1779.scala new file mode 100644 index 000000000..92100fa06 --- /dev/null +++ b/tests/neg/i1779.scala @@ -0,0 +1,13 @@ +object Test { + implicit class Foo(sc: StringContext) { + object q { + def apply(arg: Any*): Int = 3 + } + } + + def f = { + val _parent = 3 + q"val hello = $_parent" + q"class $_" // error // error + } +} diff --git a/tests/run/i1779.check b/tests/run/i1779.check new file mode 100644 index 000000000..4ef6e900e --- /dev/null +++ b/tests/run/i1779.check @@ -0,0 +1 @@ + extends diff --git a/tests/run/i1779.scala b/tests/run/i1779.scala new file mode 100644 index 000000000..e81bc97b6 --- /dev/null +++ b/tests/run/i1779.scala @@ -0,0 +1,13 @@ +object Test { + implicit class Foo(sc: StringContext) { + object q { + def unapply(arg: Any): Option[(Any, Any)] = + Some((sc.parts(0), sc.parts(1))) + } + } + + def main(args: Array[String]): Unit = { + val q"class $_ extends $_parent" = new Object + println(_parent) + } +} |