@@ -557,6 +557,8 @@ class SpaceEngine(implicit ctx: Context) extends SpaceLogic {
557
557
558
558
debug.println(s " bases of ${tp1.show}: " + bases1)
559
559
debug.println(s " bases of ${tp2.show}: " + bases2)
560
+ debug.println(s " ${tp1.show} <:< ${tp2.show} : " + (tp1 <:< tp2))
561
+ debug.println(s " ${tp2.show} <:< ${tp1.show} : " + (tp2 <:< tp1))
560
562
561
563
val noClassConflict =
562
564
bases1.forall(sym1 => sym1.is(Trait ) || bases2.forall(sym2 => sym2.is(Trait ) || sym1.isSubClass(sym2))) ||
@@ -638,15 +640,31 @@ class SpaceEngine(implicit ctx: Context) extends SpaceLogic {
638
640
}
639
641
}
640
642
643
+ // Fix subtype checking for child instantiation,
644
+ // such that `Foo(Test.this.foo) <:< Foo(Foo.this)`
645
+ // See tests/patmat/i3938.scala
646
+ def removeThisType (implicit ctx : Context ) = new TypeMap {
647
+ def apply (tp : Type ): Type = tp match {
648
+ case ThisType (tref : TypeRef ) =>
649
+ if (tref.symbol.is(Module ))
650
+ TermRef (tref.prefix, tref.symbol.sourceModule)
651
+ else
652
+ mapOver(tref)
653
+ case _ => mapOver(tp)
654
+ }
655
+ }
656
+
641
657
// We are checking the possibility of `tp1 <:< tp2`, thus we should
642
658
// minimize `tp1` while maximizing `tp2`. See tests/patmat/3645b.scala
643
659
def childTypeMap (implicit ctx : Context ) = new AbstractTypeMap (maximize = false ) {
644
660
def apply (t : Type ): Type = t.dealias match {
645
661
// map `ThisType` of `tp1` to a type variable
646
662
// precondition: `tp1` should have the same shape as `path.Child`, thus `ThisType` is always covariant
647
663
case tp @ ThisType (tref) if ! tref.symbol.isStaticOwner =>
648
- if (tref.symbol.is(Module )) this (tref)
649
- else newTypeVar(TypeBounds .upper(tp.underlying))
664
+ if (tref.symbol.is(Module ))
665
+ this (TermRef (tref.prefix, tref.symbol.sourceModule))
666
+ else
667
+ newTypeVar(TypeBounds .upper(removeThisType.apply(tref)))
650
668
651
669
case tp =>
652
670
mapOver(tp)
0 commit comments