Skip to content

Commit

Permalink
fix: disallow toplevel infix definitions for vals, vars, givens, meth…
Browse files Browse the repository at this point in the history
…ods and implicits

Part of scala#17738
  • Loading branch information
arainko committed Jun 17, 2023
1 parent 2d9eb1c commit ed64113
Show file tree
Hide file tree
Showing 5 changed files with 46 additions and 0 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -196,6 +196,7 @@ enum ErrorMessageID(val isActive: Boolean = true) extends java.lang.Enum[ErrorMe
case AmbiguousExtensionMethodID // errorNumber 180
case UnqualifiedCallToAnyRefMethodID // errorNumber: 181
case NotConstantID // errorNumber: 182
case ToplevelDefCantBeInfixID // errorNumber: 183

def errorNumber = ordinal - 1

Expand Down
10 changes: 10 additions & 0 deletions compiler/src/dotty/tools/dotc/reporting/messages.scala
Original file line number Diff line number Diff line change
Expand Up @@ -2913,3 +2913,13 @@ class MatchTypeScrutineeCannotBeHigherKinded(tp: Type)(using Context)
extends TypeMsg(MatchTypeScrutineeCannotBeHigherKindedID) :
def msg(using Context) = i"the scrutinee of a match type cannot be higher-kinded"
def explain(using Context) = ""

class ToplevelDefCantBeInfix(sym: Symbol)(using Context)
extends SyntaxMsg(ToplevelDefCantBeInfixID):
def msg(using Context) = i"a toplevel $defName cannot be infix"
def explain(using Context) = ""
private val defName =
if sym.flags.is(Method) then "def"
else if sym.flags.is(Mutable) then "var"
else if sym.flags.is(Given) then "given"
else "val"
1 change: 1 addition & 0 deletions compiler/src/dotty/tools/dotc/typer/Checking.scala
Original file line number Diff line number Diff line change
Expand Up @@ -555,6 +555,7 @@ object Checking {
fail(CannotHaveSameNameAs(sym, cls, CannotHaveSameNameAs.CannotBeOverridden))
sym.setFlag(Private) // break the overriding relationship by making sym Private
}
if sym.isWrappedToplevelDef && !sym.isType then fail(ToplevelDefCantBeInfix(sym))
checkApplicable(Erased,
!sym.isOneOf(MutableOrLazy, butNot = Given) && !sym.isType || sym.isClass)
checkCombination(Final, Open)
Expand Down
20 changes: 20 additions & 0 deletions tests/neg/i17738-toplevel-infix.check
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
-- [E183] Syntax Error: tests/neg/i17738-toplevel-infix.scala:10:10 ----------------------------------------------------
10 |infix val toplevelVal = ??? // error
| ^
| a toplevel val cannot be infix
-- [E183] Syntax Error: tests/neg/i17738-toplevel-infix.scala:11:10 ----------------------------------------------------
11 |infix var toplevelVar = ??? // error
| ^
| a toplevel var cannot be infix
-- [E183] Syntax Error: tests/neg/i17738-toplevel-infix.scala:12:10 ----------------------------------------------------
12 |infix def toplevelDef = ??? // error
| ^
| a toplevel def cannot be infix
-- [E183] Syntax Error: tests/neg/i17738-toplevel-infix.scala:13:12 ----------------------------------------------------
13 |infix given toplevelGiven: Int = ??? // error
| ^
| a toplevel given cannot be infix
-- [E183] Syntax Error: tests/neg/i17738-toplevel-infix.scala:14:19 ----------------------------------------------------
14 |infix implicit val topevelImplicit: Int = ??? // error
| ^
| a toplevel val cannot be infix
14 changes: 14 additions & 0 deletions tests/neg/i17738-toplevel-infix.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
infix type A[b, a] = Nothing

infix type B[b, a] = b match {
case Int => a
}

infix class C[A, B]
infix trait D[A, B]

infix val toplevelVal = ??? // error
infix var toplevelVar = ??? // error
infix def toplevelDef = ??? // error
infix given toplevelGiven: Int = ??? // error
infix implicit val topevelImplicit: Int = ??? // error

0 comments on commit ed64113

Please sign in to comment.