Skip to content

Commit

Permalink
fix scala#4030: avoid adding duplicate binders
Browse files Browse the repository at this point in the history
  • Loading branch information
liufengyun committed Feb 22, 2018
1 parent 02725c6 commit 24841e1
Show file tree
Hide file tree
Showing 2 changed files with 37 additions and 11 deletions.
26 changes: 15 additions & 11 deletions compiler/src/dotty/tools/dotc/typer/Applications.scala
Original file line number Diff line number Diff line change
Expand Up @@ -908,17 +908,21 @@ trait Applications extends Compatibility { self: Typer with Dynamic =>
}

/** Add a `Bind` node for each `bound` symbol in a type application `unapp` */
def addBinders(unapp: Tree, bound: List[Symbol]) = unapp match {
case TypeApply(fn, args) =>
def addBinder(arg: Tree) = arg.tpe.stripTypeVar match {
case ref: TypeRef if bound.contains(ref.symbol) =>
tpd.Bind(ref.symbol, Ident(ref))
case _ =>
arg
}
tpd.cpy.TypeApply(unapp)(fn, args.mapConserve(addBinder))
case _ =>
unapp
def addBinders(unapp: Tree, bound: List[Symbol]) = {
var remain = bound.toSet
unapp match {
case TypeApply(fn, args) =>
def addBinder(arg: Tree) = arg.tpe.stripTypeVar match {
case ref: TypeRef if remain.contains(ref.symbol) =>
remain -= ref.symbol
tpd.Bind(ref.symbol, Ident(ref))
case _ =>
arg
}
tpd.cpy.TypeApply(unapp)(fn, args.mapConserve(addBinder))
case _ =>
unapp
}
}

def fromScala2x = unapplyFn.symbol.exists && (unapplyFn.symbol.owner is Scala2x)
Expand Down
22 changes: 22 additions & 0 deletions tests/pos/i4030.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
sealed trait Root[T]
case object C1 extends Root[Int]
case object C2 extends Root[String]
//case class C3[X, Y]() extends Root[X|Y|(X => X)]
case class C3[X, Y]() extends Root[(X => X)|(Y => Y)|(X => Y)]
case class C4[X, Y]() extends Root[(X => X)|(Y => Y)|(X => Y)]

object TestGADT {
//type Foo // abstract

def f[A <: Seq[_], B, Foo >: A => B](v: Root[Foo], u: Root[Foo]) = (v, u) match {
//case C1 =>
//case C2 =>
case (C3(), C3()) =>
}
//f(C3[Int, Int]())
//implicitly[Int <:< Int|(Int => Int)]
//implicitly[(Int => Int) <:< String|(Int => Int)]//($conforms[Int => Int])
//f[Int, Int, Int|(Int => Int)](C3[Int, Int]())
//f(C3[Int, Int]())
f(C3[Seq[_], Long](), C4[Seq[_], Long]())
}

0 comments on commit 24841e1

Please sign in to comment.