WIP on Java8. Looking at lambda reloading first (required invokedynamic handling)
This commit is contained in:
6
j8code/.classpath
Normal file
6
j8code/.classpath
Normal file
@@ -0,0 +1,6 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<classpath>
|
||||
<classpathentry kind="src" path="src"/>
|
||||
<classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/J180_b128"/>
|
||||
<classpathentry kind="output" path="bin"/>
|
||||
</classpath>
|
||||
17
j8code/.project
Normal file
17
j8code/.project
Normal file
@@ -0,0 +1,17 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<projectDescription>
|
||||
<name>j8code</name>
|
||||
<comment></comment>
|
||||
<projects>
|
||||
</projects>
|
||||
<buildSpec>
|
||||
<buildCommand>
|
||||
<name>org.eclipse.jdt.core.javabuilder</name>
|
||||
<arguments>
|
||||
</arguments>
|
||||
</buildCommand>
|
||||
</buildSpec>
|
||||
<natures>
|
||||
<nature>org.eclipse.jdt.core.javanature</nature>
|
||||
</natures>
|
||||
</projectDescription>
|
||||
11
j8code/.settings/org.eclipse.jdt.core.prefs
Normal file
11
j8code/.settings/org.eclipse.jdt.core.prefs
Normal file
@@ -0,0 +1,11 @@
|
||||
eclipse.preferences.version=1
|
||||
org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=disabled
|
||||
org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.2
|
||||
org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve
|
||||
org.eclipse.jdt.core.compiler.compliance=1.4
|
||||
org.eclipse.jdt.core.compiler.debug.lineNumber=generate
|
||||
org.eclipse.jdt.core.compiler.debug.localVariable=generate
|
||||
org.eclipse.jdt.core.compiler.debug.sourceFile=generate
|
||||
org.eclipse.jdt.core.compiler.problem.assertIdentifier=warning
|
||||
org.eclipse.jdt.core.compiler.problem.enumIdentifier=warning
|
||||
org.eclipse.jdt.core.compiler.source=1.3
|
||||
69
j8code/src/j8code/J8Helper.java
Normal file
69
j8code/src/j8code/J8Helper.java
Normal file
@@ -0,0 +1,69 @@
|
||||
package j8code;
|
||||
|
||||
import java.lang.invoke.CallSite;
|
||||
import java.lang.invoke.LambdaMetafactory;
|
||||
import java.lang.invoke.MethodHandle;
|
||||
import java.lang.invoke.MethodHandles;
|
||||
import java.lang.invoke.MethodType;
|
||||
|
||||
public class J8Helper {
|
||||
|
||||
public static Object simulateInvokeDynamic(Object lookup) {
|
||||
try {
|
||||
CallSite callsite = callLambdaMetaFactory(lookup);
|
||||
// java.lang.invoke.ConstantCallSite@1e965684
|
||||
// nameAndDescriptor at invokedynamic: m()Lbasic/LambdaA$Foo;
|
||||
MethodHandles.Lookup caller = (MethodHandles.Lookup)lookup;
|
||||
return callsite.dynamicInvoker().invokeWithArguments((Object[])null);//asType(MethodType.methodType())invoke(new Object[]{"m", MethodType.methodType(Class.forName("basic.LambdaA$Foo",false,caller.lookupClass().getClassLoader()))});
|
||||
} catch (Throwable t) {
|
||||
throw new RuntimeException(t);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static CallSite callLambdaMetaFactory(Object lookup) throws Exception {
|
||||
// At invokedynamic:
|
||||
// bsmId = 0
|
||||
// nameAndDescriptor = m()Lbasic/LambdaA$Foo;
|
||||
|
||||
// 0: #31 invokestatic java/lang/invoke/LambdaMetafactory.metafactory:
|
||||
// (Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/invoke/MethodType;Ljava/lang/invoke/MethodType;
|
||||
// Ljava/lang/invoke/MethodHandle;Ljava/lang/invoke/MethodType;)Ljava/lang/invoke/CallSite;
|
||||
// Method arguments:
|
||||
// #32 ()I
|
||||
// #33 invokestatic basic/LambdaA.lambda$run$0:()I
|
||||
// #32 ()I
|
||||
|
||||
// First two stacked by VM when used with invokedynamic
|
||||
|
||||
// 0: #31 invokestatic java/lang/invoke/LambdaMetafactory.metafactory:
|
||||
// (Ljava/lang/invoke/MethodHandles$Lookup;Ljava/lang/String;Ljava/lang/invoke/MethodType;Ljava/lang/invoke/MethodType;
|
||||
// Ljava/lang/invoke/MethodHandle;Ljava/lang/invoke/MethodType;)Ljava/lang/invoke/CallSite;
|
||||
// Method arguments:
|
||||
// #32 ()I
|
||||
// #33 invokestatic basic/LambdaA.lambda$run$0:()I
|
||||
// #32 ()I
|
||||
|
||||
// caller = basic.LambdaA (MethodHandles$Lookup)
|
||||
|
||||
// invokedName = m (String)
|
||||
// invokedType = ()Foo (MethodType)
|
||||
|
||||
// samMethodType=()int (MethodType)
|
||||
// implMethod=MethodHandle()int (DirectMethodHandle - membername in this object is "basic.LambdaA.lambda$run$0()int/invokeStatic")
|
||||
// form members is:
|
||||
//
|
||||
// DMH.invokeStatic__I=Lambda(a0:L)=>{
|
||||
// t1:L=DirectMethodHandle.internalMemberName(a0:L);
|
||||
// t2:I=MethodHandle.linkToStatic(t1:L);t2:I}
|
||||
// instantiatedMethodType=()int (MethodType)
|
||||
MethodHandles.Lookup caller = (MethodHandles.Lookup)lookup;
|
||||
MethodType invokedType = MethodType.methodType(Class.forName("basic.LambdaA$Foo",false,caller.lookupClass().getClassLoader()));
|
||||
|
||||
MethodType samMethodType = MethodType.methodType(Integer.TYPE);
|
||||
// Cheating here by changing first param to pretend the original type is looking for it rather than the executor
|
||||
MethodHandle implMethod = caller.findStatic(caller.lookupClass(), "lambda$run$0",MethodType.methodType(Integer.TYPE));
|
||||
MethodType instantiatedMethodType = MethodType.methodType(Integer.TYPE);
|
||||
return LambdaMetafactory.metafactory(caller, "m", invokedType, samMethodType, implMethod, instantiatedMethodType);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user