aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/dotty/tools/dotc/core/TypeErasure.scala1
-rw-r--r--src/dotty/tools/dotc/core/Types.scala20
-rw-r--r--src/dotty/tools/dotc/typer/Typer.scala2
-rw-r--r--test/dotc/tests.scala1
-rw-r--r--tests/neg/selfreq.scala37
5 files changed, 55 insertions, 6 deletions
diff --git a/src/dotty/tools/dotc/core/TypeErasure.scala b/src/dotty/tools/dotc/core/TypeErasure.scala
index 9b41eb982..0ef31015c 100644
--- a/src/dotty/tools/dotc/core/TypeErasure.scala
+++ b/src/dotty/tools/dotc/core/TypeErasure.scala
@@ -439,6 +439,7 @@ class TypeErasure(isJava: Boolean, semiEraseVCs: Boolean, isConstructor: Boolean
case ErasedValueType(_, underlying) =>
sigName(underlying)
case tp: TypeRef =>
+ if (!tp.denot.exists) throw new MissingType(tp.prefix, tp.name)
val sym = tp.symbol
if (!sym.isClass) sigName(tp.info)
else if (isDerivedValueClass(sym)) sigName(eraseDerivedValueClassRef(tp))
diff --git a/src/dotty/tools/dotc/core/Types.scala b/src/dotty/tools/dotc/core/Types.scala
index d6bb9c3c5..f4dbfb0e3 100644
--- a/src/dotty/tools/dotc/core/Types.scala
+++ b/src/dotty/tools/dotc/core/Types.scala
@@ -936,6 +936,7 @@ object Types {
/** the self type of the underlying classtype */
def givenSelfType(implicit ctx: Context): Type = this match {
case tp @ RefinedType(parent, name) => tp.wrapIfMember(parent.givenSelfType)
+ case tp: ThisType => tp.tref.givenSelfType
case tp: TypeProxy => tp.underlying.givenSelfType
case _ => NoType
}
@@ -3181,14 +3182,23 @@ object Types {
// ----- Exceptions -------------------------------------------------------------
class TypeError(msg: String) extends Exception(msg)
- class FatalTypeError(msg: String) extends TypeError(msg)
class MalformedType(pre: Type, denot: Denotation, absMembers: Set[Name])
- extends FatalTypeError(
- s"""malformed type: $pre is not a legal prefix for $denot because it contains abstract type member${if (absMembers.size == 1) "" else "s"} ${absMembers.mkString(", ")}""")
+ extends TypeError(
+ s"malformed type: $pre is not a legal prefix for $denot because it contains abstract type member${if (absMembers.size == 1) "" else "s"} ${absMembers.mkString(", ")}")
+
+ class MissingType(pre: Type, name: Name)(implicit ctx: Context) extends TypeError(
+ i"""cannot resolve reference to type $pre.$name
+ |the classfile defining the type might be missing from the classpath${otherReason(pre)}""".stripMargin)
+
+ private def otherReason(pre: Type)(implicit ctx: Context): String = pre match {
+ case pre: ThisType if pre.givenSelfType.exists =>
+ i"\nor the self type of $pre might not contain all transitive dependencies"
+ case _ => ""
+ }
class CyclicReference private (val denot: SymDenotation)
- extends FatalTypeError(s"cyclic reference involving $denot") {
+ extends TypeError(s"cyclic reference involving $denot") {
def show(implicit ctx: Context) = s"cyclic reference involving ${denot.show}"
}
@@ -3204,7 +3214,7 @@ object Types {
}
}
- class MergeError(msg: String) extends FatalTypeError(msg)
+ class MergeError(msg: String) extends TypeError(msg)
// ----- Debug ---------------------------------------------------------
diff --git a/src/dotty/tools/dotc/typer/Typer.scala b/src/dotty/tools/dotc/typer/Typer.scala
index 479eedd38..33ec156a1 100644
--- a/src/dotty/tools/dotc/typer/Typer.scala
+++ b/src/dotty/tools/dotc/typer/Typer.scala
@@ -1087,7 +1087,7 @@ class Typer extends Namer with TypeAssigner with Applications with Implicits wit
try adapt(typedUnadapted(tree, pt), pt, tree)
catch {
case ex: CyclicReference => errorTree(tree, cyclicErrorMsg(ex))
- case ex: FatalTypeError => errorTree(tree, ex.getMessage)
+ case ex: TypeError => errorTree(tree, ex.getMessage)
}
}
diff --git a/test/dotc/tests.scala b/test/dotc/tests.scala
index f222daca4..ee7b93297 100644
--- a/test/dotc/tests.scala
+++ b/test/dotc/tests.scala
@@ -139,6 +139,7 @@ class tests extends CompilerTest {
@Test def neg_escapingRefs = compileFile(negDir, "escapingRefs", xerrors = 2)
@Test def neg_instantiateAbstract = compileFile(negDir, "instantiateAbstract", xerrors = 8)
@Test def neg_selfInheritance = compileFile(negDir, "selfInheritance", xerrors = 5)
+ @Test def neg_selfreq = compileFile(negDir, "selfreq", xerrors = 4)
@Test def neg_shadowedImplicits = compileFile(negDir, "arrayclone-new", xerrors = 2)
@Test def neg_traitParamsTyper = compileFile(negDir, "traitParamsTyper", xerrors = 5)
@Test def neg_traitParamsMixin = compileFile(negDir, "traitParamsMixin", xerrors = 2)
diff --git a/tests/neg/selfreq.scala b/tests/neg/selfreq.scala
new file mode 100644
index 000000000..e75e03c16
--- /dev/null
+++ b/tests/neg/selfreq.scala
@@ -0,0 +1,37 @@
+trait X { self: Y =>
+
+ type T <: self.U
+
+ def foo(x: T): T
+ def foo(x: String): String
+
+}
+
+trait Y { self: Z =>
+
+ type U <: self.V
+
+}
+
+trait Z {
+
+ class V
+
+}
+
+object O {
+ val x: X = ???
+ x.foo("a")
+}
+
+import scala.tools.nsc.interpreter.IMain
+
+object Test extends dotty.runtime.LegacyApp {
+ val engine = new IMain.Factory getScriptEngine()
+ engine.asInstanceOf[IMain].settings.usejavacp.value = true
+ val res2 = engine.asInstanceOf[javax.script.Compilable]
+ res2 compile "8" eval()
+ val res5 = res2 compile """println("hello") ; 8"""
+ res5 eval()
+ res5 eval()
+}