Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 14 additions & 1 deletion compiler/src/dotty/tools/dotc/typer/VarianceChecker.scala
Original file line number Diff line number Diff line change
Expand Up @@ -164,7 +164,20 @@ class VarianceChecker(using Context) {
i"\n${hl("enum case")} ${towner.name} requires explicit declaration of $tvar to resolve this issue.\n$example"
else
""
em"${varianceLabel(tvar.flags)} $tvar occurs in ${varianceLabel(required)} position in type ${sym.info} of $sym$enumAddendum"
val privateParamAddendum =
if sym.flags.is(ParamAccessor) && sym.flags.is(Private) then
val varOrVal = if sym.is(Mutable) then "var" else "val"
val varFieldInstead = if sym.is(Mutable) then " and add\na field inside the class instead" else ""
s"""
|
|Implementation limitation: ${hl(f"private $varOrVal")} parameters cannot be inferred to be local
|and therefore are always variance-checked.
|
|Potential fix: remove the ${hl(f"private $varOrVal")} modifiers on the parameter ${sym.name}$varFieldInstead.
""".stripMargin
else
""
em"${varianceLabel(tvar.flags)} $tvar occurs in ${varianceLabel(required)} position in type ${sym.info} of $sym$enumAddendum$privateParamAddendum"
if (migrateTo3 &&
(sym.owner.isConstructor || sym.ownersIterator.exists(_.isAllOf(ProtectedLocal))))
report.migrationWarning(
Expand Down
21 changes: 21 additions & 0 deletions tests/neg/i22620.check
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
-- Error: tests/neg/i22620.scala:4:34 ----------------------------------------------------------------------------------
4 |class PrivateTest[-M](private val v: ArrayBuffer[M]) // error
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
| contravariant type M occurs in invariant position in type scala.collection.mutable.ArrayBuffer[M] of value v
|
| Implementation limitation: private val parameters cannot be inferred to be local
| and therefore are always variance-checked.
|
| Potential fix: remove the private val modifiers on the parameter v.
|
-- Error: tests/neg/i22620.scala:6:37 ----------------------------------------------------------------------------------
6 |class PrivateTestMut[-M](private var v: ArrayBuffer[M]) // error
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
| contravariant type M occurs in invariant position in type scala.collection.mutable.ArrayBuffer[M] of variable v
|
| Implementation limitation: private var parameters cannot be inferred to be local
| and therefore are always variance-checked.
|
| Potential fix: remove the private var modifiers on the parameter v and add
| a field inside the class instead.
|
4 changes: 4 additions & 0 deletions tests/neg/i22620.scala
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,7 @@
import scala.collection.mutable.ArrayBuffer

class PrivateTest[-M](private val v: ArrayBuffer[M]) // error

class PrivateTestMut[-M](private var v: ArrayBuffer[M]) // error

class PrivateTestParamOnly[-M](v: ArrayBuffer[M]) // no error