Skip to content

Commit 1c6b99a

Browse files
committed
restrict mirrors of any union type
1 parent 9d68778 commit 1c6b99a

File tree

3 files changed

+30
-28
lines changed

3 files changed

+30
-28
lines changed

compiler/src/dotty/tools/dotc/typer/Synthesizer.scala

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ class Synthesizer(typer: Typer)(using @constructorOnly c: Context):
2626
/** Handlers to synthesize implicits for special types */
2727
type SpecialHandler = (Type, Span) => Context ?=> TreeWithErrors
2828
private type SpecialHandlers = List[(ClassSymbol, SpecialHandler)]
29-
29+
3030
val synthesizedClassTag: SpecialHandler = (formal, span) =>
3131
formal.argInfos match
3232
case arg :: Nil =>
@@ -282,7 +282,7 @@ class Synthesizer(typer: Typer)(using @constructorOnly c: Context):
282282
def acceptable(tp: Type, cls: Symbol): Boolean = tp match
283283
case tp: HKTypeLambda if tp.resultType.isInstanceOf[HKTypeLambda] => false
284284
case tp: TypeProxy => acceptable(tp.underlying, cls)
285-
case OrType(tp1, tp2) => acceptable(tp1, cls) && acceptable(tp2, cls)
285+
case OrType(tp1, tp2) => false
286286
case _ => tp.classSymbol eq cls
287287

288288
/** for a case class, if it will have an anonymous mirror,
@@ -323,12 +323,12 @@ class Synthesizer(typer: Typer)(using @constructorOnly c: Context):
323323
withNoErrors(mirrorRef.cast(mirrorType))
324324
end makeProductMirror
325325

326-
def getError(cls: Symbol): String =
326+
def getError(cls: Symbol): String =
327327
val reason = if !cls.isGenericProduct then
328328
i"because ${cls.whyNotGenericProduct}"
329329
else if !canAccessCtor(cls) then
330330
i"because the constructor of $cls is innaccessible from the calling scope."
331-
else
331+
else
332332
""
333333
i"$cls is not a generic product $reason"
334334
end getError
@@ -369,7 +369,7 @@ class Synthesizer(typer: Typer)(using @constructorOnly c: Context):
369369
case tp: TermRef => false
370370
case tp: HKTypeLambda if tp.resultType.isInstanceOf[HKTypeLambda] => false
371371
case tp: TypeProxy => acceptable(tp.underlying)
372-
case OrType(tp1, tp2) => acceptable(tp1) && acceptable(tp2)
372+
case OrType(tp1, tp2) => false
373373
case _ => tp.classSymbol eq cls
374374

375375
if acceptable(mirroredType) && clsIsGenericSum then
@@ -428,7 +428,7 @@ class Synthesizer(typer: Typer)(using @constructorOnly c: Context):
428428
withNoErrors(mirrorRef.cast(mirrorType))
429429
else if !clsIsGenericSum then
430430
(EmptyTree, List(i"$cls is not a generic sum because ${cls.whyNotGenericSum(declScope)}"))
431-
else
431+
else
432432
EmptyTreeNoError
433433
end sumMirror
434434

@@ -595,7 +595,7 @@ class Synthesizer(typer: Typer)(using @constructorOnly c: Context):
595595
tp.baseType(cls)
596596
val base = baseWithRefinements(formal)
597597
val result =
598-
if (base <:< formal.widenExpr)
598+
if (base <:< formal.widenExpr)
599599
// With the subtype test we enforce that the searched type `formal` is of the right form
600600
handler(base, span)
601601
else EmptyTreeNoError
@@ -609,19 +609,19 @@ end Synthesizer
609609

610610
object Synthesizer:
611611

612-
/** Tuple used to store the synthesis result with a list of errors. */
612+
/** Tuple used to store the synthesis result with a list of errors. */
613613
type TreeWithErrors = (Tree, List[String])
614614
private def withNoErrors(tree: Tree): TreeWithErrors = (tree, List.empty)
615615

616616
private val EmptyTreeNoError: TreeWithErrors = withNoErrors(EmptyTree)
617617

618618
private def orElse(treeWithErrors1: TreeWithErrors, treeWithErrors2: => TreeWithErrors): TreeWithErrors = treeWithErrors1 match
619-
case (tree, errors) if tree eq genericEmptyTree =>
619+
case (tree, errors) if tree eq genericEmptyTree =>
620620
val (tree2, errors2) = treeWithErrors2
621621
(tree2, errors ::: errors2)
622622
case _ => treeWithErrors1
623623

624-
private def clearErrorsIfNotEmpty(treeWithErrors: TreeWithErrors) = treeWithErrors match
624+
private def clearErrorsIfNotEmpty(treeWithErrors: TreeWithErrors) = treeWithErrors match
625625
case (tree, _) if tree eq genericEmptyTree => treeWithErrors
626626
case (tree, _) => withNoErrors(tree)
627627

tests/neg/i14823a.scala

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
import deriving.Mirror
2+
3+
object MirrorK1:
4+
type Of[F[_]] = Mirror { type MirroredType[A] = F[A] }
5+
6+
sealed trait Box[T]
7+
object Box
8+
9+
case class Child[T]() extends Box[T]
10+
11+
sealed abstract class Foo[T]
12+
object Foo {
13+
case class A[T]() extends Foo[T]
14+
}
15+
16+
val foo = summon[Mirror.Of[Box[Int] | Box[Int]]] // error
17+
val bar = summon[MirrorK1.Of[[X] =>> Box[Int] | Box[Int]]] // error
18+
def baz = summon[deriving.Mirror.Of[Foo[String] | Foo[String]]] // error
19+
20+
def qux = summon[deriving.Mirror.Of[Option[Int] | Option[String]]] // error

tests/pos/i14823.scala

Lines changed: 0 additions & 18 deletions
This file was deleted.

0 commit comments

Comments
 (0)