-
Notifications
You must be signed in to change notification settings - Fork 3.1k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Port StructuralCallSite, LambdaDeserialize to Scala
- Loading branch information
Showing
5 changed files
with
125 additions
and
165 deletions.
There are no files selected for viewing
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,44 @@ | ||
/* | ||
* Scala (https://www.scala-lang.org) | ||
* | ||
* Copyright EPFL and Lightbend, Inc. | ||
* | ||
* Licensed under Apache License 2.0 | ||
* (http://www.apache.org/licenses/LICENSE-2.0). | ||
* | ||
* See the NOTICE file distributed with this work for | ||
* additional information regarding copyright ownership. | ||
*/ | ||
|
||
package scala.runtime | ||
|
||
import java.lang.invoke._ | ||
import java.util | ||
|
||
import scala.annotation.varargs | ||
import scala.collection.immutable | ||
|
||
final class LambdaDeserialize private (lookup: MethodHandles.Lookup, targetMethods: Array[MethodHandle]) { | ||
private val targetMethodMap: util.HashMap[String, MethodHandle] = new util.HashMap[String, MethodHandle](targetMethods.length) | ||
|
||
for (targetMethod <- targetMethods) { | ||
val info = lookup.revealDirect(targetMethod) | ||
val key = LambdaDeserialize.nameAndDescriptorKey(info.getName, info.getMethodType.toMethodDescriptorString) | ||
targetMethodMap.put(key, targetMethod) | ||
} | ||
|
||
private val cache = new util.HashMap[String, MethodHandle] | ||
|
||
def deserializeLambda(serialized: SerializedLambda): AnyRef = LambdaDeserializer.deserializeLambda(lookup, cache, targetMethodMap, serialized) | ||
} | ||
|
||
object LambdaDeserialize { | ||
@varargs @throws[Throwable] | ||
def bootstrap(lookup: MethodHandles.Lookup, invokedName: String, invokedType: MethodType, targetMethods: MethodHandle*): CallSite = { | ||
val targetMethodsArray = targetMethods.asInstanceOf[immutable.ArraySeq[_]].unsafeArray.asInstanceOf[Array[MethodHandle]] | ||
val exact = MethodHandleConstants.LAMBDA_DESERIALIZE_DESERIALIZE_LAMBDA.bindTo(new LambdaDeserialize(lookup, targetMethodsArray)).asType(invokedType) | ||
new ConstantCallSite(exact) | ||
} | ||
|
||
def nameAndDescriptorKey(name: String, descriptor: String): String = name + descriptor | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,35 @@ | ||
/* | ||
* Scala (https://www.scala-lang.org) | ||
* | ||
* Copyright EPFL and Lightbend, Inc. | ||
* | ||
* Licensed under Apache License 2.0 | ||
* (http://www.apache.org/licenses/LICENSE-2.0). | ||
* | ||
* See the NOTICE file distributed with this work for | ||
* additional information regarding copyright ownership. | ||
*/ | ||
|
||
package scala.runtime; | ||
|
||
import java.lang.invoke.MethodHandle; | ||
import java.lang.invoke.MethodHandles; | ||
import java.lang.invoke.MethodType; | ||
import java.lang.invoke.SerializedLambda; | ||
|
||
class MethodHandleConstants { | ||
// static final MethodHandles are optimized by the JIT (https://stackoverflow.com/a/14146641/248998) | ||
static final MethodHandle LAMBDA_DESERIALIZE_DESERIALIZE_LAMBDA; | ||
|
||
static { | ||
LAMBDA_DESERIALIZE_DESERIALIZE_LAMBDA = lookupDeserialize(); | ||
} | ||
|
||
private static MethodHandle lookupDeserialize() { | ||
try { | ||
return MethodHandles.lookup().findVirtual(Class.forName("scala.runtime.LambdaDeserialize"), "deserializeLambda", MethodType.methodType(Object.class, SerializedLambda.class)); | ||
} catch (NoSuchMethodException | IllegalAccessException | ClassNotFoundException e) { | ||
throw new ExceptionInInitializerError(e); | ||
} | ||
} | ||
} |
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,46 @@ | ||
/* | ||
* Scala (https://www.scala-lang.org) | ||
* | ||
* Copyright EPFL and Lightbend, Inc. | ||
* | ||
* Licensed under Apache License 2.0 | ||
* (http://www.apache.org/licenses/LICENSE-2.0). | ||
* | ||
* See the NOTICE file distributed with this work for | ||
* additional information regarding copyright ownership. | ||
*/ | ||
|
||
package scala.runtime | ||
|
||
import java.lang.invoke._ | ||
import java.lang.ref.SoftReference | ||
import java.lang.reflect.Method | ||
|
||
final class StructuralCallSite private (callType: MethodType) { | ||
private var cache: SoftReference[MethodCache] = new SoftReference(new EmptyMethodCache) | ||
|
||
val parameterTypes: Array[Class[_]] = callType.parameterArray | ||
|
||
def get: MethodCache = { | ||
var cache = this.cache.get | ||
if (cache == null) { | ||
cache = new EmptyMethodCache | ||
this.cache = new SoftReference(cache) | ||
} | ||
cache | ||
} | ||
|
||
def find(receiver: Class[_]): Method = get.find(receiver) | ||
|
||
def add(receiver: Class[_], m: Method): Method = { | ||
cache = new SoftReference(get.add(receiver, m)) | ||
m | ||
} | ||
} | ||
|
||
object StructuralCallSite { | ||
def bootstrap(lookup: MethodHandles.Lookup, invokedName: String, invokedType: MethodType, reflectiveCallType: MethodType): CallSite = { | ||
val structuralCallSite = new StructuralCallSite(reflectiveCallType) | ||
new ConstantCallSite(MethodHandles.constant(classOf[StructuralCallSite], structuralCallSite)) | ||
} | ||
} |