Skip to content

Commit

Permalink
Space: Revert how invariant targs are erased to fix regression
Browse files Browse the repository at this point in the history
The motivating case (i16451) is complicated, because it involves
unchecked type arguments.  To fix the regression, I'm reverting the fix.
  • Loading branch information
dwijnand committed Aug 1, 2023
1 parent b40122f commit 09df3ef
Show file tree
Hide file tree
Showing 10 changed files with 61 additions and 15 deletions.
15 changes: 4 additions & 11 deletions compiler/src/dotty/tools/dotc/transform/patmat/Space.scala
Original file line number Diff line number Diff line change
Expand Up @@ -458,17 +458,10 @@ object SpaceEngine {
WildcardType

case tp @ AppliedType(tycon, args) =>
val args2 =
if tycon.isRef(defn.ArrayClass) then
args.map(arg => erase(arg, inArray = true, isValue = false))
else tycon.typeParams.lazyZip(args).map { (tparam, arg) =>
if isValue && tparam.paramVarianceSign == 0 then
// when matching against a value,
// any type argument for an invariant type parameter will be unchecked,
// meaning it won't fail to match against anything; thus the wildcard replacement
WildcardType
else erase(arg, inArray = false, isValue = false)
}
val inArray = tycon.isRef(defn.ArrayClass)
val args2 = tycon.typeParams.lazyZip(args).map { (tparam, arg) =>
erase(arg, inArray = inArray, isValue = false)
}
tp.derivedAppliedType(erase(tycon, inArray, isValue = false), args2)

case tp @ OrType(tp1, tp2) =>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,12 @@ object Test {
def err2[A, B](value: Foo[A, B], a: A => Int): B = value match {
case b: Bar[B] => // spurious // error
b.x
case _ => ??? // avoid fatal inexhaustivity warnings suppressing the uncheckable warning
}

def fail[A, B](value: Foo[A, B], a: A => Int): B = value match {
case b: Bar[Int] => // error
b.x
case _ => ??? // avoid fatal inexhaustivity warnings suppressing the uncheckable warning
}
}
2 changes: 2 additions & 0 deletions tests/neg-custom-args/isInstanceOf/enum-approx2.scala
Original file line number Diff line number Diff line change
Expand Up @@ -4,5 +4,7 @@ case class Fun[A, B](f: Exp[A => B]) extends Exp[A => B]
class Test {
def eval(e: Fun[Int, Int]) = e match {
case Fun(x: Fun[Int, Double]) => ??? // error
case Fun(x: Exp[Int => String]) => ??? // error
case _ =>
}
}
1 change: 1 addition & 0 deletions tests/neg-custom-args/isInstanceOf/i11178.scala
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ object Test1 {
def test[A](bar: Bar[A]) =
bar match {
case _: Bar[Boolean] => ??? // error
case _ => ???
}
}

Expand Down
1 change: 1 addition & 0 deletions tests/neg-custom-args/isInstanceOf/i8932.scala
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ class Dummy extends Bar[Nothing] with Foo[String]
def bugReport[A](foo: Foo[A]): Foo[A] =
foo match {
case bar: Bar[A] => bar // error
case dummy: Dummy => ???
}

def test = bugReport(new Dummy: Foo[String])
File renamed without changes.
4 changes: 0 additions & 4 deletions tests/neg/i16451.scala → tests/pending/neg/i16451.scala
Original file line number Diff line number Diff line change
@@ -1,10 +1,6 @@
// scalac: -Werror
enum Color:
case Red, Green
//sealed trait Color
//object Color:
// case object Red extends Color
// case object Green extends Color

case class Wrapper[A](value: A)

Expand Down
16 changes: 16 additions & 0 deletions tests/pos/i17230.bootstrap.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
type Untyped = Type | Null

class Type
abstract class SearchFailureType extends Type

abstract class Tree[+T <: Untyped]:
def tpe: T = null.asInstanceOf[T]

class SearchFailureIdent[+T <: Untyped] extends Tree[T]

class Test_i17230_bootstrap:
def t1(arg: Tree[Type]) = arg match
case arg: SearchFailureIdent[?] => arg.tpe match
case x: SearchFailureType =>
case _ =>
case _ =>
15 changes: 15 additions & 0 deletions tests/pos/i17230.min1.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
// scalac: -Werror
trait Foo:
type Bar[_]

object Foo:
type Aux[B[_]] = Foo { type Bar[A] = B[A] }

class Test:
def t1[B[_]](self: Option[Foo.Aux[B]]) = self match
case Some(_) => 1
case None => 2

def t2[B[_]](self: Option[Foo.Aux[B]]) = self match
case Some(f) => 1
case None => 2
20 changes: 20 additions & 0 deletions tests/pos/i17230.orig.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
// scalac: -Werror
import scala.util.*

trait Transaction {
type State[_]
}
object Transaction {
type of[S[_]] = Transaction { type State[A] = S[A] }
}
trait DynamicScope[State[_]]

case class ScopeSearch[State[_]](self: Either[Transaction.of[State], DynamicScope[State]]) {

def embedTransaction[T](f: Transaction.of[State] => T): T =
self match {
case Left(integrated) => ???
case Right(ds) => ???
}
}

0 comments on commit 09df3ef

Please sign in to comment.