Skip to content

Commit 18d1f68

Browse files
authored
Merge pull request #3475 from dotty-staging/fix-3333
Fix #3333: adapt child instantiation
2 parents b5f3bde + 6c58df8 commit 18d1f68

File tree

6 files changed

+63
-7
lines changed

6 files changed

+63
-7
lines changed

compiler/src/dotty/tools/dotc/transform/patmat/Space.scala

Lines changed: 24 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -584,10 +584,9 @@ class SpaceEngine(implicit ctx: Context) extends SpaceLogic {
584584
// precondition: `tp1` should have the shape `path.Child`, thus `ThisType` is always covariant
585585
val thisTypeMap = new TypeMap {
586586
def apply(t: Type): Type = t match {
587-
case tp @ ThisType(tref) if !tref.symbol.isStaticOwner && !tref.symbol.is(Module) =>
588-
// TODO: stackoverflow here
589-
// newTypeVar(TypeBounds.upper(mapOver(tp.underlying)))
590-
newTypeVar(TypeBounds.upper(mapOver(tref & tref.classSymbol.asClass.givenSelfType)))
587+
case tp @ ThisType(tref) if !tref.symbol.isStaticOwner =>
588+
if (tref.symbol.is(Module)) mapOver(tref)
589+
else newTypeVar(TypeBounds.upper(tp.underlying))
591590
case _ =>
592591
mapOver(t)
593592
}
@@ -596,7 +595,6 @@ class SpaceEngine(implicit ctx: Context) extends SpaceLogic {
596595
// replace type parameter references with bounds
597596
val typeParamMap = new TypeMap {
598597
def apply(t: Type): Type = t match {
599-
600598
case tp: TypeRef if tp.symbol.is(TypeParam) && tp.underlying.isInstanceOf[TypeBounds] =>
601599
// See tests/patmat/gadt.scala tests/patmat/exhausting.scala tests/patmat/t9657.scala
602600
val exposed =
@@ -611,13 +609,32 @@ class SpaceEngine(implicit ctx: Context) extends SpaceLogic {
611609
}
612610
}
613611

612+
// replace uninstantiated type vars with WildcardType, check tests/patmat/3333.scala
613+
val instUndetMap = new TypeMap {
614+
def apply(t: Type): Type = t match {
615+
case tvar: TypeVar if !tvar.isInstantiated => WildcardType(tvar.origin.underlying.bounds)
616+
case _ => mapOver(t)
617+
}
618+
}
619+
620+
val force = new ForceDegree.Value(
621+
tvar => !(ctx.typerState.constraint.entry(tvar.origin) eq tvar.origin.underlying),
622+
minimizeAll = false
623+
)
624+
614625
val tvars = tp1.typeParams.map { tparam => newTypeVar(tparam.paramInfo.bounds) }
615626
val protoTp1 = thisTypeMap(tp1.appliedTo(tvars))
616627

617-
if (protoTp1 <:< tp2 && isFullyDefined(protoTp1, ForceDegree.noBottom)) protoTp1
628+
if (protoTp1 <:< tp2) {
629+
if (isFullyDefined(protoTp1, force)) protoTp1
630+
else instUndetMap(protoTp1)
631+
}
618632
else {
619633
val protoTp2 = typeParamMap(tp2)
620-
if (protoTp1 <:< protoTp2 && isFullyDefined(protoTp1 & protoTp2, ForceDegree.noBottom)) protoTp1
634+
if (protoTp1 <:< protoTp2) {
635+
if (isFullyDefined(AndType(protoTp1, protoTp2), force)) protoTp1
636+
else instUndetMap(protoTp1)
637+
}
621638
else {
622639
debug.println(s"$protoTp1 <:< $protoTp2 = false")
623640
NoType

tests/patmat/3333.check

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
10: Pattern Match Exhaustivity: _: IntNumber, NotNaN

tests/patmat/3333.scala

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
sealed trait IntegralNumber
2+
3+
object IntegralNumber {
4+
object NaN extends IntegralNumber
5+
object NotNaN extends IntegralNumber
6+
7+
sealed abstract class FiniteNumberImpl[N](val value: N) extends IntegralNumber
8+
sealed class IntNumber(value: Int) extends FiniteNumberImpl[Int](value)
9+
10+
def test(o: IntegralNumber) = o match {
11+
case NaN => -1
12+
}
13+
14+
}

tests/patmat/3455.check

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
11: Pattern Match Exhaustivity: Decimal

tests/patmat/3455.scala

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
trait AxisCompanion {
2+
sealed trait Format
3+
object Format {
4+
case object Decimal extends Format
5+
case object Integer extends Format
6+
}
7+
}
8+
object Axis extends AxisCompanion
9+
class Axis {
10+
import Axis._
11+
def test( f: Format ) = f match {
12+
case Format.Integer => "Int"
13+
}
14+
}

tests/patmat/3469.scala

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
object O {
2+
sealed trait Trait[+A] { type T }
3+
case class CaseClass[+A](a: A) extends Trait[A] { type T = Nothing }
4+
5+
def id[TT, A](v: Trait[A] { type T = TT }): Trait[A] { type T = TT } =
6+
v match {
7+
case CaseClass(a) => CaseClass(a)
8+
}
9+
}

0 commit comments

Comments
 (0)