Somewhere along the way AnyVal stopped working as sealed. (It was
still sealed but had lost its children.) Closes #3163, review by rytz. git-svn-id: http://lampsvn.epfl.ch/svn-repos/scala/scala/trunk@23192 5e8d7ff9-d8ef-0310-90f0-a4852d11357a
This commit is contained in:
parent
db8f536c20
commit
cb10c89599
|
@ -21,6 +21,7 @@ trait MatrixAdditions extends ast.TreeDSL
|
|||
import CODE._
|
||||
import Debug._
|
||||
import treeInfo.{ IsTrue, IsFalse }
|
||||
import definitions.{ isValueClass }
|
||||
|
||||
/** The Squeezer, responsible for all the squeezing.
|
||||
*/
|
||||
|
@ -172,11 +173,14 @@ trait MatrixAdditions extends ast.TreeDSL
|
|||
private def rowCoversCombo(row: Row, combos: List[Combo]) =
|
||||
row.guard.isEmpty && (combos forall (c => c isCovered row.pats(c.index)))
|
||||
|
||||
private def requiresExhaustive(s: Symbol) =
|
||||
private def requiresExhaustive(s: Symbol) = {
|
||||
(s hasFlag MUTABLE) && // indicates that have not yet checked exhaustivity
|
||||
!(s hasFlag TRANS_FLAG) && // indicates @unchecked
|
||||
(s.tpe.typeSymbol.isSealed) &&
|
||||
{ s resetFlag MUTABLE ; true } // side effects MUTABLE flag
|
||||
(s.tpe.typeSymbol.isSealed) && {
|
||||
s resetFlag MUTABLE // side effects MUTABLE flag
|
||||
!isValueClass(s.tpe.typeSymbol) // but make sure it's not a primitive, else (5: Byte) match { case 5 => ... } sees no Byte
|
||||
}
|
||||
}
|
||||
|
||||
private lazy val inexhaustives: List[List[Combo]] = {
|
||||
val collected =
|
||||
|
|
|
@ -865,6 +865,8 @@ trait Definitions extends reflect.generic.StandardDefinitions {
|
|||
Object_isInstanceOf,
|
||||
Object_asInstanceOf
|
||||
)
|
||||
// AnyVal is sealed but needs to be made aware of its children
|
||||
ScalaValueClasses foreach (AnyValClass addChild _)
|
||||
|
||||
if (forMSIL) {
|
||||
val intType = IntClass.typeConstructor
|
||||
|
|
|
@ -1491,10 +1491,13 @@ trait Symbols extends reflect.generic.Symbols { self: SymbolTable =>
|
|||
/** If this is a sealed class, its known direct subclasses. Otherwise Set.empty */
|
||||
def children: List[Symbol] = Nil
|
||||
|
||||
/** Recursively finds all sealed descendants and returns a sorted list. */
|
||||
/** Recursively finds all sealed descendants and returns a sorted list.
|
||||
* Includes this symbol unless it is abstract, but as value classes are
|
||||
* marked abstract so they can't be instantiated, they are special cased.
|
||||
*/
|
||||
def sealedDescendants: List[Symbol] = {
|
||||
val kids = children flatMap (_.sealedDescendants)
|
||||
val all = if (this hasFlag ABSTRACT) kids else this :: kids
|
||||
val all = if (isAbstractClass && !isValueClass(this)) kids else this :: kids
|
||||
|
||||
all.distinct sortBy (_.sealedSortName)
|
||||
}
|
||||
|
|
|
@ -0,0 +1,12 @@
|
|||
anyval-sealed.scala:2: error: match is not exhaustive!
|
||||
missing combination Byte
|
||||
missing combination Char
|
||||
missing combination Double
|
||||
missing combination Float
|
||||
missing combination Long
|
||||
missing combination Short
|
||||
missing combination Unit
|
||||
|
||||
def f(x: AnyVal) = x match {
|
||||
^
|
||||
one error found
|
|
@ -0,0 +1 @@
|
|||
-Xfatal-warnings
|
|
@ -0,0 +1,6 @@
|
|||
class A {
|
||||
def f(x: AnyVal) = x match {
|
||||
case _: Boolean => 1
|
||||
case _: Int => 2
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue