Skip to content

Commit 3b2f444

Browse files
mbovelEugeneFlesselleaherlihybracevac
committed
Add an error message for local final defs
Co-Authored-By: Eugene Flesselle <[email protected]> Co-Authored-By: anna herlihy <[email protected]> Co-Authored-By: Oliver Bračevac <[email protected]>
1 parent af6beec commit 3b2f444

File tree

5 files changed

+44
-0
lines changed

5 files changed

+44
-0
lines changed

compiler/src/dotty/tools/dotc/parsing/Parsers.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4560,6 +4560,7 @@ object Parsers {
45604560
for (imod <- implicitMods.mods) mods = addMod(mods, imod)
45614561
if (mods.is(Final))
45624562
// A final modifier means the local definition is "class-like". // FIXME: Deal with modifiers separately
4563+
if isDclIntro && in.token != GIVEN then syntaxError(FinalLocalDef())
45634564
tmplDef(start, mods)
45644565
else
45654566
defOrDcl(start, mods)

compiler/src/dotty/tools/dotc/reporting/ErrorMessageID.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -212,6 +212,7 @@ enum ErrorMessageID(val isActive: Boolean = true) extends java.lang.Enum[ErrorMe
212212
case ContextBoundCompanionNotValueID // errorNumber: 196
213213
case InlinedAnonClassWarningID // errorNumber: 197
214214
case UnusedSymbolID // errorNumber: 198
215+
case FinalLocalDefID // errorNumber: 199
215216

216217
def errorNumber = ordinal - 1
217218

compiler/src/dotty/tools/dotc/reporting/messages.scala

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1850,6 +1850,12 @@ class ExpectedStartOfTopLevelDefinition()(using Context)
18501850
i"You have to provide either ${hl("class")}, ${hl("trait")}, ${hl("object")}, or ${hl("enum")} definitions after modifiers"
18511851
}
18521852

1853+
class FinalLocalDef()(using Context)
1854+
extends SyntaxMsg(FinalLocalDefID) {
1855+
def msg(using Context) = i"The ${hl("final")} modifier is not allowed on local definitions"
1856+
def explain(using Context) = ""
1857+
}
1858+
18531859
class NoReturnFromInlineable(owner: Symbol)(using Context)
18541860
extends SyntaxMsg(NoReturnFromInlineableID) {
18551861
def msg(using Context) = i"No explicit ${hl("return")} allowed from inlineable $owner"

tests/neg/17579.check

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
-- [E199] Syntax Error: tests/neg/17579.scala:4:10 ---------------------------------------------------------------------
2+
4 | final val v1 = 42 // error
3+
| ^^^
4+
| The final modifier is not allowed on local definitions
5+
-- [E199] Syntax Error: tests/neg/17579.scala:5:15 ---------------------------------------------------------------------
6+
5 | final lazy val v2 = 42 // error
7+
| ^^^
8+
| The final modifier is not allowed on local definitions
9+
-- [E088] Syntax Error: tests/neg/17579.scala:6:10 ---------------------------------------------------------------------
10+
6 | final private val v3 = 42 // error
11+
| ^^^^^^^
12+
| Expected start of definition
13+
|
14+
| longer explanation available when compiling with `-explain`
15+
-- [E199] Syntax Error: tests/neg/17579.scala:7:10 ---------------------------------------------------------------------
16+
7 | final def v4 = 42 // error
17+
| ^^^
18+
| The final modifier is not allowed on local definitions
19+
-- [E199] Syntax Error: tests/neg/17579.scala:8:10 ---------------------------------------------------------------------
20+
8 | final var v5 = 42 // error
21+
| ^^^
22+
| The final modifier is not allowed on local definitions
23+
-- [E199] Syntax Error: tests/neg/17579.scala:9:10 ---------------------------------------------------------------------
24+
9 | final type Foo = String // error
25+
| ^^^^
26+
| The final modifier is not allowed on local definitions

tests/neg/17579.scala

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
class C:
2+
final var v = 42 // ok
3+
def f =
4+
final val v1 = 42 // error
5+
final lazy val v2 = 42 // error
6+
final private val v3 = 42 // error
7+
final def v4 = 42 // error
8+
final var v5 = 42 // error
9+
final type Foo = String // error
10+
final given String = ???

0 commit comments

Comments
 (0)