8161550: [JVMCI] Crash: assert(sig_bt[member_arg_pos] == T_OBJECT)
Reviewed-by: zmajo
--- a/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/CompilerToVM.java Mon Aug 29 07:32:37 2016 +0200
+++ b/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/CompilerToVM.java Mon Aug 29 17:15:20 2016 +0000
@@ -366,8 +366,8 @@
* {@code exactReceiver}.
*
* @param caller the caller or context type used to perform access checks
- * @return the link-time resolved method (might be abstract) or {@code 0} if it can not be
- * linked
+ * @return the link-time resolved method (might be abstract) or {@code null} if it is either a
+ * signature polymorphic method or can not be linked.
*/
native HotSpotResolvedJavaMethodImpl resolveMethod(HotSpotResolvedObjectTypeImpl exactReceiver, HotSpotResolvedJavaMethodImpl method, HotSpotResolvedObjectTypeImpl caller);
--- a/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotConstantPool.java Mon Aug 29 07:32:37 2016 +0200
+++ b/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotConstantPool.java Mon Aug 29 17:15:20 2016 +0000
@@ -722,7 +722,7 @@
/**
* Determines if {@code type} contains signature polymorphic methods.
*/
- private static boolean isSignaturePolymorphicHolder(final HotSpotResolvedObjectTypeImpl type) {
+ static boolean isSignaturePolymorphicHolder(final ResolvedJavaType type) {
String name = type.getName();
if (signaturePolymorphicHolders == null) {
signaturePolymorphicHolders = compilerToVM().getSignaturePolymorphicHolders();
--- a/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotResolvedObjectTypeImpl.java Mon Aug 29 07:32:37 2016 +0200
+++ b/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.hotspot/src/jdk/vm/ci/hotspot/HotSpotResolvedObjectTypeImpl.java Mon Aug 29 17:15:20 2016 +0000
@@ -24,6 +24,7 @@
import static java.util.Objects.requireNonNull;
import static jdk.vm.ci.hotspot.CompilerToVM.compilerToVM;
+import static jdk.vm.ci.hotspot.HotSpotConstantPool.isSignaturePolymorphicHolder;
import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime;
import static jdk.vm.ci.hotspot.HotSpotVMConfig.config;
import static jdk.vm.ci.hotspot.UnsafeAccess.UNSAFE;
@@ -426,7 +427,7 @@
// Methods can only be resolved against concrete types
return null;
}
- if (method.isConcrete() && method.getDeclaringClass().equals(this) && method.isPublic()) {
+ if (method.isConcrete() && method.getDeclaringClass().equals(this) && method.isPublic() && !isSignaturePolymorphicHolder(method.getDeclaringClass())) {
return method;
}
if (!method.getDeclaringClass().isAssignableFrom(this)) {
--- a/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.meta/src/jdk/vm/ci/meta/ResolvedJavaType.java Mon Aug 29 07:32:37 2016 +0200
+++ b/hotspot/src/jdk.vm.ci/share/classes/jdk.vm.ci.meta/src/jdk/vm/ci/meta/ResolvedJavaType.java Mon Aug 29 17:15:20 2016 +0000
@@ -209,8 +209,8 @@
*
* @param method the method to select the implementation of
* @param callerType the caller or context type used to perform access checks
- * @return the method that would be selected at runtime (might be abstract) or {@code null} if
- * it can not be resolved
+ * @return the link-time resolved method (might be abstract) or {@code null} if it is either a
+ * signature polymorphic method or can not be linked.
*/
ResolvedJavaMethod resolveMethod(ResolvedJavaMethod method, ResolvedJavaType callerType);
--- a/hotspot/src/share/vm/jvmci/jvmciCompilerToVM.cpp Mon Aug 29 07:32:37 2016 +0200
+++ b/hotspot/src/share/vm/jvmci/jvmciCompilerToVM.cpp Mon Aug 29 17:15:20 2016 +0000
@@ -768,6 +768,11 @@
Symbol* h_name = method->name();
Symbol* h_signature = method->signature();
+ if (MethodHandles::is_signature_polymorphic_method(method())) {
+ // Signature polymorphic methods are already resolved, JVMCI just returns NULL in this case.
+ return NULL;
+ }
+
LinkInfo link_info(h_resolved, h_name, h_signature, caller_klass);
methodHandle m;
// Only do exact lookup if receiver klass has been linked. Otherwise,
@@ -782,7 +787,7 @@
}
if (m.is_null()) {
- // Return NULL only if there was a problem with lookup (uninitialized class, etc.)
+ // Return NULL if there was a problem with lookup (uninitialized class, etc.)
return NULL;
}
--- a/hotspot/test/compiler/jvmci/jdk.vm.ci.runtime.test/src/jdk/vm/ci/runtime/test/TestResolvedJavaType.java Mon Aug 29 07:32:37 2016 +0200
+++ b/hotspot/test/compiler/jvmci/jdk.vm.ci.runtime.test/src/jdk/vm/ci/runtime/test/TestResolvedJavaType.java Mon Aug 29 17:15:20 2016 +0000
@@ -25,7 +25,6 @@
* @test
* @requires (vm.simpleArch == "x64" | vm.simpleArch == "sparcv9" | vm.simpleArch == "aarch64")
* @library ../../../../../
- * @ignore 8161550
* @modules java.base/jdk.internal.reflect
* jdk.vm.ci/jdk.vm.ci.meta
* jdk.vm.ci/jdk.vm.ci.runtime
@@ -74,11 +73,29 @@
/**
* Tests for {@link ResolvedJavaType}.
*/
+@SuppressWarnings("unchecked")
public class TestResolvedJavaType extends TypeUniverse {
+ private static final Class<? extends Annotation> SIGNATURE_POLYMORPHIC_CLASS = findPolymorphicSignatureClass();
public TestResolvedJavaType() {
}
+ private static Class<? extends Annotation> findPolymorphicSignatureClass() {
+ Class<? extends Annotation> signaturePolyAnnotation = null;
+ try {
+ for (Class<?> clazz : TestResolvedJavaType.class.getClassLoader().loadClass("java.lang.invoke.MethodHandle").getDeclaredClasses()) {
+ if (clazz.getName().endsWith("PolymorphicSignature") && Annotation.class.isAssignableFrom(clazz)) {
+ signaturePolyAnnotation = (Class<? extends Annotation>) clazz;
+ break;
+ }
+ }
+ } catch (Throwable e) {
+ throw new AssertionError("Could not find annotation PolymorphicSignature in java.lang.invoke.MethodHandle", e);
+ }
+ assertNotNull(signaturePolyAnnotation);
+ return signaturePolyAnnotation;
+ }
+
@Test
public void findInstanceFieldWithOffsetTest() {
for (Class<?> c : classes) {
@@ -577,8 +594,14 @@
for (Method decl : decls) {
ResolvedJavaMethod m = metaAccess.lookupJavaMethod(decl);
if (m.isPublic()) {
- ResolvedJavaMethod i = metaAccess.lookupJavaMethod(impl);
- assertEquals(m.toString(), i, type.resolveMethod(m, context));
+ ResolvedJavaMethod resolvedmethod = type.resolveMethod(m, context);
+ if (isSignaturePolymorphic(m)) {
+ // Signature polymorphic methods must not be resolved
+ assertNull(resolvedmethod);
+ } else {
+ ResolvedJavaMethod i = metaAccess.lookupJavaMethod(impl);
+ assertEquals(m.toString(), i, resolvedmethod);
+ }
}
}
}
@@ -606,8 +629,14 @@
for (Method decl : decls) {
ResolvedJavaMethod m = metaAccess.lookupJavaMethod(decl);
if (m.isPublic()) {
- ResolvedJavaMethod i = metaAccess.lookupJavaMethod(impl);
- assertEquals(i, type.resolveConcreteMethod(m, context));
+ ResolvedJavaMethod resolvedMethod = type.resolveConcreteMethod(m, context);
+ if (isSignaturePolymorphic(m)) {
+ // Signature polymorphic methods must not be resolved
+ assertNull(String.format("Got: %s", resolvedMethod), resolvedMethod);
+ } else {
+ ResolvedJavaMethod i = metaAccess.lookupJavaMethod(impl);
+ assertEquals(i, resolvedMethod);
+ }
}
}
}
@@ -929,4 +958,8 @@
}
}
}
+
+ private static boolean isSignaturePolymorphic(ResolvedJavaMethod method) {
+ return method.getAnnotation(SIGNATURE_POLYMORPHIC_CLASS) != null;
+ }
}