diff options
author | Adriaan Moors <adriaan.moors@typesafe.com> | 2016-03-29 00:21:07 -0700 |
---|---|---|
committer | Adriaan Moors <adriaan.moors@typesafe.com> | 2016-03-29 12:34:19 -0700 |
commit | 0a3362b3ea5cd7355cd9ccc529783549a4cb5c5f (patch) | |
tree | cd1c7a3892bfbd657870c619440c047334a1373f /src/compiler/scala/tools/nsc/transform/UnCurry.scala | |
parent | 3ae39036771acb107cbb4a37fe6113c243d89acc (diff) | |
download | scala-0a3362b3ea5cd7355cd9ccc529783549a4cb5c5f.tar.gz scala-0a3362b3ea5cd7355cd9ccc529783549a4cb5c5f.tar.bz2 scala-0a3362b3ea5cd7355cd9ccc529783549a4cb5c5f.zip |
Specialization precludes use of LambdaMetaFactory for SAM
When a SAM type is specialized (i.e., a specialized type
parameter receives a specialized type argument), do not use
LambdaMetaFactory (expand during Uncurry instead).
This is an implementation restriction -- the current
specialization scheme is not amenable to using
LambdaMetaFactory to spin up subclasses. Since the generic
method is abstract, and the specialized ones are concrete,
specialization is rendered moot because we cannot implement
the specialized method with the lambda using LMF.
Diffstat (limited to 'src/compiler/scala/tools/nsc/transform/UnCurry.scala')
-rw-r--r-- | src/compiler/scala/tools/nsc/transform/UnCurry.scala | 8 |
1 files changed, 5 insertions, 3 deletions
diff --git a/src/compiler/scala/tools/nsc/transform/UnCurry.scala b/src/compiler/scala/tools/nsc/transform/UnCurry.scala index afa0fc92ff..9c4b125fc1 100644 --- a/src/compiler/scala/tools/nsc/transform/UnCurry.scala +++ b/src/compiler/scala/tools/nsc/transform/UnCurry.scala @@ -77,8 +77,8 @@ abstract class UnCurry extends InfoTransform // We use Java's LambdaMetaFactory (LMF), which requires an interface for the sam's owner private def mustExpandFunction(fun: Function) = forceExpandFunction || { // (TODO: Can't use isInterface, yet, as it hasn't been updated for the new trait encoding) - val canUseLambdaMetaFactory = inConstructorFlag == 0 && (fun.attachments.get[SAMFunction].map(_.samTp) match { - case Some(userDefinedSamTp) => + val canUseLambdaMetaFactory = inConstructorFlag == 0 && (fun.attachments.get[SAMFunction] match { + case Some(SAMFunction(userDefinedSamTp, sam)) => val tpSym = erasure.javaErasure(userDefinedSamTp).typeSymbol // we only care about what ends up in the bytecode ( // LMF only supports interfaces @@ -90,7 +90,9 @@ abstract class UnCurry extends InfoTransform // to expand sam at compile time or use LMF, and this implementation restriction could be lifted. && tpSym.isStatic // impl restriction -- we currently use the boxed apply, so not really useful to allow specialized sam types (https://github.com/scala/scala/pull/4971#issuecomment-198119167) - && !tpSym.isSpecialized + // specialization and LMF are at odds, since LMF implements the single abstract method, + // but that's the one that specialization leaves generic, whereas we need to implement the specialized one to avoid boxing + && !specializeTypes.isSpecializedIn(sam, userDefinedSamTp) ) case _ => true // our built-in FunctionN's are suitable for LambdaMetaFactory by construction |