Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix #19445: Remove too-strict test in match type matching. #19511

Merged
merged 1 commit into from
Jan 23, 2024
Merged
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
3 changes: 2 additions & 1 deletion compiler/src/dotty/tools/dotc/core/TypeComparer.scala
Original file line number Diff line number Diff line change
Expand Up @@ -3436,7 +3436,8 @@ class TrackingTypeComparer(initctx: Context) extends TypeComparer(initctx) {
case MatchTypeCasePattern.BaseTypeTest(classType, argPatterns, needsConcreteScrut) =>
val cls = classType.classSymbol.asClass
scrut.baseType(cls) match
case base @ AppliedType(baseTycon, baseArgs) if baseTycon =:= classType =>
case base @ AppliedType(baseTycon, baseArgs) =>
// #19445 Don't check the prefix of baseTycon here; it is handled by `scrut <:< instantiatedPat`.
val innerScrutIsWidenedAbstract =
scrutIsWidenedAbstract
|| (needsConcreteScrut && !isConcrete(scrut)) // no point in checking concreteness if it does not need to be concrete
Expand Down
36 changes: 36 additions & 0 deletions tests/neg/i19445.check
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
-- [E007] Type Mismatch Error: tests/neg/i19445.scala:17:15 ------------------------------------------------------------
17 | val x: Int = ??? : UnwrapTypes[FooBar.Bar[Int]] // error
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
| Found: Test.UnwrapTypes[FooBar.Bar[Int]]
| Required: Int
|
| Note: a match type could not be fully reduced:
|
| trying to reduce Test.UnwrapTypes[FooBar.Bar[Int]]
| failed since selector FooBar.Bar[Int]
| does not match case BarFoo.Bar[x] => Test.UnwrapTypes[x]
| and cannot be shown to be disjoint from it either.
| Therefore, reduction cannot advance to the remaining cases
|
| case String => String
| case Int => Int
|
| longer explanation available when compiling with `-explain`
-- [E007] Type Mismatch Error: tests/neg/i19445.scala:18:28 ------------------------------------------------------------
18 | val tup: (Int, String) = ??? : UnwrapTypes[(FooBar.Bar[Int], FooBar.Bar[String])] // error
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
| Found: (Test.UnwrapTypes[FooBar.Bar[Int]], Test.UnwrapTypes[FooBar.Bar[String]])
| Required: (Int, String)
|
| Note: a match type could not be fully reduced:
|
| trying to reduce Test.UnwrapTypes[FooBar.Bar[Int]]
| failed since selector FooBar.Bar[Int]
| does not match case BarFoo.Bar[x] => Test.UnwrapTypes[x]
| and cannot be shown to be disjoint from it either.
| Therefore, reduction cannot advance to the remaining cases
|
| case String => String
| case Int => Int
|
| longer explanation available when compiling with `-explain`
19 changes: 19 additions & 0 deletions tests/neg/i19445.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
trait Foo:
case class Bar[A](value: A)

object FooBar extends Foo

object BarFoo extends Foo

object Test:
type UnwrapTypes[Xs] =
Xs match
case EmptyTuple => Xs
case x *: xs => UnwrapTypes[x] *: UnwrapTypes[xs]
case BarFoo.Bar[x] => UnwrapTypes[x]
case String => String
case Int => Int

val x: Int = ??? : UnwrapTypes[FooBar.Bar[Int]] // error
val tup: (Int, String) = ??? : UnwrapTypes[(FooBar.Bar[Int], FooBar.Bar[String])] // error
end Test
17 changes: 17 additions & 0 deletions tests/pos/i19445.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
trait Foo:
case class Bar[A](value: A)

object FooBar extends Foo

object Test:
type UnwrapTypes[Xs] =
Xs match
case EmptyTuple => Xs
case x *: xs => UnwrapTypes[x] *: UnwrapTypes[xs]
case Foo#Bar[x] => UnwrapTypes[x]
case String => String
case Int => Int

val x: Int = ??? : UnwrapTypes[FooBar.Bar[Int]]
val tup: (Int, String) = ??? : UnwrapTypes[(FooBar.Bar[Int], FooBar.Bar[String])]
end Test
Loading