summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSom Snytt <som.snytt@gmail.com>2015-06-29 00:29:15 -0700
committerSom Snytt <som.snytt@gmail.com>2015-06-29 00:29:15 -0700
commitd7547cb76d41da04c8448cf1de8a5b5686152d17 (patch)
tree8d2d636a7ed5c48c43b4ab8e766d61f5810f01a7
parentd90d8b89687be5c817cc081ed970328c6d8fd13f (diff)
downloadscala-d7547cb76d41da04c8448cf1de8a5b5686152d17.tar.gz
scala-d7547cb76d41da04c8448cf1de8a5b5686152d17.tar.bz2
scala-d7547cb76d41da04c8448cf1de8a5b5686152d17.zip
SI-6810 Disallow EOL in char literal
It's clear that char literals are one-lined like normal string literals. By the same token, pun intended, char literals accept unicode escapes the same as string literals, including `\u000A`. This commit adds the usual exclusions (CR, NL, SU). The spec is outdated in outlawing chars that are not "printable", in particular, the ASCII control codes. The original intention may have been that the ordinary string escapes are required, such as "\b\n". Note that some common escapes are absent, such as "\a".
-rw-r--r--src/compiler/scala/tools/nsc/ast/parser/Scanners.scala8
-rw-r--r--test/files/neg/t6810.check22
-rw-r--r--test/files/neg/t6810.scala22
3 files changed, 49 insertions, 3 deletions
diff --git a/src/compiler/scala/tools/nsc/ast/parser/Scanners.scala b/src/compiler/scala/tools/nsc/ast/parser/Scanners.scala
index 92833d647b..d5cb0d6a3b 100644
--- a/src/compiler/scala/tools/nsc/ast/parser/Scanners.scala
+++ b/src/compiler/scala/tools/nsc/ast/parser/Scanners.scala
@@ -515,7 +515,7 @@ trait Scanners extends ScannersCommon {
charLitOr(getIdentRest)
else if (isOperatorPart(ch) && (ch != '\\'))
charLitOr(getOperatorRest)
- else {
+ else if (!isAtEnd && (ch != SU && ch != CR && ch != LF || isUnicodeEscape)) {
getLitChar()
if (ch == '\'') {
nextChar()
@@ -525,6 +525,8 @@ trait Scanners extends ScannersCommon {
syntaxError("unclosed character literal")
}
}
+ else
+ syntaxError("unclosed character literal")
}
fetchSingleQuote()
case '.' =>
@@ -690,7 +692,7 @@ trait Scanners extends ScannersCommon {
private def unclosedStringLit(): Unit = syntaxError("unclosed string literal")
- private def getRawStringLit(): Unit = {
+ @tailrec private def getRawStringLit(): Unit = {
if (ch == '\"') {
nextRawChar()
if (isTripleQuote()) {
@@ -707,7 +709,7 @@ trait Scanners extends ScannersCommon {
}
}
- @scala.annotation.tailrec private def getStringPart(multiLine: Boolean): Unit = {
+ @tailrec private def getStringPart(multiLine: Boolean): Unit = {
def finishStringPart() = {
setStrVal()
token = STRINGPART
diff --git a/test/files/neg/t6810.check b/test/files/neg/t6810.check
new file mode 100644
index 0000000000..8b0e6715aa
--- /dev/null
+++ b/test/files/neg/t6810.check
@@ -0,0 +1,22 @@
+t6810.scala:4: error: unclosed character literal
+ val y = '
+ ^
+t6810.scala:5: error: unclosed character literal
+' // but not embedded EOL sequences not represented as escapes
+^
+t6810.scala:9: error: unclosed string literal
+ val Y = "
+ ^
+t6810.scala:10: error: unclosed string literal
+" // obviously not
+^
+t6810.scala:20: error: unclosed quoted identifier
+ val `
+ ^
+t6810.scala:21: error: unclosed quoted identifier
+` = EOL // not raw string literals aka triple-quoted, multiline strings
+^
+t6810.scala:22: error: '=' expected but '}' found.
+}
+^
+7 errors found
diff --git a/test/files/neg/t6810.scala b/test/files/neg/t6810.scala
new file mode 100644
index 0000000000..a9d8813389
--- /dev/null
+++ b/test/files/neg/t6810.scala
@@ -0,0 +1,22 @@
+
+trait t6810 {
+ val x = '\u000A' // char literals accept arbitrary unicode escapes
+ val y = '
+' // but not embedded EOL sequences not represented as escapes
+ val z = '\n' // normally, expect this escape
+
+ val X = "\u000A" // it's the same as ordinary string literals
+ val Y = "
+" // obviously not
+ val Z = "\n" // normally, expect this escape
+
+ val A = """
+""" // which is what these are for
+ val B = s"""
+""" // or the same for interpolated strings
+
+ import scala.compat.Platform.EOL
+ val `\u000A` = EOL // backquoted identifiers are arbitrary string literals
+ val `
+` = EOL // not raw string literals aka triple-quoted, multiline strings
+}