aboutsummaryrefslogtreecommitdiff
path: root/compiler/src/dotty/tools/dotc/core/TypeErasure.scala
diff options
context:
space:
mode:
authorGuillaume Martres <smarter@ubuntu.com>2017-03-08 22:46:41 +0100
committerGuillaume Martres <smarter@ubuntu.com>2017-03-08 23:21:11 +0100
commite0b6f397e5476a6a0ca95e81dd3a7a6711f8119e (patch)
tree4e994f7ec0f8f6a0121b180631f23edda7383fac /compiler/src/dotty/tools/dotc/core/TypeErasure.scala
parentc84480960cf618c29705dbaab9332d304a081524 (diff)
downloaddotty-e0b6f397e5476a6a0ca95e81dd3a7a6711f8119e.tar.gz
dotty-e0b6f397e5476a6a0ca95e81dd3a7a6711f8119e.tar.bz2
dotty-e0b6f397e5476a6a0ca95e81dd3a7a6711f8119e.zip
Fix bug in erasedLub leading to incorrect signatures
Before this commit, the added testcase failed in a strange way: 14 | def bla(foo: Foo) = orElse2(identity).apply(foo) | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ |value of type <nonsensical><notype></nonsensical> does not take parameters This happened because the TermRef for the apply method had an incorrect signature, therefore its underlying type was NoType. According to the documentation of `erasedLub`, the erasure should be: "a common superclass or trait S of the argument classes, with the following two properties: S is minimal: no other common superclass or trait derives from S] S is last : in the linearization of the first argument type `tp1` there are no minimal common superclasses or traits that come after S. (the reason to pick last is that we prefer classes over traits that way)." I'm not convinced that the implementation satisfies either of these two properties, but this commit at least makes S closer to being minimal by making sure that the last best candidate never derives from it.
Diffstat (limited to 'compiler/src/dotty/tools/dotc/core/TypeErasure.scala')
-rw-r--r--compiler/src/dotty/tools/dotc/core/TypeErasure.scala12
1 files changed, 8 insertions, 4 deletions
diff --git a/compiler/src/dotty/tools/dotc/core/TypeErasure.scala b/compiler/src/dotty/tools/dotc/core/TypeErasure.scala
index ff99008bb..2140405b1 100644
--- a/compiler/src/dotty/tools/dotc/core/TypeErasure.scala
+++ b/compiler/src/dotty/tools/dotc/core/TypeErasure.scala
@@ -246,10 +246,14 @@ object TypeErasure {
val cls2 = tp2.classSymbol
def loop(bcs: List[ClassSymbol], bestSoFar: ClassSymbol): ClassSymbol = bcs match {
case bc :: bcs1 =>
- if (cls2.derivesFrom(bc))
- if (!bc.is(Trait) && bc != defn.AnyClass) bc
- else loop(bcs1, if (bestSoFar.derivesFrom(bc)) bestSoFar else bc)
- else
+ if (cls2.derivesFrom(bc)) {
+ val newBest = if (bestSoFar.derivesFrom(bc)) bestSoFar else bc
+
+ if (!bc.is(Trait) && bc != defn.AnyClass)
+ newBest
+ else
+ loop(bcs1, newBest)
+ } else
loop(bcs1, bestSoFar)
case nil =>
bestSoFar