diff options
author | Seth Tisue <seth@tisue.net> | 2017-02-16 14:14:39 -0800 |
---|---|---|
committer | Seth Tisue <seth@tisue.net> | 2017-02-16 14:34:18 -0800 |
commit | 04c45e15f198c3e33b0e6709fb8ca5267f129fac (patch) | |
tree | 215307f083dba29d2c53c83ca3702c8d4a34d27f /src/compiler/scala/tools/nsc/transform | |
parent | 6be69d6d5e710e2022772a326a48baf093a70508 (diff) | |
parent | 096502880900d8daa75d813c63ac88aa50c25ef0 (diff) | |
download | scala-04c45e15f198c3e33b0e6709fb8ca5267f129fac.tar.gz scala-04c45e15f198c3e33b0e6709fb8ca5267f129fac.tar.bz2 scala-04c45e15f198c3e33b0e6709fb8ca5267f129fac.zip |
Merge commit '0965028809' into merge-2.11.x-to-2.12.x-20170214
Diffstat (limited to 'src/compiler/scala/tools/nsc/transform')
-rw-r--r-- | src/compiler/scala/tools/nsc/transform/Erasure.scala | 38 |
1 files changed, 21 insertions, 17 deletions
diff --git a/src/compiler/scala/tools/nsc/transform/Erasure.scala b/src/compiler/scala/tools/nsc/transform/Erasure.scala index 3ce7db35d8..e327a6658c 100644 --- a/src/compiler/scala/tools/nsc/transform/Erasure.scala +++ b/src/compiler/scala/tools/nsc/transform/Erasure.scala @@ -456,7 +456,15 @@ abstract class Erasure extends InfoTransform override def newTyper(context: Context) = new Eraser(context) class ComputeBridges(unit: CompilationUnit, root: Symbol) { - assert(phase == currentRun.erasurePhase, phase) + + class BridgesCursor(root: Symbol) extends overridingPairs.Cursor(root) { + override def parents = List(root.info.firstParent) + // Varargs bridges may need generic bridges due to the non-repeated part of the signature of the involved methods. + // The vararg bridge is generated during refchecks (probably to simplify override checking), + // but then the resulting varargs "bridge" method may itself need an actual erasure bridge. + // TODO: like javac, generate just one bridge method that wraps Seq <-> varargs and does erasure-induced casts + override def exclude(sym: Symbol) = !sym.isMethod || super.exclude(sym) + } var toBeRemoved = immutable.Set[Symbol]() val site = root.thisType @@ -464,12 +472,7 @@ abstract class Erasure extends InfoTransform val bridgeTarget = mutable.HashMap[Symbol, Symbol]() var bridges = List[Tree]() - val opc = enteringExplicitOuter { - new overridingPairs.Cursor(root) { - override def parents = List(root.info.firstParent) - override def exclude(sym: Symbol) = !sym.isMethod || super.exclude(sym) - } - } + val opc = enteringExplicitOuter { new BridgesCursor(root) } def compute(): (List[Tree], immutable.Set[Symbol]) = { while (opc.hasNext) { @@ -860,6 +863,16 @@ abstract class Erasure extends InfoTransform } } + private class DoubleDefsCursor(root: Symbol) extends Cursor(root) { + // specialized members have no type history before 'specialize', causing double def errors for curried defs + override def exclude(sym: Symbol): Boolean = ( + sym.isType + || super.exclude(sym) + || !sym.hasTypeAt(currentRun.refchecksPhase.id) + ) + override def matches(lo: Symbol, high: Symbol) = !high.isPrivate + } + /** Emit an error if there is a double definition. This can happen if: * * - A template defines two members with the same name and erased type. @@ -870,21 +883,12 @@ abstract class Erasure extends InfoTransform */ private def checkNoDoubleDefs(root: Symbol) { checkNoDeclaredDoubleDefs(root) - object opc extends Cursor(root) { - // specialized members have no type history before 'specialize', causing double def errors for curried defs - override def exclude(sym: Symbol): Boolean = ( - sym.isType - || super.exclude(sym) - || !sym.hasTypeAt(currentRun.refchecksPhase.id) - ) - override def matches(lo: Symbol, high: Symbol) = !high.isPrivate - } def isErasureDoubleDef(pair: SymbolPair) = { import pair._ log(s"Considering for erasure clash:\n$pair") !exitingRefchecks(lowType matches highType) && sameTypeAfterErasure(low, high) } - opc.iterator filter isErasureDoubleDef foreach doubleDefError + (new DoubleDefsCursor(root)).iterator filter isErasureDoubleDef foreach doubleDefError } /** Add bridge definitions to a template. This means: |