Skip to content

Commit be32eb9

Browse files
authored
Fix #11541: Specialize ClassTag[T] in exhaustivity check (#17385)
2 parents 8a055d6 + 4d32116 commit be32eb9

File tree

3 files changed

+20
-1
lines changed

3 files changed

+20
-1
lines changed

compiler/src/dotty/tools/dotc/core/Definitions.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -798,6 +798,7 @@ class Definitions {
798798

799799
@tu lazy val ReflectPackageClass: Symbol = requiredPackage("scala.reflect.package").moduleClass
800800
@tu lazy val ClassTagClass: ClassSymbol = requiredClass("scala.reflect.ClassTag")
801+
@tu lazy val ClassTagClass_unapply: Symbol = ClassTagClass.requiredMethod("unapply")
801802
@tu lazy val ClassTagModule: Symbol = ClassTagClass.companionModule
802803
@tu lazy val ClassTagModule_apply: Symbol = ClassTagModule.requiredMethod(nme.apply)
803804

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

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -602,10 +602,15 @@ object SpaceEngine {
602602

603603
/** Whether the extractor covers the given type */
604604
def covers(unapp: TermRef, scrutineeTp: Type, argLen: Int)(using Context): Boolean =
605-
SpaceEngine.isIrrefutable(unapp, argLen) || unapp.symbol == defn.TypeTest_unapply && {
605+
SpaceEngine.isIrrefutable(unapp, argLen)
606+
|| unapp.symbol == defn.TypeTest_unapply && {
606607
val AppliedType(_, _ :: tp :: Nil) = unapp.prefix.widen.dealias: @unchecked
607608
scrutineeTp <:< tp
608609
}
610+
|| unapp.symbol == defn.ClassTagClass_unapply && {
611+
val AppliedType(_, tp :: Nil) = unapp.prefix.widen.dealias: @unchecked
612+
scrutineeTp <:< tp
613+
}
609614

610615
/** Decompose a type into subspaces -- assume the type can be decomposed */
611616
def decompose(tp: Type)(using Context): List[Type] = trace(i"decompose($tp)", debug) {

tests/patmat/i11541.scala

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
import scala.reflect.ClassTag
2+
3+
class Test:
4+
type A
5+
6+
given ClassTag[A] = ???
7+
8+
var a: A | Null = null
9+
10+
a match { //WARNING: match may not be exhaustive. It would fail on pattern case: _: A
11+
case null =>
12+
case a: A =>
13+
}

0 commit comments

Comments
 (0)