aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMartin Odersky <odersky@gmail.com>2017-02-01 17:18:13 +1100
committerMartin Odersky <odersky@gmail.com>2017-02-01 17:48:32 +1100
commite34555f69e7cdd6d19d0d1ed969127f4ee65c36e (patch)
tree9b3011bf3074f1d1d8e7d815814b8ed370d98639
parentb11e6d678a92187e5e9f821ba1116cec2cce0f8c (diff)
downloaddotty-e34555f69e7cdd6d19d0d1ed969127f4ee65c36e.tar.gz
dotty-e34555f69e7cdd6d19d0d1ed969127f4ee65c36e.tar.bz2
dotty-e34555f69e7cdd6d19d0d1ed969127f4ee65c36e.zip
Disallow taking a class tag of Nothing or Null.
It seems in most cases this leads to weird behavior and cause confusing error messages later. It also means we cannot create an Array[Nothing], except by passing the classtag explicitly.
-rw-r--r--compiler/src/dotty/tools/dotc/typer/Implicits.scala2
-rw-r--r--tests/neg/i1802.scala4
-rw-r--r--tests/neg/i1907.scala7
-rw-r--r--tests/neg/undet-classtag.scala5
-rw-r--r--tests/pos/t3859.scala2
-rw-r--r--tests/pos/t5859.scala4
-rw-r--r--tests/run/array-addition.scala4
7 files changed, 21 insertions, 7 deletions
diff --git a/compiler/src/dotty/tools/dotc/typer/Implicits.scala b/compiler/src/dotty/tools/dotc/typer/Implicits.scala
index 2112b1221..f7d8556a7 100644
--- a/compiler/src/dotty/tools/dotc/typer/Implicits.scala
+++ b/compiler/src/dotty/tools/dotc/typer/Implicits.scala
@@ -521,6 +521,8 @@ trait Implicits { self: Typer =>
val etag = inferImplicitArg(defn.ClassTagType.appliedTo(elemTp), error, pos)
if (etag.isEmpty) etag else etag.select(nme.wrap)
case tp if hasStableErasure(tp) =>
+ if (defn.isBottomClass(tp.typeSymbol))
+ error(where => i"attempt to take ClassTag of undetermined type for $where")
ref(defn.ClassTagModule)
.select(nme.apply)
.appliedToType(tp)
diff --git a/tests/neg/i1802.scala b/tests/neg/i1802.scala
index 56da672a8..93e790f18 100644
--- a/tests/neg/i1802.scala
+++ b/tests/neg/i1802.scala
@@ -14,8 +14,8 @@ object Exception {
def apply(x: Throwable): T = f(downcast(x).get)
}
- def mkThrowableCatcher[T](isDef: Throwable => Boolean, f: Throwable => T) = mkCatcher(isDef, f)
+ def mkThrowableCatcher[T](isDef: Throwable => Boolean, f: Throwable => T) = mkCatcher(isDef, f) // error: undetermined ClassTag
- implicit def throwableSubtypeToCatcher[Ex <: Throwable: ClassTag, T](pf: PartialFunction[Ex, T]) = // error: cyclic reference
+ implicit def throwableSubtypeToCatcher[Ex <: Throwable: ClassTag, T](pf: PartialFunction[Ex, T]) =
mkCatcher(pf.isDefinedAt _, pf.apply _)
}
diff --git a/tests/neg/i1907.scala b/tests/neg/i1907.scala
new file mode 100644
index 000000000..6bc3bb56f
--- /dev/null
+++ b/tests/neg/i1907.scala
@@ -0,0 +1,7 @@
+import java.io.File
+
+object Test {
+ Some(new File("."))
+ .map(_.listFiles).getOrElse(Array.empty) // error: undetermined ClassTag
+ .map(_.listFiles)
+}
diff --git a/tests/neg/undet-classtag.scala b/tests/neg/undet-classtag.scala
new file mode 100644
index 000000000..563596d14
--- /dev/null
+++ b/tests/neg/undet-classtag.scala
@@ -0,0 +1,5 @@
+object Test {
+ def f[T: reflect.ClassTag](x: T) = ???
+
+ f(???) // error: undetermined ClassTag
+}
diff --git a/tests/pos/t3859.scala b/tests/pos/t3859.scala
index 992207301..486c1d4b2 100644
--- a/tests/pos/t3859.scala
+++ b/tests/pos/t3859.scala
@@ -1,4 +1,4 @@
class Test {
- def foo: Unit = bar(Array(): _*)
+ def foo: Unit = bar(Array[AnyRef](): _*)
def bar(values: AnyRef*): Unit = ()
}
diff --git a/tests/pos/t5859.scala b/tests/pos/t5859.scala
index 2a31e68ee..60ec8b4cb 100644
--- a/tests/pos/t5859.scala
+++ b/tests/pos/t5859.scala
@@ -7,9 +7,9 @@ class A {
f(List[AnyRef](): _*)
f(List(): _*)
f(Nil: _*)
- f(Array(): _*)
+ // f(Array(): _*) // undetermined ClassTag
f(Array[AnyRef](): _*)
f(List(1))
f(List(1), Nil: _*)
- f(List(1), Array(): _*)
+ // f(List(1), Array(): _*) // undetermined ClassTag
}
diff --git a/tests/run/array-addition.scala b/tests/run/array-addition.scala
index 8def48e85..09a1b0bad 100644
--- a/tests/run/array-addition.scala
+++ b/tests/run/array-addition.scala
@@ -4,8 +4,8 @@ object Test {
def main(args: Array[String]): Unit = {
prettyPrintArray(Array(1,2,3) :+ 4)
prettyPrintArray(1 +: Array(2,3,4))
- prettyPrintArray(Array() :+ 1)
- prettyPrintArray(1 +: Array())
+ prettyPrintArray(Array[Int]() :+ 1)
+ prettyPrintArray(1 +: Array[Int]())
}
}