aboutsummaryrefslogtreecommitdiff
path: root/src/dotty/tools
diff options
context:
space:
mode:
Diffstat (limited to 'src/dotty/tools')
-rw-r--r--src/dotty/tools/dotc/ast/Desugar.scala2
-rw-r--r--src/dotty/tools/dotc/ast/Trees.scala30
-rw-r--r--src/dotty/tools/dotc/ast/tpd.scala22
-rw-r--r--src/dotty/tools/dotc/ast/untpd.scala4
-rw-r--r--src/dotty/tools/dotc/core/classfile/ClassfileParser.scala9
-rw-r--r--src/dotty/tools/dotc/core/tasty/TreePickler.scala4
-rw-r--r--src/dotty/tools/dotc/core/tasty/TreeUnpickler.scala5
-rw-r--r--src/dotty/tools/dotc/core/unpickleScala2/Scala2Unpickler.scala6
-rw-r--r--src/dotty/tools/dotc/printing/RefinedPrinter.scala4
-rw-r--r--src/dotty/tools/dotc/transform/ElimRepeated.scala4
-rw-r--r--src/dotty/tools/dotc/transform/SeqLiterals.scala4
-rw-r--r--src/dotty/tools/dotc/transform/TreeTransform.scala3
-rw-r--r--src/dotty/tools/dotc/typer/Applications.scala7
-rw-r--r--src/dotty/tools/dotc/typer/ReTyper.scala2
-rw-r--r--src/dotty/tools/dotc/typer/TypeAssigner.scala14
-rw-r--r--src/dotty/tools/dotc/typer/Typer.scala9
16 files changed, 74 insertions, 55 deletions
diff --git a/src/dotty/tools/dotc/ast/Desugar.scala b/src/dotty/tools/dotc/ast/Desugar.scala
index 8ba155097..1eafea049 100644
--- a/src/dotty/tools/dotc/ast/Desugar.scala
+++ b/src/dotty/tools/dotc/ast/Desugar.scala
@@ -1000,7 +1000,7 @@ object desugar {
collect(expr)
case NamedArg(_, arg) =>
collect(arg)
- case SeqLiteral(elems) =>
+ case SeqLiteral(elems, _) =>
elems foreach collect
case Alternative(trees) =>
for (tree <- trees; (vble, _) <- getVariables(tree))
diff --git a/src/dotty/tools/dotc/ast/Trees.scala b/src/dotty/tools/dotc/ast/Trees.scala
index 54ace3be4..5fbbad9a1 100644
--- a/src/dotty/tools/dotc/ast/Trees.scala
+++ b/src/dotty/tools/dotc/ast/Trees.scala
@@ -515,16 +515,18 @@ object Trees {
type ThisTree[-T >: Untyped] = Try[T]
}
- /** Seq(elems) */
- case class SeqLiteral[-T >: Untyped] private[ast] (elems: List[Tree[T]])
+ /** Seq(elems)
+ * @param tpt The element type of the sequence.
+ */
+ case class SeqLiteral[-T >: Untyped] private[ast] (elems: List[Tree[T]], elemtpt: Tree[T])
extends Tree[T] {
type ThisTree[-T >: Untyped] = SeqLiteral[T]
}
/** Array(elems) */
- class JavaSeqLiteral[T >: Untyped] private[ast] (elems: List[Tree[T]])
- extends SeqLiteral(elems) {
- override def toString = s"JavaSeqLiteral($elems)"
+ class JavaSeqLiteral[T >: Untyped] private[ast] (elems: List[Tree[T]], elemtpt: Tree[T])
+ extends SeqLiteral(elems, elemtpt) {
+ override def toString = s"JavaSeqLiteral($elems, $elemtpt)"
}
/** A type tree that represents an existing or inferred type */
@@ -974,12 +976,12 @@ object Trees {
case tree: Try if (expr eq tree.expr) && (cases eq tree.cases) && (finalizer eq tree.finalizer) => tree
case _ => finalize(tree, untpd.Try(expr, cases, finalizer))
}
- def SeqLiteral(tree: Tree)(elems: List[Tree])(implicit ctx: Context): SeqLiteral = tree match {
+ def SeqLiteral(tree: Tree)(elems: List[Tree], elemtpt: Tree)(implicit ctx: Context): SeqLiteral = tree match {
case tree: JavaSeqLiteral =>
- if (elems eq tree.elems) tree
- else finalize(tree, new JavaSeqLiteral(elems))
- case tree: SeqLiteral if elems eq tree.elems => tree
- case _ => finalize(tree, untpd.SeqLiteral(elems))
+ if ((elems eq tree.elems) && (elemtpt eq tree.elemtpt)) tree
+ else finalize(tree, new JavaSeqLiteral(elems, elemtpt))
+ case tree: SeqLiteral if (elems eq tree.elems) && (elemtpt eq tree.elemtpt) => tree
+ case _ => finalize(tree, untpd.SeqLiteral(elems, elemtpt))
}
def TypeTree(tree: Tree)(original: Tree): TypeTree = tree match {
case tree: TypeTree if original eq tree.original => tree
@@ -1125,8 +1127,8 @@ object Trees {
cpy.Return(tree)(transform(expr), transformSub(from))
case Try(block, cases, finalizer) =>
cpy.Try(tree)(transform(block), transformSub(cases), transform(finalizer))
- case SeqLiteral(elems) =>
- cpy.SeqLiteral(tree)(transform(elems))
+ case SeqLiteral(elems, elemtpt) =>
+ cpy.SeqLiteral(tree)(transform(elems), transform(elemtpt))
case TypeTree(original) =>
tree
case SingletonTypeTree(ref) =>
@@ -1229,8 +1231,8 @@ object Trees {
this(this(x, expr), from)
case Try(block, handler, finalizer) =>
this(this(this(x, block), handler), finalizer)
- case SeqLiteral(elems) =>
- this(x, elems)
+ case SeqLiteral(elems, elemtpt) =>
+ this(this(x, elems), elemtpt)
case TypeTree(original) =>
x
case SingletonTypeTree(ref) =>
diff --git a/src/dotty/tools/dotc/ast/tpd.scala b/src/dotty/tools/dotc/ast/tpd.scala
index 9a6f74331..a6d97478b 100644
--- a/src/dotty/tools/dotc/ast/tpd.scala
+++ b/src/dotty/tools/dotc/ast/tpd.scala
@@ -123,14 +123,11 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo {
def Try(block: Tree, cases: List[CaseDef], finalizer: Tree)(implicit ctx: Context): Try =
ta.assignType(untpd.Try(block, cases, finalizer), block, cases)
- def SeqLiteral(elems: List[Tree])(implicit ctx: Context): SeqLiteral =
- ta.assignType(untpd.SeqLiteral(elems), elems)
+ def SeqLiteral(elems: List[Tree], elemtpt: Tree)(implicit ctx: Context): SeqLiteral =
+ ta.assignType(untpd.SeqLiteral(elems, elemtpt), elems, elemtpt)
- def SeqLiteral(tpe: Type, elems: List[Tree])(implicit ctx: Context): SeqLiteral =
- if (tpe derivesFrom defn.SeqClass) SeqLiteral(elems) else JavaSeqLiteral(elems)
-
- def JavaSeqLiteral(elems: List[Tree])(implicit ctx: Context): SeqLiteral =
- ta.assignType(new untpd.JavaSeqLiteral(elems), elems)
+ def JavaSeqLiteral(elems: List[Tree], elemtpt: Tree)(implicit ctx: Context): SeqLiteral =
+ ta.assignType(new untpd.JavaSeqLiteral(elems, elemtpt), elems, elemtpt)
def TypeTree(original: Tree)(implicit ctx: Context): TypeTree =
TypeTree(original.tpe, original)
@@ -564,11 +561,14 @@ object tpd extends Trees.Instance[Type] with TypedTreeInfo {
}
}
- override def SeqLiteral(tree: Tree)(elems: List[Tree])(implicit ctx: Context): SeqLiteral = {
- val tree1 = untpd.cpy.SeqLiteral(tree)(elems)
+ override def SeqLiteral(tree: Tree)(elems: List[Tree], elemtpt: Tree)(implicit ctx: Context): SeqLiteral = {
+ val tree1 = untpd.cpy.SeqLiteral(tree)(elems, elemtpt)
tree match {
- case tree: SeqLiteral if sameTypes(elems, tree.elems) => tree1.withTypeUnchecked(tree.tpe)
- case _ => ta.assignType(tree1, elems)
+ case tree: SeqLiteral
+ if sameTypes(elems, tree.elems) && (elemtpt.tpe eq tree.elemtpt.tpe) =>
+ tree1.withTypeUnchecked(tree.tpe)
+ case _ =>
+ ta.assignType(tree1, elems, elemtpt)
}
}
diff --git a/src/dotty/tools/dotc/ast/untpd.scala b/src/dotty/tools/dotc/ast/untpd.scala
index 85052a4da..c7a7036c3 100644
--- a/src/dotty/tools/dotc/ast/untpd.scala
+++ b/src/dotty/tools/dotc/ast/untpd.scala
@@ -127,8 +127,8 @@ object untpd extends Trees.Instance[Untyped] with UntypedTreeInfo {
def CaseDef(pat: Tree, guard: Tree, body: Tree): CaseDef = new CaseDef(pat, guard, body)
def Return(expr: Tree, from: Tree): Return = new Return(expr, from)
def Try(expr: Tree, cases: List[CaseDef], finalizer: Tree): Try = new Try(expr, cases, finalizer)
- def SeqLiteral(elems: List[Tree]): SeqLiteral = new SeqLiteral(elems)
- def JavaSeqLiteral(elems: List[Tree]): JavaSeqLiteral = new JavaSeqLiteral(elems)
+ def SeqLiteral(elems: List[Tree], elemtpt: Tree): SeqLiteral = new SeqLiteral(elems, elemtpt)
+ def JavaSeqLiteral(elems: List[Tree], elemtpt: Tree): JavaSeqLiteral = new JavaSeqLiteral(elems, elemtpt)
def TypeTree(original: Tree): TypeTree = new TypeTree(original)
def TypeTree() = new TypeTree(EmptyTree)
def SingletonTypeTree(ref: Tree): SingletonTypeTree = new SingletonTypeTree(ref)
diff --git a/src/dotty/tools/dotc/core/classfile/ClassfileParser.scala b/src/dotty/tools/dotc/core/classfile/ClassfileParser.scala
index 9ea24324b..25558a79a 100644
--- a/src/dotty/tools/dotc/core/classfile/ClassfileParser.scala
+++ b/src/dotty/tools/dotc/core/classfile/ClassfileParser.scala
@@ -438,7 +438,14 @@ class ClassfileParser(
case None => hasError = true
}
if (hasError) None
- else if (skip) None else Some(JavaSeqLiteral(arr.toList))
+ else if (skip) None
+ else {
+ val elems = arr.toList
+ val elemType =
+ if (elems.isEmpty) defn.ObjectType
+ else ctx.typeComparer.lub(elems.tpes).widen
+ Some(JavaSeqLiteral(elems, TypeTree(elemType)))
+ }
case ANNOTATION_TAG =>
parseAnnotation(index, skip) map (_.tree)
}
diff --git a/src/dotty/tools/dotc/core/tasty/TreePickler.scala b/src/dotty/tools/dotc/core/tasty/TreePickler.scala
index bb6c3cd2e..d7fc62a16 100644
--- a/src/dotty/tools/dotc/core/tasty/TreePickler.scala
+++ b/src/dotty/tools/dotc/core/tasty/TreePickler.scala
@@ -407,9 +407,9 @@ class TreePickler(pickler: TastyPickler) {
case Try(block, cases, finalizer) =>
writeByte(TRY)
withLength { pickleTree(block); cases.foreach(pickleTree); pickleTreeUnlessEmpty(finalizer) }
- case SeqLiteral(elems) =>
+ case SeqLiteral(elems, elemtpt) =>
writeByte(REPEATED)
- withLength { elems.foreach(pickleTree) }
+ withLength { pickleTree(elemtpt); elems.foreach(pickleTree) }
case TypeTree(original) =>
pickleTpt(tree)
case Bind(name, body) =>
diff --git a/src/dotty/tools/dotc/core/tasty/TreeUnpickler.scala b/src/dotty/tools/dotc/core/tasty/TreeUnpickler.scala
index 16caac02e..9d692cc93 100644
--- a/src/dotty/tools/dotc/core/tasty/TreeUnpickler.scala
+++ b/src/dotty/tools/dotc/core/tasty/TreeUnpickler.scala
@@ -801,7 +801,7 @@ class TreeUnpickler(reader: TastyReader, tastyName: TastyName.Table) {
val fn = readTerm()
val isJava = fn.tpe.isInstanceOf[JavaMethodType]
def readArg() = readTerm() match {
- case SeqLiteral(elems) if isJava => JavaSeqLiteral(elems)
+ case SeqLiteral(elems, elemtpt) if isJava => JavaSeqLiteral(elems, elemtpt)
case arg => arg
}
tpd.Apply(fn, until(end)(readArg()))
@@ -837,7 +837,8 @@ class TreeUnpickler(reader: TastyReader, tastyName: TastyName.Table) {
case TRY =>
Try(readTerm(), readCases(end), ifBefore(end)(readTerm(), EmptyTree))
case REPEATED =>
- SeqLiteral(until(end)(readTerm()))
+ val elemtpt = readTpt()
+ SeqLiteral(until(end)(readTerm()), elemtpt)
case BIND =>
val name = readName()
val info = readType()
diff --git a/src/dotty/tools/dotc/core/unpickleScala2/Scala2Unpickler.scala b/src/dotty/tools/dotc/core/unpickleScala2/Scala2Unpickler.scala
index 7a13388ae..2831de3e0 100644
--- a/src/dotty/tools/dotc/core/unpickleScala2/Scala2Unpickler.scala
+++ b/src/dotty/tools/dotc/core/unpickleScala2/Scala2Unpickler.scala
@@ -850,8 +850,8 @@ class Scala2Unpickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClas
val end = readNat() + readIndex
// array elements are trees representing instances of scala.annotation.Annotation
SeqLiteral(
- defn.SeqType.appliedTo(defn.AnnotationType :: Nil),
- until(end, () => readClassfileAnnotArg(readNat())))
+ until(end, () => readClassfileAnnotArg(readNat())),
+ TypeTree(defn.AnnotationType))
}
private def readAnnotInfoArg()(implicit ctx: Context): Tree = {
@@ -1063,7 +1063,7 @@ class Scala2Unpickler(bytes: Array[Byte], classRoot: ClassDenotation, moduleClas
case ARRAYVALUEtree =>
val elemtpt = readTreeRef()
val trees = until(end, readTreeRef)
- SeqLiteral(defn.SeqType.appliedTo(elemtpt.tpe :: Nil), trees)
+ SeqLiteral(trees, elemtpt)
// note can't deal with trees passed to Java methods as arrays here
case FUNCTIONtree =>
diff --git a/src/dotty/tools/dotc/printing/RefinedPrinter.scala b/src/dotty/tools/dotc/printing/RefinedPrinter.scala
index a03a01e8d..e21f12410 100644
--- a/src/dotty/tools/dotc/printing/RefinedPrinter.scala
+++ b/src/dotty/tools/dotc/printing/RefinedPrinter.scala
@@ -380,8 +380,8 @@ class RefinedPrinter(_ctx: Context) extends PlainPrinter(_ctx) {
changePrec(GlobalPrec) {
"throw " ~ toText(expr)
}
- case SeqLiteral(elems) =>
- "[" ~ toTextGlobal(elems, ",") ~ "]"
+ case SeqLiteral(elems, elemtpt) =>
+ "[" ~ toTextGlobal(elems, ",") ~ " : " ~ toText(elemtpt) ~ "]"
case tpt: untpd.DerivedTypeTree =>
"<derived typetree watching " ~ summarized(toText(tpt.watched)) ~ ">"
case TypeTree(orig) =>
diff --git a/src/dotty/tools/dotc/transform/ElimRepeated.scala b/src/dotty/tools/dotc/transform/ElimRepeated.scala
index 98abbb26d..30778267d 100644
--- a/src/dotty/tools/dotc/transform/ElimRepeated.scala
+++ b/src/dotty/tools/dotc/transform/ElimRepeated.scala
@@ -71,8 +71,8 @@ class ElimRepeated extends MiniPhaseTransform with InfoTransformer with Annotati
/** Convert sequence argument to Java array */
private def seqToArray(tree: Tree)(implicit ctx: Context): Tree = tree match {
- case SeqLiteral(elems) =>
- JavaSeqLiteral(elems)
+ case SeqLiteral(elems, elemtpt) =>
+ JavaSeqLiteral(elems, elemtpt)
case _ =>
val elemType = tree.tpe.firstBaseArgInfo(defn.SeqClass)
var elemClass = elemType.classSymbol
diff --git a/src/dotty/tools/dotc/transform/SeqLiterals.scala b/src/dotty/tools/dotc/transform/SeqLiterals.scala
index 6e29d7e09..49ea69530 100644
--- a/src/dotty/tools/dotc/transform/SeqLiterals.scala
+++ b/src/dotty/tools/dotc/transform/SeqLiterals.scala
@@ -32,9 +32,9 @@ class SeqLiterals extends MiniPhaseTransform {
override def transformSeqLiteral(tree: SeqLiteral)(implicit ctx: Context, info: TransformerInfo): Tree = tree match {
case tree: JavaSeqLiteral => tree
case _ =>
- val arr = JavaSeqLiteral(tree.elems)
+ val arr = JavaSeqLiteral(tree.elems, tree.elemtpt)
//println(i"trans seq $tree, arr = $arr: ${arr.tpe} ${arr.tpe.elemType}")
- val elemtp = arr.tpe.elemType.bounds.hi
+ val elemtp = tree.elemtpt.tpe
val elemCls = elemtp.classSymbol
val (wrapMethStr, targs) =
if (elemCls.isPrimitiveValueClass) (s"wrap${elemCls.name}Array", Nil)
diff --git a/src/dotty/tools/dotc/transform/TreeTransform.scala b/src/dotty/tools/dotc/transform/TreeTransform.scala
index 7a2280baa..7fe003388 100644
--- a/src/dotty/tools/dotc/transform/TreeTransform.scala
+++ b/src/dotty/tools/dotc/transform/TreeTransform.scala
@@ -1148,7 +1148,8 @@ object TreeTransforms {
if (mutatedInfo eq null) tree
else {
val elems = transformTrees(tree.elems, mutatedInfo, cur)
- goSeqLiteral(cpy.SeqLiteral(tree)(elems), mutatedInfo.nx.nxTransSeqLiteral(cur))
+ val elemtpt = transform(tree.elemtpt, mutatedInfo, cur)
+ goSeqLiteral(cpy.SeqLiteral(tree)(elems, elemtpt), mutatedInfo.nx.nxTransSeqLiteral(cur))
}
case tree: TypeTree =>
implicit val mutatedInfo: TransformerInfo = mutateTransformers(info, prepForTypeTree, info.nx.nxPrepTypeTree, tree, cur)
diff --git a/src/dotty/tools/dotc/typer/Applications.scala b/src/dotty/tools/dotc/typer/Applications.scala
index 3b8c56ea6..3ad9902a4 100644
--- a/src/dotty/tools/dotc/typer/Applications.scala
+++ b/src/dotty/tools/dotc/typer/Applications.scala
@@ -442,7 +442,10 @@ trait Applications extends Compatibility { self: Typer =>
def makeVarArg(n: Int, elemFormal: Type): Unit = {
val args = typedArgBuf.takeRight(n).toList
typedArgBuf.trimEnd(n)
- val seqLit = if (methodType.isJava) JavaSeqLiteral(args) else SeqLiteral(args)
+ val elemtpt = TypeTree(elemFormal)
+ val seqLit =
+ if (methodType.isJava) JavaSeqLiteral(args, elemtpt)
+ else SeqLiteral(args, elemtpt)
typedArgBuf += seqToRepeated(seqLit)
}
@@ -771,7 +774,7 @@ trait Applications extends Compatibility { self: Typer =>
for (argType <- argTypes) assert(!argType.isInstanceOf[TypeBounds], unapplyApp.tpe.show)
val bunchedArgs = argTypes match {
case argType :: Nil =>
- if (argType.isRepeatedParam) untpd.SeqLiteral(args) :: Nil
+ if (argType.isRepeatedParam) untpd.SeqLiteral(args, untpd.TypeTree()) :: Nil
else if (args.lengthCompare(1) > 0 && ctx.canAutoTuple) untpd.Tuple(args) :: Nil
else args
case _ => args
diff --git a/src/dotty/tools/dotc/typer/ReTyper.scala b/src/dotty/tools/dotc/typer/ReTyper.scala
index 49718fd00..225451886 100644
--- a/src/dotty/tools/dotc/typer/ReTyper.scala
+++ b/src/dotty/tools/dotc/typer/ReTyper.scala
@@ -92,7 +92,7 @@ class ReTyper extends Typer {
try super.typedUnadapted(tree, pt)
catch {
case NonFatal(ex) =>
- Printers.transforms.println(i"exception while typing $tree of class ${tree.getClass} # ${tree.uniqueId}")
+ println(i"exception while typing $tree of class ${tree.getClass} # ${tree.uniqueId}")
throw ex
}
diff --git a/src/dotty/tools/dotc/typer/TypeAssigner.scala b/src/dotty/tools/dotc/typer/TypeAssigner.scala
index 476839ab3..84951fd2b 100644
--- a/src/dotty/tools/dotc/typer/TypeAssigner.scala
+++ b/src/dotty/tools/dotc/typer/TypeAssigner.scala
@@ -392,14 +392,12 @@ trait TypeAssigner {
if (cases.isEmpty) tree.withType(expr.tpe)
else tree.withType(ctx.typeComparer.lub(expr.tpe :: cases.tpes))
- def assignType(tree: untpd.SeqLiteral, elems: List[Tree])(implicit ctx: Context) = tree match {
- case tree: JavaSeqLiteral =>
- tree.withType(defn.ArrayOf(ctx.typeComparer.lub(elems.tpes).widen))
- case _ =>
- val ownType =
- if (ctx.erasedTypes) defn.SeqType
- else defn.SeqType.appliedTo(ctx.typeComparer.lub(elems.tpes).widen)
- tree.withType(ownType)
+ def assignType(tree: untpd.SeqLiteral, elems: List[Tree], elemtpt: Tree)(implicit ctx: Context) = {
+ val ownType = tree match {
+ case tree: JavaSeqLiteral => defn.ArrayOf(elemtpt.tpe)
+ case _ => if (ctx.erasedTypes) defn.SeqType else defn.SeqType.appliedTo(elemtpt.tpe)
+ }
+ tree.withType(ownType)
}
def assignType(tree: untpd.SingletonTypeTree, ref: Tree)(implicit ctx: Context) =
diff --git a/src/dotty/tools/dotc/typer/Typer.scala b/src/dotty/tools/dotc/typer/Typer.scala
index fdb92a40b..2683b2364 100644
--- a/src/dotty/tools/dotc/typer/Typer.scala
+++ b/src/dotty/tools/dotc/typer/Typer.scala
@@ -836,7 +836,14 @@ class Typer extends Namer with TypeAssigner with Applications with Implicits wit
def typedSeqLiteral(tree: untpd.SeqLiteral, pt: Type)(implicit ctx: Context): SeqLiteral = track("typedSeqLiteral") {
val proto1 = pt.elemType orElse WildcardType
val elems1 = tree.elems mapconserve (typed(_, proto1))
- assignType(cpy.SeqLiteral(tree)(elems1), elems1)
+ 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 typedTypeTree(tree: untpd.TypeTree, pt: Type)(implicit ctx: Context): TypeTree = track("typedTypeTree") {