aboutsummaryrefslogtreecommitdiff
path: root/src/dotty/tools/dotc/TypeErasure.scala
diff options
context:
space:
mode:
authorMartin Odersky <odersky@gmail.com>2014-11-28 22:10:37 +0100
committerMartin Odersky <odersky@gmail.com>2014-11-28 22:12:51 +0100
commit91c61e4694097971b9a0c139048b7239d0f05588 (patch)
tree6836b169dce43f32e588f60bb16d14dba850b254 /src/dotty/tools/dotc/TypeErasure.scala
parentb18ce863f5f2444a5a00ccc9d55c4ee12115c467 (diff)
downloaddotty-91c61e4694097971b9a0c139048b7239d0f05588.tar.gz
dotty-91c61e4694097971b9a0c139048b7239d0f05588.tar.bz2
dotty-91c61e4694097971b9a0c139048b7239d0f05588.zip
Previous scheme was buggy; leaked Array types to backend.
Now: All new Array[T] methods are translated to calls of the form dotty.Arrays.newXYZArray ...
Diffstat (limited to 'src/dotty/tools/dotc/TypeErasure.scala')
-rw-r--r--src/dotty/tools/dotc/TypeErasure.scala24
1 files changed, 19 insertions, 5 deletions
diff --git a/src/dotty/tools/dotc/TypeErasure.scala b/src/dotty/tools/dotc/TypeErasure.scala
index 1786e2e29..7920667e7 100644
--- a/src/dotty/tools/dotc/TypeErasure.scala
+++ b/src/dotty/tools/dotc/TypeErasure.scala
@@ -142,7 +142,7 @@ object TypeErasure {
tp.derivedPolyType(
tp.paramNames, tp.paramNames map (Function.const(TypeBounds.upper(defn.ObjectType))), tp.resultType)
- if ((sym eq defn.Any_asInstanceOf) || (sym eq defn.Any_isInstanceOf)) eraseParamBounds(sym.info.asInstanceOf[PolyType])
+ if (defn.isPolymorphicAfterErasure(sym)) eraseParamBounds(sym.info.asInstanceOf[PolyType])
else if (sym.isAbstractType) TypeAlias(WildcardType)
else if (sym.isConstructor) outer.addParam(sym.owner.asClass, erase(tp)(erasureCtx))
else eraseInfo(tp)(erasureCtx) match {
@@ -153,10 +153,24 @@ object TypeErasure {
}
}
- def isUnboundedGeneric(tp: Type)(implicit ctx: Context) = !(
- (tp derivesFrom defn.ObjectClass) ||
- tp.classSymbol.isPrimitiveValueClass ||
- (tp.typeSymbol is JavaDefined))
+ /** Is `tp` an abstract type or polymorphic type parameter that has `Any`
+ * as upper bound and that is not Java defined? Arrays of such types are
+ * erased to `Object` instead of `ObjectArray`.
+ */
+ def isUnboundedGeneric(tp: Type)(implicit ctx: Context): Boolean = tp match {
+ case tp: TypeRef =>
+ tp.symbol.isAbstractType &&
+ !tp.derivesFrom(defn.ObjectClass) &&
+ !tp.typeSymbol.is(JavaDefined)
+ case tp: PolyParam =>
+ !tp.derivesFrom(defn.ObjectClass) &&
+ !tp.binder.resultType.isInstanceOf[JavaMethodType]
+ case tp: TypeProxy => isUnboundedGeneric(tp.underlying)
+ case tp: AndType => isUnboundedGeneric(tp.tp1) || isUnboundedGeneric(tp.tp2)
+ case tp: OrType => isUnboundedGeneric(tp.tp1) && isUnboundedGeneric(tp.tp2)
+ case _ => false
+ }
+
/** The erased least upper bound is computed as follows
* - if both argument are arrays, an array of the lub of the element types