Skip to content

Fix #4375: Properly erase SeqLiteral #4387

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Apr 27, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 21 additions & 10 deletions compiler/src/dotty/tools/dotc/typer/Typer.scala
Original file line number Diff line number Diff line change
Expand Up @@ -1126,20 +1126,31 @@ class Typer extends Namer
}

def typedSeqLiteral(tree: untpd.SeqLiteral, pt: Type)(implicit ctx: Context): SeqLiteral = track("typedSeqLiteral") {
val proto1 = pt.elemType match {
val elemProto = pt.elemType match {
case NoType => WildcardType
case bounds: TypeBounds => WildcardType(bounds)
case elemtp => elemtp
}
val elems1 = tree.elems mapconserve (typed(_, proto1))
val proto2 = // the computed type of the `elemtpt` field
if (!tree.elemtpt.isEmpty) WildcardType
else if (isFullyDefined(proto1, ForceDegree.none)) proto1
else if (tree.elems.isEmpty && tree.isInstanceOf[Trees.JavaSeqLiteral[_]])
defn.ObjectType // generic empty Java varargs are of type Object[]
else ctx.typeComparer.lub(elems1.tpes)
val elemtpt1 = typed(tree.elemtpt, proto2)
assignType(cpy.SeqLiteral(tree)(elems1, elemtpt1), elems1, elemtpt1)

def assign(elems1: List[Tree], elemtpt1: Tree) =
assignType(cpy.SeqLiteral(tree)(elems1, elemtpt1), elems1, elemtpt1)

if (!tree.elemtpt.isEmpty) {
val elemtpt1 = typed(tree.elemtpt, elemProto)
val elems1 = tree.elems.mapconserve(typed(_, elemtpt1.tpe))
assign(elems1, elemtpt1)
} else {
val elems1 = tree.elems.mapconserve(typed(_, elemProto))
val elemtptType =
if (isFullyDefined(elemProto, ForceDegree.none))
elemProto
else if (tree.elems.isEmpty && tree.isInstanceOf[Trees.JavaSeqLiteral[_]])
defn.ObjectType // generic empty Java varargs are of type Object[]
else
ctx.typeComparer.lub(elems1.tpes)
val elemtpt1 = typed(tree.elemtpt, elemtptType)
assign(elems1, elemtpt1)
}
}

def typedInlined(tree: untpd.Inlined, pt: Type)(implicit ctx: Context): Inlined = {
Expand Down
13 changes: 13 additions & 0 deletions tests/pos/i4375.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
object Test {
type Id[A] >: A
def test: Unit = {
val a: Array[_ >: Id[Int]] = Array(1, 2)
val b = a(0)
}

class VC(i: String) extends AnyVal
def test2: Unit = {
val c: Array[_ >: Id[VC]] = Array(new VC(""))
val d = c(0)
}
}