< prev index next >

src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotMethodHandleAccessProvider.java

Print this page

        

*** 22,41 **** */ package jdk.vm.ci.hotspot; import static jdk.vm.ci.hotspot.CompilerToVM.compilerToVM; import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime; ! import static jdk.vm.ci.hotspot.HotSpotResolvedObjectTypeImpl.fromObjectClass; import jdk.vm.ci.common.JVMCIError; import jdk.vm.ci.meta.ConstantReflectionProvider; import jdk.vm.ci.meta.JavaConstant; - import jdk.vm.ci.meta.JavaKind; import jdk.vm.ci.meta.MethodHandleAccessProvider; import jdk.vm.ci.meta.ResolvedJavaField; import jdk.vm.ci.meta.ResolvedJavaMethod; import jdk.vm.ci.meta.ResolvedJavaType; - import jdk.vm.ci.meta.Signature; public class HotSpotMethodHandleAccessProvider implements MethodHandleAccessProvider { private final ConstantReflectionProvider constantReflection; --- 22,42 ---- */ package jdk.vm.ci.hotspot; import static jdk.vm.ci.hotspot.CompilerToVM.compilerToVM; import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime; ! ! import java.lang.invoke.MethodHandle; ! import java.util.Objects; ! import jdk.vm.ci.common.JVMCIError; import jdk.vm.ci.meta.ConstantReflectionProvider; import jdk.vm.ci.meta.JavaConstant; import jdk.vm.ci.meta.MethodHandleAccessProvider; import jdk.vm.ci.meta.ResolvedJavaField; import jdk.vm.ci.meta.ResolvedJavaMethod; import jdk.vm.ci.meta.ResolvedJavaType; public class HotSpotMethodHandleAccessProvider implements MethodHandleAccessProvider { private final ConstantReflectionProvider constantReflection;
*** 46,137 **** /** * Lazy initialization to break class initialization cycle. Field and method lookup is only * possible after the {@link HotSpotJVMCIRuntime} is fully initialized. */ static class LazyInitialization { static final ResolvedJavaField methodHandleFormField; static final ResolvedJavaField lambdaFormVmentryField; - static final ResolvedJavaMethod lambdaFormCompileToBytecodeMethod; static final HotSpotResolvedJavaField memberNameVmtargetField; - static final ResolvedJavaType CLASS = fromObjectClass(LazyInitialization.class); - /** * Search for an instance field with the given name in a class. * ! * @param className name of the class to search in * @param fieldName name of the field to be searched * @param fieldType resolved Java type of the field * @return resolved Java field - * @throws ClassNotFoundException * @throws NoSuchFieldError */ ! private static ResolvedJavaField findFieldInClass(String className, String fieldName, ResolvedJavaType fieldType) ! throws ClassNotFoundException { ! Class<?> clazz = Class.forName(className); ! ResolvedJavaType type = runtime().fromClass(clazz); ! ResolvedJavaField[] fields = type.getInstanceFields(false); for (ResolvedJavaField field : fields) { if (field.getName().equals(fieldName) && field.getType().equals(fieldType)) { return field; } } ! throw new NoSuchFieldError(fieldType.getName() + " " + className + "." + fieldName); } ! private static ResolvedJavaMethod findMethodInClass(String className, String methodName, ! ResolvedJavaType resultType, ResolvedJavaType[] parameterTypes) throws ClassNotFoundException { ! Class<?> clazz = Class.forName(className); ! HotSpotResolvedObjectTypeImpl type = fromObjectClass(clazz); ! ResolvedJavaMethod result = null; ! for (ResolvedJavaMethod method : type.getDeclaredMethods()) { ! if (method.getName().equals(methodName) && signatureMatches(method, resultType, parameterTypes)) { ! result = method; ! } ! } ! if (result == null) { ! StringBuilder sig = new StringBuilder("("); ! for (ResolvedJavaType t : parameterTypes) { ! sig.append(t.getName()).append(","); ! } ! if (sig.length() > 1) { ! sig.replace(sig.length() - 1, sig.length(), ")"); ! } else { ! sig.append(')'); ! } ! throw new NoSuchMethodError(resultType.getName() + " " + className + "." + methodName + sig.toString()); ! } ! return result; } ! private static boolean signatureMatches(ResolvedJavaMethod m, ResolvedJavaType resultType, ! ResolvedJavaType[] parameterTypes) { ! Signature s = m.getSignature(); ! if (!s.getReturnType(CLASS).equals(resultType)) { ! return false; ! } ! if (s.getParameterCount(false) != parameterTypes.length) { ! return false; ! } ! for (int i = 0; i < s.getParameterCount(false); ++i) { ! if (!s.getParameterType(i, CLASS).equals(parameterTypes[i])) { ! return false; ! } ! } ! return true; } static { try { ! methodHandleFormField = findFieldInClass("java.lang.invoke.MethodHandle", "form", ! fromObjectClass(Class.forName("java.lang.invoke.LambdaForm"))); ! lambdaFormVmentryField = findFieldInClass("java.lang.invoke.LambdaForm", "vmentry", ! fromObjectClass(Class.forName("java.lang.invoke.MemberName"))); ! lambdaFormCompileToBytecodeMethod = findMethodInClass("java.lang.invoke.LambdaForm", "compileToBytecode", ! new HotSpotResolvedPrimitiveType(JavaKind.Void), new ResolvedJavaType[]{}); ! memberNameVmtargetField = (HotSpotResolvedJavaField) findFieldInClass("java.lang.invoke.MemberName", "vmtarget", ! new HotSpotResolvedPrimitiveType(JavaKind.Long)); } catch (Throwable ex) { throw new JVMCIError(ex); } } } --- 47,96 ---- /** * Lazy initialization to break class initialization cycle. Field and method lookup is only * possible after the {@link HotSpotJVMCIRuntime} is fully initialized. */ static class LazyInitialization { + static final ResolvedJavaType lambdaFormType; static final ResolvedJavaField methodHandleFormField; static final ResolvedJavaField lambdaFormVmentryField; static final HotSpotResolvedJavaField memberNameVmtargetField; /** * Search for an instance field with the given name in a class. * ! * @param declaringType the type declaring the field * @param fieldName name of the field to be searched * @param fieldType resolved Java type of the field * @return resolved Java field * @throws NoSuchFieldError */ ! private static ResolvedJavaField findFieldInClass(ResolvedJavaType declaringType, String fieldName, ResolvedJavaType fieldType) { ! ResolvedJavaField[] fields = declaringType.getInstanceFields(false); for (ResolvedJavaField field : fields) { if (field.getName().equals(fieldName) && field.getType().equals(fieldType)) { return field; } } ! throw new NoSuchFieldError(fieldType.getName() + " " + declaringType + "." + fieldName); } ! private static ResolvedJavaType resolveType(Class<?> c) { ! return runtime().fromClass(c); } ! private static ResolvedJavaType resolveType(String className) throws ClassNotFoundException { ! return resolveType(Class.forName(className)); } static { try { ! ResolvedJavaType methodHandleType = resolveType(MethodHandle.class); ! ResolvedJavaType memberNameType = resolveType("java.lang.invoke.MemberName"); ! lambdaFormType = resolveType("java.lang.invoke.LambdaForm"); ! methodHandleFormField = findFieldInClass(methodHandleType, "form", lambdaFormType); ! lambdaFormVmentryField = findFieldInClass(lambdaFormType, "vmentry", memberNameType); ! memberNameVmtargetField = (HotSpotResolvedJavaField) findFieldInClass(memberNameType, "vmtarget", resolveType(long.class)); } catch (Throwable ex) { throw new JVMCIError(ex); } } }
*** 171,186 **** JavaConstant lambdaForm = constantReflection.readFieldValue(LazyInitialization.methodHandleFormField, methodHandle); if (lambdaForm == null || lambdaForm.isNull()) { return null; } ! if (forceBytecodeGeneration) { ! /* Invoke non-public method: MemberName LambdaForm.compileToBytecode() */ ! LazyInitialization.lambdaFormCompileToBytecodeMethod.invoke(lambdaForm, new JavaConstant[0]); } /* Load non-public field: MemberName LambdaForm.vmentry */ - JavaConstant memberName = constantReflection.readFieldValue(LazyInitialization.lambdaFormVmentryField, lambdaForm); return getTargetMethod(memberName); } @Override public ResolvedJavaMethod resolveLinkToTarget(JavaConstant memberName) { --- 130,147 ---- JavaConstant lambdaForm = constantReflection.readFieldValue(LazyInitialization.methodHandleFormField, methodHandle); if (lambdaForm == null || lambdaForm.isNull()) { return null; } ! JavaConstant memberName = constantReflection.readFieldValue(LazyInitialization.lambdaFormVmentryField, lambdaForm); ! if (memberName.isNull() && forceBytecodeGeneration) { ! Object lf = ((HotSpotObjectConstant) lambdaForm).asObject(LazyInitialization.lambdaFormType); ! compilerToVM().compileToBytecode(Objects.requireNonNull(lf)); ! memberName = constantReflection.readFieldValue(LazyInitialization.lambdaFormVmentryField, lambdaForm); ! assert memberName.isNonNull(); } /* Load non-public field: MemberName LambdaForm.vmentry */ return getTargetMethod(memberName); } @Override public ResolvedJavaMethod resolveLinkToTarget(JavaConstant memberName) {
*** 198,203 **** Object object = ((HotSpotObjectConstantImpl) memberName).object(); /* Read the ResolvedJavaMethod from the injected field MemberName.vmtarget */ return compilerToVM().getResolvedJavaMethod(object, LazyInitialization.memberNameVmtargetField.offset()); } } - --- 159,163 ----
< prev index next >