diff options
author | Martin Odersky <odersky@gmail.com> | 2013-09-05 15:36:25 +0200 |
---|---|---|
committer | Martin Odersky <odersky@gmail.com> | 2013-09-05 15:37:57 +0200 |
commit | f7ab848229e8b9b0de1b719725816209aa1271c8 (patch) | |
tree | 2d7ea759ed63413e8b6ac19cff8eea930797f412 | |
parent | 441613bd49f9b5629eefffdc30a52869c0732ca0 (diff) | |
download | dotty-f7ab848229e8b9b0de1b719725816209aa1271c8.tar.gz dotty-f7ab848229e8b9b0de1b719725816209aa1271c8.tar.bz2 dotty-f7ab848229e8b9b0de1b719725816209aa1271c8.zip |
Several fixes in typer.
Also updated tests.
-rw-r--r-- | src/dotty/tools/dotc/core/TyperState.scala | 49 | ||||
-rw-r--r-- | src/dotty/tools/dotc/typer/Applications.scala | 2 | ||||
-rw-r--r-- | src/dotty/tools/dotc/typer/Typer.scala | 2 | ||||
-rw-r--r-- | tests/pos/implicits1.scala | 10 | ||||
-rw-r--r-- | tests/pos/inferred.scala | 4 |
5 files changed, 54 insertions, 13 deletions
diff --git a/src/dotty/tools/dotc/core/TyperState.scala b/src/dotty/tools/dotc/core/TyperState.scala index 7f161d994..21dc73579 100644 --- a/src/dotty/tools/dotc/core/TyperState.scala +++ b/src/dotty/tools/dotc/core/TyperState.scala @@ -7,8 +7,11 @@ import Flags._ import Contexts._ import util.SimpleMap import reporting._ +import printing.{Showable, Printer} +import printing.Texts._ +import annotation.elidable -class TyperState(val reporter: Reporter = ThrowingReporter) extends DotClass { +class TyperState(val reporter: Reporter = ThrowingReporter) extends DotClass with Showable { /** The current constraint set */ def constraint: Constraint = new Constraint(SimpleMap.Empty) @@ -18,7 +21,7 @@ class TyperState(val reporter: Reporter = ThrowingReporter) extends DotClass { /** A map that records for instantiated type vars their instance type. * Used only in a temporary way for contexts that may be retracted - * without also retracting the type var. + * without also retracting the type var as a whole. */ def instType: SimpleMap[TypeVar, Type] = SimpleMap.Empty @@ -29,14 +32,16 @@ class TyperState(val reporter: Reporter = ThrowingReporter) extends DotClass { def fresh: TyperState = this def commit()(implicit ctx: Context): Unit = unsupported("commit") + + @elidable(elidable.FINER) + def checkConsistent(implicit ctx: Context) = () + + override def toText(printer: Printer): Text = "ImmutableTyperState" } class MutableTyperState(previous: TyperState, reporter: Reporter) extends TyperState(reporter) { - def checkConsistent() = - for (tvar <- undetVars) assert(constraint(tvar.origin) != NoType, tvar) - private var myConstraint: Constraint = previous.constraint private var myUndetVars: Set[TypeVar] = previous.undetVars private var myInstType: SimpleMap[TypeVar, Type] = previous.instType @@ -46,10 +51,7 @@ extends TyperState(reporter) { override def instType = myInstType override def constraint_=(c: Constraint) = myConstraint = c - override def undetVars_=(vs: Set[TypeVar]) = { - myUndetVars = vs - //checkConsistent() - } + override def undetVars_=(vs: Set[TypeVar]) = myUndetVars = vs override def instType_=(m: SimpleMap[TypeVar, Type]): Unit = myInstType = m override def fresh: TyperState = new MutableTyperState(this, new StoreReporter) @@ -61,7 +63,7 @@ extends TyperState(reporter) { * instantiated instead. */ override def commit()(implicit ctx: Context) = { - var targetState = ctx.typerState + val targetState = ctx.typerState targetState.constraint = constraint targetState.undetVars = undetVars targetState.instType = instType @@ -69,7 +71,7 @@ extends TyperState(reporter) { def adjustOwningState(tvar: TypeVar) = if (tvar.owningState eq this) tvar.owningState = targetState undetVars foreach adjustOwningState - instType foreachKey { case tvar: TypeVar => + instType foreachKey { tvar => adjustOwningState(tvar) if (tvar.owningState == targetState) { tvar.inst = instType(tvar) @@ -79,4 +81,29 @@ extends TyperState(reporter) { reporter.flush() } + + @elidable(elidable.FINER) + override def checkConsistent(implicit ctx: Context) = { + def err(msg: String, what: Showable) = s"$msg: ${what.show}\n${this.show}" + for (tvar <- undetVars) + assert(constraint(tvar.origin).exists, err("unconstrained type var", tvar)) + val undetParams = undetVars map (_.origin) + for (param <- constraint.domainParams) + assert(undetParams contains param, err("junk constraint on", param)) + instType.foreachKey { tvar => + assert(undetVars contains tvar, err("junk instType on", tvar)) + } + } + + override def toText(printer: Printer): Text = { + val undetVarsText = + " undetVars = (" ~ + Text(undetVars map (_.toText(printer)), ", ") ~ ")" + val constraintText = + " constraint = " ~ constraint.toText(printer) + val instTypeText = + " instType = (" ~ + Text(instType.map2((k, v) => s"${k.toText(printer)} -> ${v.toText(printer)}"), ", ") ~ ")" + Text.lines(List(undetVarsText, constraintText, instTypeText)) + } } diff --git a/src/dotty/tools/dotc/typer/Applications.scala b/src/dotty/tools/dotc/typer/Applications.scala index 99e29fb30..8e3bb9dbb 100644 --- a/src/dotty/tools/dotc/typer/Applications.scala +++ b/src/dotty/tools/dotc/typer/Applications.scala @@ -713,7 +713,7 @@ trait Applications extends Compatibility { self: Typer => best :: asGood(alts1) } - private val dummyTree = untpd.Literal(Constant(null)) + private lazy val dummyTree = untpd.Literal(Constant(null)) def dummyTreeOfType(tp: Type): Tree = dummyTree withTypeUnchecked tp /** Resolve overloaded alternative `alts`, given expected type `pt`. */ diff --git a/src/dotty/tools/dotc/typer/Typer.scala b/src/dotty/tools/dotc/typer/Typer.scala index dd07c921d..9815015c1 100644 --- a/src/dotty/tools/dotc/typer/Typer.scala +++ b/src/dotty/tools/dotc/typer/Typer.scala @@ -1000,7 +1000,7 @@ class Typer extends Namer with Applications with Implicits { i"""missing arguments for $methodStr |follow this method with `_' if you want to treat it as a partially applied function""".stripMargin) case _ => - if (typeConforms(tree.tpe, pt)) tree + if (tree.tpe <:< pt) tree else if (ctx.mode is Mode.Pattern) tree // no subtype check for patterns else if (ctx.mode is Mode.Type) err.typeMismatch(tree, pt) else adaptToSubType(wtp) diff --git a/tests/pos/implicits1.scala b/tests/pos/implicits1.scala index 2f0399b74..76d9dfd25 100644 --- a/tests/pos/implicits1.scala +++ b/tests/pos/implicits1.scala @@ -2,6 +2,12 @@ class X(val elem: Int) { def foo(y: String): Int = y.length + elem } +object X { + implicit class BarDeco(x: X) { + def bar: String = "!" + } +} + object Implicits { implicit val impl: X = new X(0) @@ -29,6 +35,10 @@ object Implicits { val c: Int = y.elem val d: Int = z.foo("abc") + + import X.BarDeco + + println(z.bar) // val e: Int = z.foo(true) not yet diff --git a/tests/pos/inferred.scala b/tests/pos/inferred.scala index 295cc9b49..c138a8e53 100644 --- a/tests/pos/inferred.scala +++ b/tests/pos/inferred.scala @@ -12,4 +12,8 @@ object Inferred { val nn = bar(Nil) + val ints: List[Int] = 1 :: Nil + + val a = if (1 == 0) Nil else ints + } |