mirror of
https://github.com/openjdk/jdk.git
synced 2025-08-28 07:14:30 +02:00
8165434: [JVMCI] remove uses of setAccessible
Reviewed-by: twisti, never
This commit is contained in:
parent
a83ab529f9
commit
d5ca7a299c
24 changed files with 269 additions and 392 deletions
|
@ -26,8 +26,7 @@ package jdk.vm.ci.hotspot;
|
||||||
import static jdk.vm.ci.common.InitTimer.timer;
|
import static jdk.vm.ci.common.InitTimer.timer;
|
||||||
import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime;
|
import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime;
|
||||||
|
|
||||||
import java.lang.reflect.Constructor;
|
import java.lang.reflect.Executable;
|
||||||
import java.lang.reflect.Method;
|
|
||||||
|
|
||||||
import jdk.vm.ci.code.BytecodeFrame;
|
import jdk.vm.ci.code.BytecodeFrame;
|
||||||
import jdk.vm.ci.code.InstalledCode;
|
import jdk.vm.ci.code.InstalledCode;
|
||||||
|
@ -385,10 +384,9 @@ final class CompilerToVM {
|
||||||
native boolean hasFinalizableSubclass(HotSpotResolvedObjectTypeImpl type);
|
native boolean hasFinalizableSubclass(HotSpotResolvedObjectTypeImpl type);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the method corresponding to {@code holder} and slot number {@code slot} (i.e.
|
* Gets the method corresponding to {@code executable}.
|
||||||
* {@link Method#slot} or {@link Constructor#slot}).
|
|
||||||
*/
|
*/
|
||||||
native HotSpotResolvedJavaMethodImpl getResolvedJavaMethodAtSlot(Class<?> holder, int slot);
|
native HotSpotResolvedJavaMethodImpl asResolvedJavaMethod(Executable executable);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the maximum absolute offset of a PC relative call to {@code address} from any position
|
* Gets the maximum absolute offset of a PC relative call to {@code address} from any position
|
||||||
|
@ -616,4 +614,9 @@ final class CompilerToVM {
|
||||||
*/
|
*/
|
||||||
native int interpreterFrameSize(BytecodeFrame frame);
|
native int interpreterFrameSize(BytecodeFrame frame);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Invokes non-public method {@code java.lang.invoke.LambdaForm.compileToBytecode()} on
|
||||||
|
* {@code lambdaForm} (which must be a {@code java.lang.invoke.LambdaForm} instance).
|
||||||
|
*/
|
||||||
|
native void compileToBytecode(Object lambdaForm);
|
||||||
}
|
}
|
||||||
|
|
|
@ -22,7 +22,7 @@
|
||||||
*/
|
*/
|
||||||
package jdk.vm.ci.hotspot;
|
package jdk.vm.ci.hotspot;
|
||||||
|
|
||||||
import java.lang.reflect.Field;
|
import java.util.Map;
|
||||||
|
|
||||||
import jdk.vm.ci.code.BailoutException;
|
import jdk.vm.ci.code.BailoutException;
|
||||||
import jdk.vm.ci.code.BytecodeFrame;
|
import jdk.vm.ci.code.BytecodeFrame;
|
||||||
|
@ -56,16 +56,11 @@ public class HotSpotCodeCacheProvider implements CodeCacheProvider {
|
||||||
@Override
|
@Override
|
||||||
public String getMarkName(Mark mark) {
|
public String getMarkName(Mark mark) {
|
||||||
int markId = (int) mark.id;
|
int markId = (int) mark.id;
|
||||||
Field[] fields = runtime.getConfig().getClass().getDeclaredFields();
|
HotSpotVMConfigStore store = runtime.getConfigStore();
|
||||||
for (Field f : fields) {
|
for (Map.Entry<String, Long> e : store.getConstants().entrySet()) {
|
||||||
if (f.getName().startsWith("MARKID_")) {
|
String name = e.getKey();
|
||||||
f.setAccessible(true);
|
if (name.startsWith("MARKID_") && e.getValue() == markId) {
|
||||||
try {
|
return name;
|
||||||
if (f.getInt(runtime.getConfig()) == markId) {
|
|
||||||
return f.getName();
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return CodeCacheProvider.super.getMarkName(mark);
|
return CodeCacheProvider.super.getMarkName(mark);
|
||||||
|
@ -76,17 +71,13 @@ public class HotSpotCodeCacheProvider implements CodeCacheProvider {
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public String getTargetName(Call call) {
|
public String getTargetName(Call call) {
|
||||||
Field[] fields = runtime.getConfig().getClass().getDeclaredFields();
|
if (call.target instanceof HotSpotForeignCallTarget) {
|
||||||
for (Field f : fields) {
|
long address = ((HotSpotForeignCallTarget) call.target).address;
|
||||||
if (f.getName().endsWith("Stub")) {
|
HotSpotVMConfigStore store = runtime.getConfigStore();
|
||||||
f.setAccessible(true);
|
for (Map.Entry<String, VMField> e : store.getFields().entrySet()) {
|
||||||
Object address;
|
VMField field = e.getValue();
|
||||||
try {
|
if (field.isStatic() && field.value != null && field.value == address) {
|
||||||
address = f.get(runtime.getConfig());
|
return e.getValue() + ":0x" + Long.toHexString(address);
|
||||||
if (address.equals(call.target)) {
|
|
||||||
return f.getName() + ":0x" + Long.toHexString((Long) address);
|
|
||||||
}
|
|
||||||
} catch (IllegalArgumentException | IllegalAccessException e) {
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,11 +28,10 @@ import static jdk.vm.ci.hotspot.HotSpotResolvedObjectTypeImpl.fromObjectClass;
|
||||||
import static jdk.vm.ci.hotspot.UnsafeAccess.UNSAFE;
|
import static jdk.vm.ci.hotspot.UnsafeAccess.UNSAFE;
|
||||||
|
|
||||||
import java.lang.reflect.Array;
|
import java.lang.reflect.Array;
|
||||||
import java.lang.reflect.Constructor;
|
|
||||||
import java.lang.reflect.Executable;
|
import java.lang.reflect.Executable;
|
||||||
import java.lang.reflect.Field;
|
import java.lang.reflect.Field;
|
||||||
import java.lang.reflect.Method;
|
|
||||||
import java.lang.reflect.Modifier;
|
import java.lang.reflect.Modifier;
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
import jdk.vm.ci.code.CodeUtil;
|
import jdk.vm.ci.code.CodeUtil;
|
||||||
import jdk.vm.ci.code.TargetDescription;
|
import jdk.vm.ci.code.TargetDescription;
|
||||||
|
@ -78,35 +77,8 @@ public class HotSpotMetaAccessProvider implements MetaAccessProvider {
|
||||||
return new HotSpotSignature(runtime, signature);
|
return new HotSpotSignature(runtime, signature);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* {@link Field} object of {@link Method#slot}.
|
|
||||||
*/
|
|
||||||
private Field reflectionMethodSlot = getReflectionSlotField(Method.class);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* {@link Field} object of {@link Constructor#slot}.
|
|
||||||
*/
|
|
||||||
private Field reflectionConstructorSlot = getReflectionSlotField(Constructor.class);
|
|
||||||
|
|
||||||
private static Field getReflectionSlotField(Class<?> reflectionClass) {
|
|
||||||
try {
|
|
||||||
Field field = reflectionClass.getDeclaredField("slot");
|
|
||||||
field.setAccessible(true);
|
|
||||||
return field;
|
|
||||||
} catch (NoSuchFieldException | SecurityException e) {
|
|
||||||
throw new JVMCIError(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public ResolvedJavaMethod lookupJavaMethod(Executable reflectionMethod) {
|
public ResolvedJavaMethod lookupJavaMethod(Executable reflectionMethod) {
|
||||||
try {
|
return runtime.getCompilerToVM().asResolvedJavaMethod(Objects.requireNonNull(reflectionMethod));
|
||||||
Class<?> holder = reflectionMethod.getDeclaringClass();
|
|
||||||
Field slotField = reflectionMethod instanceof Constructor ? reflectionConstructorSlot : reflectionMethodSlot;
|
|
||||||
final int slot = slotField.getInt(reflectionMethod);
|
|
||||||
return runtime.getCompilerToVM().getResolvedJavaMethodAtSlot(holder, slot);
|
|
||||||
} catch (IllegalArgumentException | IllegalAccessException e) {
|
|
||||||
throw new JVMCIError(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public ResolvedJavaField lookupJavaField(Field reflectionField) {
|
public ResolvedJavaField lookupJavaField(Field reflectionField) {
|
||||||
|
|
|
@ -24,16 +24,17 @@ package jdk.vm.ci.hotspot;
|
||||||
|
|
||||||
import static jdk.vm.ci.hotspot.CompilerToVM.compilerToVM;
|
import static jdk.vm.ci.hotspot.CompilerToVM.compilerToVM;
|
||||||
import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime;
|
import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime;
|
||||||
import static jdk.vm.ci.hotspot.HotSpotResolvedObjectTypeImpl.fromObjectClass;
|
|
||||||
|
import java.lang.invoke.MethodHandle;
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
import jdk.vm.ci.common.JVMCIError;
|
import jdk.vm.ci.common.JVMCIError;
|
||||||
import jdk.vm.ci.meta.ConstantReflectionProvider;
|
import jdk.vm.ci.meta.ConstantReflectionProvider;
|
||||||
import jdk.vm.ci.meta.JavaConstant;
|
import jdk.vm.ci.meta.JavaConstant;
|
||||||
import jdk.vm.ci.meta.JavaKind;
|
|
||||||
import jdk.vm.ci.meta.MethodHandleAccessProvider;
|
import jdk.vm.ci.meta.MethodHandleAccessProvider;
|
||||||
import jdk.vm.ci.meta.ResolvedJavaField;
|
import jdk.vm.ci.meta.ResolvedJavaField;
|
||||||
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
||||||
import jdk.vm.ci.meta.ResolvedJavaType;
|
import jdk.vm.ci.meta.ResolvedJavaType;
|
||||||
import jdk.vm.ci.meta.Signature;
|
|
||||||
|
|
||||||
public class HotSpotMethodHandleAccessProvider implements MethodHandleAccessProvider {
|
public class HotSpotMethodHandleAccessProvider implements MethodHandleAccessProvider {
|
||||||
|
|
||||||
|
@ -48,88 +49,46 @@ public class HotSpotMethodHandleAccessProvider implements MethodHandleAccessProv
|
||||||
* possible after the {@link HotSpotJVMCIRuntime} is fully initialized.
|
* possible after the {@link HotSpotJVMCIRuntime} is fully initialized.
|
||||||
*/
|
*/
|
||||||
static class LazyInitialization {
|
static class LazyInitialization {
|
||||||
|
static final ResolvedJavaType lambdaFormType;
|
||||||
static final ResolvedJavaField methodHandleFormField;
|
static final ResolvedJavaField methodHandleFormField;
|
||||||
static final ResolvedJavaField lambdaFormVmentryField;
|
static final ResolvedJavaField lambdaFormVmentryField;
|
||||||
static final ResolvedJavaMethod lambdaFormCompileToBytecodeMethod;
|
|
||||||
static final HotSpotResolvedJavaField memberNameVmtargetField;
|
static final HotSpotResolvedJavaField memberNameVmtargetField;
|
||||||
|
|
||||||
static final ResolvedJavaType CLASS = fromObjectClass(LazyInitialization.class);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Search for an instance field with the given name in a class.
|
* Search for an instance field with the given name in a class.
|
||||||
*
|
*
|
||||||
* @param className name of the class to search in
|
* @param declaringType the type declaring the field
|
||||||
* @param fieldName name of the field to be searched
|
* @param fieldName name of the field to be searched
|
||||||
* @param fieldType resolved Java type of the field
|
* @param fieldType resolved Java type of the field
|
||||||
* @return resolved Java field
|
* @return resolved Java field
|
||||||
* @throws ClassNotFoundException
|
|
||||||
* @throws NoSuchFieldError
|
* @throws NoSuchFieldError
|
||||||
*/
|
*/
|
||||||
private static ResolvedJavaField findFieldInClass(String className, String fieldName, ResolvedJavaType fieldType)
|
private static ResolvedJavaField findFieldInClass(ResolvedJavaType declaringType, String fieldName, ResolvedJavaType fieldType) {
|
||||||
throws ClassNotFoundException {
|
ResolvedJavaField[] fields = declaringType.getInstanceFields(false);
|
||||||
Class<?> clazz = Class.forName(className);
|
|
||||||
ResolvedJavaType type = runtime().fromClass(clazz);
|
|
||||||
ResolvedJavaField[] fields = type.getInstanceFields(false);
|
|
||||||
for (ResolvedJavaField field : fields) {
|
for (ResolvedJavaField field : fields) {
|
||||||
if (field.getName().equals(fieldName) && field.getType().equals(fieldType)) {
|
if (field.getName().equals(fieldName) && field.getType().equals(fieldType)) {
|
||||||
return field;
|
return field;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
throw new NoSuchFieldError(fieldType.getName() + " " + className + "." + fieldName);
|
throw new NoSuchFieldError(fieldType.getName() + " " + declaringType + "." + fieldName);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static ResolvedJavaMethod findMethodInClass(String className, String methodName,
|
private static ResolvedJavaType resolveType(Class<?> c) {
|
||||||
ResolvedJavaType resultType, ResolvedJavaType[] parameterTypes) throws ClassNotFoundException {
|
return runtime().fromClass(c);
|
||||||
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,
|
private static ResolvedJavaType resolveType(String className) throws ClassNotFoundException {
|
||||||
ResolvedJavaType[] parameterTypes) {
|
return resolveType(Class.forName(className));
|
||||||
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 {
|
static {
|
||||||
try {
|
try {
|
||||||
methodHandleFormField = findFieldInClass("java.lang.invoke.MethodHandle", "form",
|
ResolvedJavaType methodHandleType = resolveType(MethodHandle.class);
|
||||||
fromObjectClass(Class.forName("java.lang.invoke.LambdaForm")));
|
ResolvedJavaType memberNameType = resolveType("java.lang.invoke.MemberName");
|
||||||
lambdaFormVmentryField = findFieldInClass("java.lang.invoke.LambdaForm", "vmentry",
|
lambdaFormType = resolveType("java.lang.invoke.LambdaForm");
|
||||||
fromObjectClass(Class.forName("java.lang.invoke.MemberName")));
|
methodHandleFormField = findFieldInClass(methodHandleType, "form", lambdaFormType);
|
||||||
lambdaFormCompileToBytecodeMethod = findMethodInClass("java.lang.invoke.LambdaForm", "compileToBytecode",
|
lambdaFormVmentryField = findFieldInClass(lambdaFormType, "vmentry", memberNameType);
|
||||||
new HotSpotResolvedPrimitiveType(JavaKind.Void), new ResolvedJavaType[]{});
|
memberNameVmtargetField = (HotSpotResolvedJavaField) findFieldInClass(memberNameType, "vmtarget", resolveType(long.class));
|
||||||
memberNameVmtargetField = (HotSpotResolvedJavaField) findFieldInClass("java.lang.invoke.MemberName", "vmtarget",
|
|
||||||
new HotSpotResolvedPrimitiveType(JavaKind.Long));
|
|
||||||
} catch (Throwable ex) {
|
} catch (Throwable ex) {
|
||||||
throw new JVMCIError(ex);
|
throw new JVMCIError(ex);
|
||||||
}
|
}
|
||||||
|
@ -173,12 +132,13 @@ public class HotSpotMethodHandleAccessProvider implements MethodHandleAccessProv
|
||||||
return null;
|
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);
|
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();
|
||||||
|
}
|
||||||
return getTargetMethod(memberName);
|
return getTargetMethod(memberName);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -200,4 +160,3 @@ public class HotSpotMethodHandleAccessProvider implements MethodHandleAccessProv
|
||||||
return compilerToVM().getResolvedJavaMethod(object, LazyInitialization.memberNameVmtargetField.offset());
|
return compilerToVM().getResolvedJavaMethod(object, LazyInitialization.memberNameVmtargetField.offset());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,66 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2016, Oracle and/or its affiliates. All rights reserved.
|
||||||
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
|
*
|
||||||
|
* This code is free software; you can redistribute it and/or modify it
|
||||||
|
* under the terms of the GNU General Public License version 2 only, as
|
||||||
|
* published by the Free Software Foundation.
|
||||||
|
*
|
||||||
|
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||||
|
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||||
|
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||||
|
* version 2 for more details (a copy is included in the LICENSE file that
|
||||||
|
* accompanied this code).
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License version
|
||||||
|
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||||
|
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||||
|
*
|
||||||
|
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||||
|
* or visit www.oracle.com if you need additional information or have any
|
||||||
|
* questions.
|
||||||
|
*/
|
||||||
|
package jdk.vm.ci.hotspot;
|
||||||
|
|
||||||
|
import static java.lang.reflect.Modifier.ABSTRACT;
|
||||||
|
import static java.lang.reflect.Modifier.FINAL;
|
||||||
|
import static java.lang.reflect.Modifier.INTERFACE;
|
||||||
|
import static java.lang.reflect.Modifier.NATIVE;
|
||||||
|
import static java.lang.reflect.Modifier.PRIVATE;
|
||||||
|
import static java.lang.reflect.Modifier.PROTECTED;
|
||||||
|
import static java.lang.reflect.Modifier.PUBLIC;
|
||||||
|
import static java.lang.reflect.Modifier.STATIC;
|
||||||
|
import static java.lang.reflect.Modifier.STRICT;
|
||||||
|
import static java.lang.reflect.Modifier.SYNCHRONIZED;
|
||||||
|
import static java.lang.reflect.Modifier.TRANSIENT;
|
||||||
|
import static java.lang.reflect.Modifier.VOLATILE;
|
||||||
|
import static jdk.vm.ci.hotspot.HotSpotVMConfig.config;
|
||||||
|
|
||||||
|
import java.lang.reflect.Modifier;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The non-public modifiers in {@link Modifier} that need to be retrieved from
|
||||||
|
* {@link HotSpotVMConfig}.
|
||||||
|
*/
|
||||||
|
public class HotSpotModifiers {
|
||||||
|
|
||||||
|
// @formatter:off
|
||||||
|
public static final int ANNOTATION = config().jvmAccAnnotation;
|
||||||
|
public static final int ENUM = config().jvmAccEnum;
|
||||||
|
public static final int VARARGS = config().jvmAccVarargs;
|
||||||
|
public static final int BRIDGE = config().jvmAccBridge;
|
||||||
|
public static final int SYNTHETIC = config().jvmAccSynthetic;
|
||||||
|
// @formatter:on
|
||||||
|
|
||||||
|
public static int jvmClassModifiers() {
|
||||||
|
return PUBLIC | FINAL | INTERFACE | ABSTRACT | ANNOTATION | ENUM | SYNTHETIC;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int jvmMethodModifiers() {
|
||||||
|
return PUBLIC | PRIVATE | PROTECTED | STATIC | FINAL | SYNCHRONIZED | BRIDGE | VARARGS | NATIVE | ABSTRACT | STRICT | SYNTHETIC;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int jvmFieldModifiers() {
|
||||||
|
return PUBLIC | PRIVATE | PROTECTED | STATIC | FINAL | VOLATILE | TRANSIENT | ENUM | SYNTHETIC;
|
||||||
|
}
|
||||||
|
}
|
|
@ -22,6 +22,7 @@
|
||||||
*/
|
*/
|
||||||
package jdk.vm.ci.hotspot;
|
package jdk.vm.ci.hotspot;
|
||||||
|
|
||||||
|
import static jdk.vm.ci.hotspot.HotSpotModifiers.jvmFieldModifiers;
|
||||||
import static jdk.vm.ci.hotspot.HotSpotVMConfig.config;
|
import static jdk.vm.ci.hotspot.HotSpotVMConfig.config;
|
||||||
|
|
||||||
import java.lang.annotation.Annotation;
|
import java.lang.annotation.Annotation;
|
||||||
|
@ -29,7 +30,6 @@ import java.lang.reflect.Field;
|
||||||
|
|
||||||
import jdk.internal.vm.annotation.Stable;
|
import jdk.internal.vm.annotation.Stable;
|
||||||
import jdk.vm.ci.meta.JavaType;
|
import jdk.vm.ci.meta.JavaType;
|
||||||
import jdk.vm.ci.meta.ModifiersProvider;
|
|
||||||
import jdk.vm.ci.meta.ResolvedJavaType;
|
import jdk.vm.ci.meta.ResolvedJavaType;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -81,7 +81,7 @@ class HotSpotResolvedJavaFieldImpl implements HotSpotResolvedJavaField {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getModifiers() {
|
public int getModifiers() {
|
||||||
return modifiers & ModifiersProvider.jvmFieldModifiers();
|
return modifiers & jvmFieldModifiers();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|
|
@ -24,13 +24,15 @@ package jdk.vm.ci.hotspot;
|
||||||
|
|
||||||
import static jdk.vm.ci.hotspot.CompilerToVM.compilerToVM;
|
import static jdk.vm.ci.hotspot.CompilerToVM.compilerToVM;
|
||||||
import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime;
|
import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime;
|
||||||
|
import static jdk.vm.ci.hotspot.HotSpotModifiers.BRIDGE;
|
||||||
|
import static jdk.vm.ci.hotspot.HotSpotModifiers.SYNTHETIC;
|
||||||
|
import static jdk.vm.ci.hotspot.HotSpotModifiers.VARARGS;
|
||||||
|
import static jdk.vm.ci.hotspot.HotSpotModifiers.jvmMethodModifiers;
|
||||||
import static jdk.vm.ci.hotspot.HotSpotVMConfig.config;
|
import static jdk.vm.ci.hotspot.HotSpotVMConfig.config;
|
||||||
import static jdk.vm.ci.hotspot.UnsafeAccess.UNSAFE;
|
import static jdk.vm.ci.hotspot.UnsafeAccess.UNSAFE;
|
||||||
|
|
||||||
import java.lang.annotation.Annotation;
|
import java.lang.annotation.Annotation;
|
||||||
import java.lang.reflect.Executable;
|
import java.lang.reflect.Executable;
|
||||||
import java.lang.reflect.InvocationTargetException;
|
|
||||||
import java.lang.reflect.Method;
|
|
||||||
import java.lang.reflect.Modifier;
|
import java.lang.reflect.Modifier;
|
||||||
import java.lang.reflect.Type;
|
import java.lang.reflect.Type;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
@ -42,13 +44,11 @@ import jdk.vm.ci.meta.Constant;
|
||||||
import jdk.vm.ci.meta.ConstantPool;
|
import jdk.vm.ci.meta.ConstantPool;
|
||||||
import jdk.vm.ci.meta.DefaultProfilingInfo;
|
import jdk.vm.ci.meta.DefaultProfilingInfo;
|
||||||
import jdk.vm.ci.meta.ExceptionHandler;
|
import jdk.vm.ci.meta.ExceptionHandler;
|
||||||
import jdk.vm.ci.meta.JavaConstant;
|
|
||||||
import jdk.vm.ci.meta.JavaMethod;
|
import jdk.vm.ci.meta.JavaMethod;
|
||||||
import jdk.vm.ci.meta.JavaType;
|
import jdk.vm.ci.meta.JavaType;
|
||||||
import jdk.vm.ci.meta.LineNumberTable;
|
import jdk.vm.ci.meta.LineNumberTable;
|
||||||
import jdk.vm.ci.meta.Local;
|
import jdk.vm.ci.meta.Local;
|
||||||
import jdk.vm.ci.meta.LocalVariableTable;
|
import jdk.vm.ci.meta.LocalVariableTable;
|
||||||
import jdk.vm.ci.meta.ModifiersProvider;
|
|
||||||
import jdk.vm.ci.meta.ProfilingInfo;
|
import jdk.vm.ci.meta.ProfilingInfo;
|
||||||
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
||||||
import jdk.vm.ci.meta.ResolvedJavaType;
|
import jdk.vm.ci.meta.ResolvedJavaType;
|
||||||
|
@ -210,7 +210,7 @@ final class HotSpotResolvedJavaMethodImpl extends HotSpotMethod implements HotSp
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public int getModifiers() {
|
public int getModifiers() {
|
||||||
return getAllModifiers() & ModifiersProvider.jvmMethodModifiers();
|
return getAllModifiers() & jvmMethodModifiers();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -490,6 +490,19 @@ final class HotSpotResolvedJavaMethodImpl extends HotSpotMethod implements HotSp
|
||||||
return javaMethod == null ? null : javaMethod.getAnnotation(annotationClass);
|
return javaMethod == null ? null : javaMethod.getAnnotation(annotationClass);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isBridge() {
|
||||||
|
return (BRIDGE & getModifiers()) != 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isSynthetic() {
|
||||||
|
return (SYNTHETIC & getModifiers()) != 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isVarArgs() {
|
||||||
|
return (VARARGS & getModifiers()) != 0;
|
||||||
|
}
|
||||||
|
|
||||||
public boolean isDefault() {
|
public boolean isDefault() {
|
||||||
if (isConstructor()) {
|
if (isConstructor()) {
|
||||||
return false;
|
return false;
|
||||||
|
@ -697,27 +710,6 @@ final class HotSpotResolvedJavaMethodImpl extends HotSpotMethod implements HotSp
|
||||||
return (getFlags() & config().methodFlagsIntrinsicCandidate) != 0;
|
return (getFlags() & config().methodFlagsIntrinsicCandidate) != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public JavaConstant invoke(JavaConstant receiver, JavaConstant[] arguments) {
|
|
||||||
assert !isConstructor();
|
|
||||||
Method javaMethod = (Method) toJava();
|
|
||||||
javaMethod.setAccessible(true);
|
|
||||||
|
|
||||||
Object[] objArguments = new Object[arguments.length];
|
|
||||||
for (int i = 0; i < arguments.length; i++) {
|
|
||||||
objArguments[i] = HotSpotObjectConstantImpl.asBoxedValue(arguments[i]);
|
|
||||||
}
|
|
||||||
Object objReceiver = receiver != null && !receiver.isNull() ? ((HotSpotObjectConstantImpl) receiver).object() : null;
|
|
||||||
|
|
||||||
try {
|
|
||||||
Object objResult = javaMethod.invoke(objReceiver, objArguments);
|
|
||||||
return javaMethod.getReturnType() == void.class ? null : HotSpotObjectConstantImpl.forBoxedValue(getSignature().getReturnKind(), objResult);
|
|
||||||
|
|
||||||
} catch (IllegalAccessException | InvocationTargetException ex) {
|
|
||||||
throw new IllegalArgumentException(ex);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Allocates a compile id for this method by asking the VM for one.
|
* Allocates a compile id for this method by asking the VM for one.
|
||||||
*
|
*
|
||||||
|
|
|
@ -26,6 +26,7 @@ import static java.util.Objects.requireNonNull;
|
||||||
import static jdk.vm.ci.hotspot.CompilerToVM.compilerToVM;
|
import static jdk.vm.ci.hotspot.CompilerToVM.compilerToVM;
|
||||||
import static jdk.vm.ci.hotspot.HotSpotConstantPool.isSignaturePolymorphicHolder;
|
import static jdk.vm.ci.hotspot.HotSpotConstantPool.isSignaturePolymorphicHolder;
|
||||||
import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime;
|
import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime;
|
||||||
|
import static jdk.vm.ci.hotspot.HotSpotModifiers.jvmClassModifiers;
|
||||||
import static jdk.vm.ci.hotspot.HotSpotVMConfig.config;
|
import static jdk.vm.ci.hotspot.HotSpotVMConfig.config;
|
||||||
import static jdk.vm.ci.hotspot.UnsafeAccess.UNSAFE;
|
import static jdk.vm.ci.hotspot.UnsafeAccess.UNSAFE;
|
||||||
|
|
||||||
|
@ -49,7 +50,6 @@ import jdk.vm.ci.meta.Constant;
|
||||||
import jdk.vm.ci.meta.JavaConstant;
|
import jdk.vm.ci.meta.JavaConstant;
|
||||||
import jdk.vm.ci.meta.JavaKind;
|
import jdk.vm.ci.meta.JavaKind;
|
||||||
import jdk.vm.ci.meta.JavaType;
|
import jdk.vm.ci.meta.JavaType;
|
||||||
import jdk.vm.ci.meta.ModifiersProvider;
|
|
||||||
import jdk.vm.ci.meta.ResolvedJavaField;
|
import jdk.vm.ci.meta.ResolvedJavaField;
|
||||||
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
||||||
import jdk.vm.ci.meta.ResolvedJavaType;
|
import jdk.vm.ci.meta.ResolvedJavaType;
|
||||||
|
@ -152,7 +152,7 @@ final class HotSpotResolvedObjectTypeImpl extends HotSpotResolvedJavaType implem
|
||||||
if (isArray()) {
|
if (isArray()) {
|
||||||
return (getElementalType().getModifiers() & (Modifier.PUBLIC | Modifier.PRIVATE | Modifier.PROTECTED)) | Modifier.FINAL | Modifier.ABSTRACT;
|
return (getElementalType().getModifiers() & (Modifier.PUBLIC | Modifier.PRIVATE | Modifier.PROTECTED)) | Modifier.FINAL | Modifier.ABSTRACT;
|
||||||
} else {
|
} else {
|
||||||
return getAccessFlags() & ModifiersProvider.jvmClassModifiers();
|
return getAccessFlags() & jvmClassModifiers();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -507,7 +507,7 @@ final class HotSpotResolvedObjectTypeImpl extends HotSpotResolvedJavaType implem
|
||||||
synchronized HotSpotResolvedJavaField createField(String fieldName, JavaType type, long offset, int rawFlags) {
|
synchronized HotSpotResolvedJavaField createField(String fieldName, JavaType type, long offset, int rawFlags) {
|
||||||
HotSpotResolvedJavaField result = null;
|
HotSpotResolvedJavaField result = null;
|
||||||
|
|
||||||
final int flags = rawFlags & ModifiersProvider.jvmFieldModifiers();
|
final int flags = rawFlags & HotSpotModifiers.jvmFieldModifiers();
|
||||||
|
|
||||||
final long id = offset + ((long) flags << 32);
|
final long id = offset + ((long) flags << 32);
|
||||||
|
|
||||||
|
|
|
@ -117,8 +117,12 @@ class HotSpotVMConfig extends HotSpotVMConfigAccess {
|
||||||
final int jvmAccFieldHasGenericSignature = getConstant("JVM_ACC_FIELD_HAS_GENERIC_SIGNATURE", Integer.class);
|
final int jvmAccFieldHasGenericSignature = getConstant("JVM_ACC_FIELD_HAS_GENERIC_SIGNATURE", Integer.class);
|
||||||
final int jvmAccIsCloneableFast = getConstant("JVM_ACC_IS_CLONEABLE_FAST", Integer.class);
|
final int jvmAccIsCloneableFast = getConstant("JVM_ACC_IS_CLONEABLE_FAST", Integer.class);
|
||||||
|
|
||||||
// Modifier.SYNTHETIC is not public so we get it via vmStructs.
|
// These modifiers are not public in Modifier so we get them via vmStructs.
|
||||||
final int jvmAccSynthetic = getConstant("JVM_ACC_SYNTHETIC", Integer.class);
|
final int jvmAccSynthetic = getConstant("JVM_ACC_SYNTHETIC", Integer.class);
|
||||||
|
final int jvmAccAnnotation = getConstant("JVM_ACC_ANNOTATION", Integer.class);
|
||||||
|
final int jvmAccBridge = getConstant("JVM_ACC_BRIDGE", Integer.class);
|
||||||
|
final int jvmAccVarargs = getConstant("JVM_ACC_VARARGS", Integer.class);
|
||||||
|
final int jvmAccEnum = getConstant("JVM_ACC_ENUM", Integer.class);
|
||||||
|
|
||||||
// This is only valid on AMD64.
|
// This is only valid on AMD64.
|
||||||
final int runtimeCallStackSize = getConstant("frame::arg_reg_save_area_bytes", Integer.class, osArch.equals("amd64") ? null : 0);
|
final int runtimeCallStackSize = getConstant("frame::arg_reg_save_area_bytes", Integer.class, osArch.equals("amd64") ? null : 0);
|
||||||
|
|
|
@ -22,8 +22,6 @@
|
||||||
*/
|
*/
|
||||||
package jdk.vm.ci.hotspot;
|
package jdk.vm.ci.hotspot;
|
||||||
|
|
||||||
import java.lang.reflect.Field;
|
|
||||||
|
|
||||||
import jdk.internal.misc.Unsafe;
|
import jdk.internal.misc.Unsafe;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -31,21 +29,5 @@ import jdk.internal.misc.Unsafe;
|
||||||
*/
|
*/
|
||||||
class UnsafeAccess {
|
class UnsafeAccess {
|
||||||
|
|
||||||
static final Unsafe UNSAFE = initUnsafe();
|
static final Unsafe UNSAFE = Unsafe.getUnsafe();
|
||||||
|
|
||||||
private static Unsafe initUnsafe() {
|
|
||||||
try {
|
|
||||||
// Fast path when we are trusted.
|
|
||||||
return Unsafe.getUnsafe();
|
|
||||||
} catch (SecurityException se) {
|
|
||||||
// Slow path when we are not trusted.
|
|
||||||
try {
|
|
||||||
Field theUnsafe = Unsafe.class.getDeclaredField("theUnsafe");
|
|
||||||
theUnsafe.setAccessible(true);
|
|
||||||
return (Unsafe) theUnsafe.get(Unsafe.class);
|
|
||||||
} catch (Exception e) {
|
|
||||||
throw new RuntimeException("exception while trying to get Unsafe", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -22,9 +22,6 @@
|
||||||
*/
|
*/
|
||||||
package jdk.vm.ci.meta;
|
package jdk.vm.ci.meta;
|
||||||
|
|
||||||
import java.lang.reflect.Field;
|
|
||||||
import java.lang.reflect.Modifier;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Miscellaneous collection of utility methods used by {@code jdk.vm.ci.meta} and its clients.
|
* Miscellaneous collection of utility methods used by {@code jdk.vm.ci.meta} and its clients.
|
||||||
*/
|
*/
|
||||||
|
@ -226,17 +223,4 @@ public class MetaUtil {
|
||||||
}
|
}
|
||||||
return obj.getClass().getName() + "@" + System.identityHashCode(obj);
|
return obj.getClass().getName() + "@" + System.identityHashCode(obj);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Used to lookup constants from {@link Modifier} that are not public (VARARGS, SYNTHETIC etc.).
|
|
||||||
*/
|
|
||||||
static int getNonPublicModifierStaticField(String name) {
|
|
||||||
try {
|
|
||||||
Field field = Modifier.class.getDeclaredField(name);
|
|
||||||
field.setAccessible(true);
|
|
||||||
return field.getInt(null);
|
|
||||||
} catch (NoSuchFieldException | SecurityException | IllegalArgumentException | IllegalAccessException e) {
|
|
||||||
throw new InternalError(e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -22,18 +22,9 @@
|
||||||
*/
|
*/
|
||||||
package jdk.vm.ci.meta;
|
package jdk.vm.ci.meta;
|
||||||
|
|
||||||
import static java.lang.reflect.Modifier.ABSTRACT;
|
|
||||||
import static java.lang.reflect.Modifier.FINAL;
|
|
||||||
import static java.lang.reflect.Modifier.INTERFACE;
|
|
||||||
import static java.lang.reflect.Modifier.NATIVE;
|
|
||||||
import static java.lang.reflect.Modifier.PRIVATE;
|
import static java.lang.reflect.Modifier.PRIVATE;
|
||||||
import static java.lang.reflect.Modifier.PROTECTED;
|
import static java.lang.reflect.Modifier.PROTECTED;
|
||||||
import static java.lang.reflect.Modifier.PUBLIC;
|
import static java.lang.reflect.Modifier.PUBLIC;
|
||||||
import static java.lang.reflect.Modifier.STATIC;
|
|
||||||
import static java.lang.reflect.Modifier.STRICT;
|
|
||||||
import static java.lang.reflect.Modifier.SYNCHRONIZED;
|
|
||||||
import static java.lang.reflect.Modifier.TRANSIENT;
|
|
||||||
import static java.lang.reflect.Modifier.VOLATILE;
|
|
||||||
|
|
||||||
import java.lang.reflect.Modifier;
|
import java.lang.reflect.Modifier;
|
||||||
|
|
||||||
|
@ -42,17 +33,9 @@ import java.lang.reflect.Modifier;
|
||||||
* language {@linkplain #getModifiers() modifiers}.
|
* language {@linkplain #getModifiers() modifiers}.
|
||||||
*/
|
*/
|
||||||
public interface ModifiersProvider {
|
public interface ModifiersProvider {
|
||||||
int BRIDGE = MetaUtil.getNonPublicModifierStaticField("BRIDGE");
|
|
||||||
int VARARGS = MetaUtil.getNonPublicModifierStaticField("VARARGS");
|
|
||||||
int SYNTHETIC = MetaUtil.getNonPublicModifierStaticField("SYNTHETIC");
|
|
||||||
int ANNOTATION = MetaUtil.getNonPublicModifierStaticField("ANNOTATION");
|
|
||||||
int ENUM = MetaUtil.getNonPublicModifierStaticField("ENUM");
|
|
||||||
int MANDATED = MetaUtil.getNonPublicModifierStaticField("MANDATED");
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns the Java Virtual Machine modifiers for this element. Note that this can differ from
|
* Returns the modifiers for this element.
|
||||||
* standard Java Reflection modifiers. For example at the JVM level, classes (
|
|
||||||
* {@link ResolvedJavaType}) can not be private or protected.
|
|
||||||
*/
|
*/
|
||||||
int getModifiers();
|
int getModifiers();
|
||||||
|
|
||||||
|
@ -161,17 +144,4 @@ public interface ModifiersProvider {
|
||||||
default boolean isConcrete() {
|
default boolean isConcrete() {
|
||||||
return !isAbstract();
|
return !isAbstract();
|
||||||
}
|
}
|
||||||
|
|
||||||
static int jvmClassModifiers() {
|
|
||||||
// no SUPER
|
|
||||||
return PUBLIC | FINAL | INTERFACE | ABSTRACT | ANNOTATION | ENUM | SYNTHETIC;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int jvmMethodModifiers() {
|
|
||||||
return PUBLIC | PRIVATE | PROTECTED | STATIC | FINAL | SYNCHRONIZED | BRIDGE | VARARGS | NATIVE | ABSTRACT | STRICT | SYNTHETIC;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int jvmFieldModifiers() {
|
|
||||||
return PUBLIC | PRIVATE | PROTECTED | STATIC | FINAL | VOLATILE | TRANSIENT | ENUM | SYNTHETIC;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -26,7 +26,6 @@ import java.lang.annotation.Annotation;
|
||||||
import java.lang.reflect.AnnotatedElement;
|
import java.lang.reflect.AnnotatedElement;
|
||||||
import java.lang.reflect.Array;
|
import java.lang.reflect.Array;
|
||||||
import java.lang.reflect.Method;
|
import java.lang.reflect.Method;
|
||||||
import java.lang.reflect.Modifier;
|
|
||||||
import java.lang.reflect.Type;
|
import java.lang.reflect.Type;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -72,14 +71,6 @@ public interface ResolvedJavaMethod extends JavaMethod, InvokeTarget, ModifiersP
|
||||||
*/
|
*/
|
||||||
int getMaxStackSize();
|
int getMaxStackSize();
|
||||||
|
|
||||||
/**
|
|
||||||
* {@inheritDoc}
|
|
||||||
* <p>
|
|
||||||
* Only the {@linkplain Modifier#methodModifiers() method flags} specified in the JVM
|
|
||||||
* specification will be included in the returned mask.
|
|
||||||
*/
|
|
||||||
int getModifiers();
|
|
||||||
|
|
||||||
default boolean isFinal() {
|
default boolean isFinal() {
|
||||||
return ModifiersProvider.super.isFinalFlagSet();
|
return ModifiersProvider.super.isFinalFlagSet();
|
||||||
}
|
}
|
||||||
|
@ -88,9 +79,7 @@ public interface ResolvedJavaMethod extends JavaMethod, InvokeTarget, ModifiersP
|
||||||
* Determines if this method is a synthetic method as defined by the Java Language
|
* Determines if this method is a synthetic method as defined by the Java Language
|
||||||
* Specification.
|
* Specification.
|
||||||
*/
|
*/
|
||||||
default boolean isSynthetic() {
|
boolean isSynthetic();
|
||||||
return (SYNTHETIC & getModifiers()) == SYNTHETIC;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Checks that the method is a
|
* Checks that the method is a
|
||||||
|
@ -99,9 +88,7 @@ public interface ResolvedJavaMethod extends JavaMethod, InvokeTarget, ModifiersP
|
||||||
*
|
*
|
||||||
* @return whether the method is a varargs method
|
* @return whether the method is a varargs method
|
||||||
*/
|
*/
|
||||||
default boolean isVarArgs() {
|
boolean isVarArgs();
|
||||||
return (VARARGS & getModifiers()) == VARARGS;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Checks that the method is a
|
* Checks that the method is a
|
||||||
|
@ -110,9 +97,7 @@ public interface ResolvedJavaMethod extends JavaMethod, InvokeTarget, ModifiersP
|
||||||
*
|
*
|
||||||
* @return whether the method is a bridge method
|
* @return whether the method is a bridge method
|
||||||
*/
|
*/
|
||||||
default boolean isBridge() {
|
boolean isBridge();
|
||||||
return (BRIDGE & getModifiers()) == BRIDGE;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns {@code true} if this method is a default method; returns {@code false} otherwise.
|
* Returns {@code true} if this method is a default method; returns {@code false} otherwise.
|
||||||
|
@ -227,18 +212,6 @@ public interface ResolvedJavaMethod extends JavaMethod, InvokeTarget, ModifiersP
|
||||||
*/
|
*/
|
||||||
LocalVariableTable getLocalVariableTable();
|
LocalVariableTable getLocalVariableTable();
|
||||||
|
|
||||||
/**
|
|
||||||
* Invokes the underlying method represented by this object, on the specified object with the
|
|
||||||
* specified parameters. This method is similar to a reflective method invocation by
|
|
||||||
* {@link Method#invoke}.
|
|
||||||
*
|
|
||||||
* @param receiver The receiver for the invocation, or {@code null} if it is a static method.
|
|
||||||
* @param arguments The arguments for the invocation.
|
|
||||||
* @return The value returned by the method invocation, or {@code null} if the return type is
|
|
||||||
* {@code void}.
|
|
||||||
*/
|
|
||||||
JavaConstant invoke(JavaConstant receiver, JavaConstant[] arguments);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets the encoding of (that is, a constant representing the value of) this method.
|
* Gets the encoding of (that is, a constant representing the value of) this method.
|
||||||
*
|
*
|
||||||
|
|
|
@ -68,15 +68,6 @@ public interface ResolvedJavaType extends JavaType, ModifiersProvider, Annotated
|
||||||
*/
|
*/
|
||||||
boolean isPrimitive();
|
boolean isPrimitive();
|
||||||
|
|
||||||
/**
|
|
||||||
* {@inheritDoc}
|
|
||||||
* <p>
|
|
||||||
* Only the flags specified in the JVM specification will be included in the returned mask. This
|
|
||||||
* method is identical to {@link Class#getModifiers()} in terms of the value return for this
|
|
||||||
* type.
|
|
||||||
*/
|
|
||||||
int getModifiers();
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The setting of the final bit for types is a bit confusing since arrays are marked as final.
|
* The setting of the final bit for types is a bit confusing since arrays are marked as final.
|
||||||
* This method provides a semantically equivalent test that appropriate for types.
|
* This method provides a semantically equivalent test that appropriate for types.
|
||||||
|
|
|
@ -473,9 +473,20 @@ C2V_VMENTRY(jlong, getExceptionTableStart, (JNIEnv *, jobject, jobject jvmci_met
|
||||||
return (jlong) (address) method->exception_table_start();
|
return (jlong) (address) method->exception_table_start();
|
||||||
C2V_END
|
C2V_END
|
||||||
|
|
||||||
C2V_VMENTRY(jobject, getResolvedJavaMethodAtSlot, (JNIEnv *, jobject, jclass holder_handle, jint slot))
|
C2V_VMENTRY(jobject, asResolvedJavaMethod, (JNIEnv *, jobject, jobject executable_handle))
|
||||||
oop java_class = JNIHandles::resolve(holder_handle);
|
oop executable = JNIHandles::resolve(executable_handle);
|
||||||
Klass* holder = java_lang_Class::as_Klass(java_class);
|
oop mirror = NULL;
|
||||||
|
int slot = 0;
|
||||||
|
|
||||||
|
if (executable->klass() == SystemDictionary::reflect_Constructor_klass()) {
|
||||||
|
mirror = java_lang_reflect_Constructor::clazz(executable);
|
||||||
|
slot = java_lang_reflect_Constructor::slot(executable);
|
||||||
|
} else {
|
||||||
|
assert(executable->klass() == SystemDictionary::reflect_Method_klass(), "wrong type");
|
||||||
|
mirror = java_lang_reflect_Method::clazz(executable);
|
||||||
|
slot = java_lang_reflect_Method::slot(executable);
|
||||||
|
}
|
||||||
|
Klass* holder = java_lang_Class::as_Klass(mirror);
|
||||||
methodHandle method = InstanceKlass::cast(holder)->method_with_idnum(slot);
|
methodHandle method = InstanceKlass::cast(holder)->method_with_idnum(slot);
|
||||||
oop result = CompilerToVM::get_jvmci_method(method, CHECK_NULL);
|
oop result = CompilerToVM::get_jvmci_method(method, CHECK_NULL);
|
||||||
return JNIHandles::make_local(THREAD, result);
|
return JNIHandles::make_local(THREAD, result);
|
||||||
|
@ -1518,6 +1529,17 @@ C2V_VMENTRY(int, interpreterFrameSize, (JNIEnv*, jobject, jobject bytecode_frame
|
||||||
return size + Deoptimization::last_frame_adjust(0, callee_locals) * BytesPerWord;
|
return size + Deoptimization::last_frame_adjust(0, callee_locals) * BytesPerWord;
|
||||||
C2V_END
|
C2V_END
|
||||||
|
|
||||||
|
C2V_VMENTRY(void, compileToBytecode, (JNIEnv*, jobject, jobject lambda_form_handle))
|
||||||
|
Handle lambda_form = JNIHandles::resolve_non_null(lambda_form_handle);
|
||||||
|
if (lambda_form->is_a(SystemDictionary::LambdaForm_klass())) {
|
||||||
|
TempNewSymbol compileToBytecode = SymbolTable::new_symbol("compileToBytecode", CHECK);
|
||||||
|
JavaValue result(T_VOID);
|
||||||
|
JavaCalls::call_special(&result, lambda_form, SystemDictionary::LambdaForm_klass(), compileToBytecode, vmSymbols::void_method_signature(), CHECK);
|
||||||
|
} else {
|
||||||
|
THROW_MSG(vmSymbols::java_lang_IllegalArgumentException(),
|
||||||
|
err_msg("Unexpected type: %s", lambda_form->klass()->external_name()));
|
||||||
|
}
|
||||||
|
C2V_END
|
||||||
|
|
||||||
#define CC (char*) /*cast a literal from (const char*)*/
|
#define CC (char*) /*cast a literal from (const char*)*/
|
||||||
#define FN_PTR(f) CAST_FROM_FN_PTR(void*, &(c2v_ ## f))
|
#define FN_PTR(f) CAST_FROM_FN_PTR(void*, &(c2v_ ## f))
|
||||||
|
@ -1525,6 +1547,7 @@ C2V_END
|
||||||
#define STRING "Ljava/lang/String;"
|
#define STRING "Ljava/lang/String;"
|
||||||
#define OBJECT "Ljava/lang/Object;"
|
#define OBJECT "Ljava/lang/Object;"
|
||||||
#define CLASS "Ljava/lang/Class;"
|
#define CLASS "Ljava/lang/Class;"
|
||||||
|
#define EXECUTABLE "Ljava/lang/reflect/Executable;"
|
||||||
#define STACK_TRACE_ELEMENT "Ljava/lang/StackTraceElement;"
|
#define STACK_TRACE_ELEMENT "Ljava/lang/StackTraceElement;"
|
||||||
#define INSTALLED_CODE "Ljdk/vm/ci/code/InstalledCode;"
|
#define INSTALLED_CODE "Ljdk/vm/ci/code/InstalledCode;"
|
||||||
#define TARGET_DESCRIPTION "Ljdk/vm/ci/code/TargetDescription;"
|
#define TARGET_DESCRIPTION "Ljdk/vm/ci/code/TargetDescription;"
|
||||||
|
@ -1572,7 +1595,7 @@ JNINativeMethod CompilerToVM::methods[] = {
|
||||||
{CC "getClassInitializer", CC "(" HS_RESOLVED_KLASS ")" HS_RESOLVED_METHOD, FN_PTR(getClassInitializer)},
|
{CC "getClassInitializer", CC "(" HS_RESOLVED_KLASS ")" HS_RESOLVED_METHOD, FN_PTR(getClassInitializer)},
|
||||||
{CC "hasFinalizableSubclass", CC "(" HS_RESOLVED_KLASS ")Z", FN_PTR(hasFinalizableSubclass)},
|
{CC "hasFinalizableSubclass", CC "(" HS_RESOLVED_KLASS ")Z", FN_PTR(hasFinalizableSubclass)},
|
||||||
{CC "getMaxCallTargetOffset", CC "(J)J", FN_PTR(getMaxCallTargetOffset)},
|
{CC "getMaxCallTargetOffset", CC "(J)J", FN_PTR(getMaxCallTargetOffset)},
|
||||||
{CC "getResolvedJavaMethodAtSlot", CC "(" CLASS "I)" HS_RESOLVED_METHOD, FN_PTR(getResolvedJavaMethodAtSlot)},
|
{CC "asResolvedJavaMethod", CC "(" EXECUTABLE ")" HS_RESOLVED_METHOD, FN_PTR(asResolvedJavaMethod)},
|
||||||
{CC "getResolvedJavaMethod", CC "(Ljava/lang/Object;J)" HS_RESOLVED_METHOD, FN_PTR(getResolvedJavaMethod)},
|
{CC "getResolvedJavaMethod", CC "(Ljava/lang/Object;J)" HS_RESOLVED_METHOD, FN_PTR(getResolvedJavaMethod)},
|
||||||
{CC "getConstantPool", CC "(Ljava/lang/Object;)" HS_CONSTANT_POOL, FN_PTR(getConstantPool)},
|
{CC "getConstantPool", CC "(Ljava/lang/Object;)" HS_CONSTANT_POOL, FN_PTR(getConstantPool)},
|
||||||
{CC "getResolvedJavaType", CC "(Ljava/lang/Object;JZ)" HS_RESOLVED_KLASS, FN_PTR(getResolvedJavaType)},
|
{CC "getResolvedJavaType", CC "(Ljava/lang/Object;JZ)" HS_RESOLVED_KLASS, FN_PTR(getResolvedJavaType)},
|
||||||
|
@ -1599,6 +1622,7 @@ JNINativeMethod CompilerToVM::methods[] = {
|
||||||
{CC "flushDebugOutput", CC "()V", FN_PTR(flushDebugOutput)},
|
{CC "flushDebugOutput", CC "()V", FN_PTR(flushDebugOutput)},
|
||||||
{CC "methodDataProfileDataSize", CC "(JI)I", FN_PTR(methodDataProfileDataSize)},
|
{CC "methodDataProfileDataSize", CC "(JI)I", FN_PTR(methodDataProfileDataSize)},
|
||||||
{CC "interpreterFrameSize", CC "(" BYTECODE_FRAME ")I", FN_PTR(interpreterFrameSize)},
|
{CC "interpreterFrameSize", CC "(" BYTECODE_FRAME ")I", FN_PTR(interpreterFrameSize)},
|
||||||
|
{CC "compileToBytecode", CC "(" OBJECT ")V", FN_PTR(compileToBytecode)},
|
||||||
};
|
};
|
||||||
|
|
||||||
int CompilerToVM::methods_count() {
|
int CompilerToVM::methods_count() {
|
||||||
|
|
|
@ -327,8 +327,11 @@
|
||||||
declare_constant(JVM_ACC_FIELD_INTERNAL) \
|
declare_constant(JVM_ACC_FIELD_INTERNAL) \
|
||||||
declare_constant(JVM_ACC_FIELD_STABLE) \
|
declare_constant(JVM_ACC_FIELD_STABLE) \
|
||||||
declare_constant(JVM_ACC_FIELD_HAS_GENERIC_SIGNATURE) \
|
declare_constant(JVM_ACC_FIELD_HAS_GENERIC_SIGNATURE) \
|
||||||
|
declare_preprocessor_constant("JVM_ACC_VARARGS", JVM_ACC_VARARGS) \
|
||||||
|
declare_preprocessor_constant("JVM_ACC_BRIDGE", JVM_ACC_BRIDGE) \
|
||||||
|
declare_preprocessor_constant("JVM_ACC_ANNOTATION", JVM_ACC_ANNOTATION) \
|
||||||
|
declare_preprocessor_constant("JVM_ACC_ENUM", JVM_ACC_ENUM) \
|
||||||
declare_preprocessor_constant("JVM_ACC_SYNTHETIC", JVM_ACC_SYNTHETIC) \
|
declare_preprocessor_constant("JVM_ACC_SYNTHETIC", JVM_ACC_SYNTHETIC) \
|
||||||
declare_preprocessor_constant("JVM_RECOGNIZED_FIELD_MODIFIERS", JVM_RECOGNIZED_FIELD_MODIFIERS) \
|
|
||||||
\
|
\
|
||||||
declare_constant(JVM_CONSTANT_Utf8) \
|
declare_constant(JVM_CONSTANT_Utf8) \
|
||||||
declare_constant(JVM_CONSTANT_Unicode) \
|
declare_constant(JVM_CONSTANT_Unicode) \
|
||||||
|
|
|
@ -57,18 +57,7 @@ public class CTVMUtilities {
|
||||||
if (!(method instanceof Method || method instanceof Constructor)) {
|
if (!(method instanceof Method || method instanceof Constructor)) {
|
||||||
throw new Error("wrong executable type " + method.getClass());
|
throw new Error("wrong executable type " + method.getClass());
|
||||||
}
|
}
|
||||||
Field slotField;
|
return CompilerToVMHelper.asResolvedJavaMethod(method);
|
||||||
int slot;
|
|
||||||
try {
|
|
||||||
slotField = method.getClass().getDeclaredField("slot");
|
|
||||||
boolean old = slotField.isAccessible();
|
|
||||||
slotField.setAccessible(true);
|
|
||||||
slot = slotField.getInt(method);
|
|
||||||
slotField.setAccessible(old);
|
|
||||||
} catch (ReflectiveOperationException e) {
|
|
||||||
throw new Error("TEST BUG: Can't get slot field", e);
|
|
||||||
}
|
|
||||||
return CompilerToVMHelper.getResolvedJavaMethodAtSlot(cls, slot);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static HotSpotResolvedJavaMethod getResolvedMethod(
|
public static HotSpotResolvedJavaMethod getResolvedMethod(
|
||||||
|
|
|
@ -28,6 +28,7 @@ import jdk.vm.ci.code.InvalidInstalledCodeException;
|
||||||
import jdk.vm.ci.code.TargetDescription;
|
import jdk.vm.ci.code.TargetDescription;
|
||||||
import jdk.vm.ci.meta.ConstantPool;
|
import jdk.vm.ci.meta.ConstantPool;
|
||||||
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
||||||
|
import java.lang.reflect.Executable;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A simple "proxy" class to get test access to CompilerToVM package-private methods
|
* A simple "proxy" class to get test access to CompilerToVM package-private methods
|
||||||
|
@ -171,9 +172,9 @@ public class CompilerToVMHelper {
|
||||||
return CTVM.hasFinalizableSubclass((HotSpotResolvedObjectTypeImpl) type);
|
return CTVM.hasFinalizableSubclass((HotSpotResolvedObjectTypeImpl) type);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static HotSpotResolvedJavaMethodImpl getResolvedJavaMethodAtSlot(
|
public static HotSpotResolvedJavaMethodImpl asResolvedJavaMethod(
|
||||||
Class<?> holder, int slot) {
|
Executable executable) {
|
||||||
return CTVM.getResolvedJavaMethodAtSlot(holder, slot);
|
return CTVM.asResolvedJavaMethod(executable);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static long getMaxCallTargetOffset(long address) {
|
public static long getMaxCallTargetOffset(long address) {
|
||||||
|
|
|
@ -36,7 +36,7 @@
|
||||||
* jdk.vm.ci/jdk.vm.ci.meta
|
* jdk.vm.ci/jdk.vm.ci.meta
|
||||||
* @build jdk.vm.ci/jdk.vm.ci.hotspot.CompilerToVMHelper
|
* @build jdk.vm.ci/jdk.vm.ci.hotspot.CompilerToVMHelper
|
||||||
* @run main/othervm -XX:+UnlockExperimentalVMOptions -XX:+EnableJVMCI
|
* @run main/othervm -XX:+UnlockExperimentalVMOptions -XX:+EnableJVMCI
|
||||||
* compiler.jvmci.compilerToVM.GetResolvedJavaMethodAtSlotTest
|
* compiler.jvmci.compilerToVM.AsResolvedJavaMethodTest
|
||||||
*/
|
*/
|
||||||
|
|
||||||
package compiler.jvmci.compilerToVM;
|
package compiler.jvmci.compilerToVM;
|
||||||
|
@ -45,10 +45,12 @@ import jdk.test.lib.Asserts;
|
||||||
import jdk.vm.ci.hotspot.CompilerToVMHelper;
|
import jdk.vm.ci.hotspot.CompilerToVMHelper;
|
||||||
import jdk.vm.ci.hotspot.HotSpotResolvedJavaMethod;
|
import jdk.vm.ci.hotspot.HotSpotResolvedJavaMethod;
|
||||||
|
|
||||||
import java.util.HashMap;
|
import java.lang.reflect.Executable;
|
||||||
import java.util.Map;
|
import java.util.Arrays;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
public class GetResolvedJavaMethodAtSlotTest {
|
public class AsResolvedJavaMethodTest {
|
||||||
|
|
||||||
private static class A {
|
private static class A {
|
||||||
{
|
{
|
||||||
|
@ -81,41 +83,31 @@ public class GetResolvedJavaMethodAtSlotTest {
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void main(String[] args) {
|
public static void main(String[] args) {
|
||||||
Map<Class<?>, Integer> testCases = getTestCases();
|
List<Class<?>> testCases = getTestCases();
|
||||||
testCases.forEach(GetResolvedJavaMethodAtSlotTest::test);
|
testCases.forEach(AsResolvedJavaMethodTest::test);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static Map<Class<?>, Integer> getTestCases() {
|
private static List<Class<?>> getTestCases() {
|
||||||
Map<Class<?>, Integer> testCases = new HashMap<>();
|
List<Class<?>> testCases = new ArrayList<>();
|
||||||
testCases.put(A.class, 5); // ctor, init, f1, f2, f3
|
testCases.add(A.class);
|
||||||
testCases.put(S.class, 5); // ctor, cinit, f1, f2, f3
|
testCases.add(S.class);
|
||||||
testCases.put(I.class, 3); // f1, f2, f3
|
testCases.add(I.class);
|
||||||
testCases.put(B.class, 2); // ctor, f4
|
testCases.add(B.class);
|
||||||
return testCases;
|
return testCases;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void test(Class<?> aClass, int methodNumber) {
|
private static void test(Class<?> aClass) {
|
||||||
testSlotBigger(aClass);
|
testCorrectMethods(aClass);
|
||||||
testCorrectMethods(aClass, methodNumber);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void testSlotBigger(Class<?> holder) {
|
private static void testCorrectMethods(Class<?> holder) {
|
||||||
HotSpotResolvedJavaMethod method
|
List<Executable> executables = new ArrayList<>();
|
||||||
= CompilerToVMHelper.getResolvedJavaMethodAtSlot(holder, 50);
|
executables.addAll(Arrays.asList(holder.getDeclaredMethods()));
|
||||||
Asserts.assertNull(method, "Got method for non existing slot 50 in "
|
executables.addAll(Arrays.asList(holder.getDeclaredConstructors()));
|
||||||
+ holder);
|
for (Executable executable : executables) {
|
||||||
}
|
|
||||||
|
|
||||||
private static void testCorrectMethods(Class<?> holder, int methodsNumber) {
|
|
||||||
for (int i = 0; i < methodsNumber; i++) {
|
|
||||||
String caseName = String.format("slot %d in %s",
|
|
||||||
i, holder.getCanonicalName());
|
|
||||||
HotSpotResolvedJavaMethod method = CompilerToVMHelper
|
HotSpotResolvedJavaMethod method = CompilerToVMHelper
|
||||||
.getResolvedJavaMethodAtSlot(holder, i);
|
.asResolvedJavaMethod(executable);
|
||||||
Asserts.assertNotNull(method, caseName + " did not got method");
|
Asserts.assertNotNull(method, "could not convert " + method);
|
||||||
Asserts.assertEQ(holder,
|
|
||||||
CompilerToVMHelper.getMirror(method.getDeclaringClass()),
|
|
||||||
caseName + " : unexpected declaring class");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -74,45 +74,37 @@ public class FindUniqueConcreteMethodTest {
|
||||||
private static Set<TestCase> createTestCases() {
|
private static Set<TestCase> createTestCases() {
|
||||||
Set<TestCase> result = new HashSet<>();
|
Set<TestCase> result = new HashSet<>();
|
||||||
// a public method
|
// a public method
|
||||||
result.add(new TestCase(true, SingleSubclass.class,
|
result.add(new TestCase(true, SingleSubclass.class, "usualMethod"));
|
||||||
SingleSubclass.class, "usualMethod"));
|
|
||||||
// overriden method
|
// overriden method
|
||||||
result.add(new TestCase(true, SingleSubclass.class,
|
result.add(new TestCase(true, SingleSubclass.class, "overridenMethod"));
|
||||||
SingleSubclass.class, "overridenMethod"));
|
|
||||||
// private method
|
// private method
|
||||||
result.add(new TestCase(true, SingleSubclass.class,
|
result.add(new TestCase(true, SingleSubclass.class, "privateMethod"));
|
||||||
SingleSubclass.class, "privateMethod"));
|
|
||||||
// protected method
|
// protected method
|
||||||
result.add(new TestCase(true, SingleSubclass.class,
|
result.add(new TestCase(true, SingleSubclass.class, "protectedMethod"));
|
||||||
SingleSubclass.class, "protectedMethod"));
|
|
||||||
// default(package-private) method
|
// default(package-private) method
|
||||||
result.add(new TestCase(true, SingleSubclass.class,
|
result.add(new TestCase(true, SingleSubclass.class, "defaultAccessMethod"));
|
||||||
SingleSubclass.class, "defaultAccessMethod"));
|
|
||||||
// default interface method redefined in implementer
|
// default interface method redefined in implementer
|
||||||
result.add(new TestCase(true, MultipleImplementer1.class,
|
result.add(new TestCase(true, MultipleImplementer1.class, "defaultMethod"));
|
||||||
MultipleImplementer1.class, "defaultMethod"));
|
|
||||||
// interface method
|
// interface method
|
||||||
result.add(new TestCase(true, MultipleImplementer1.class,
|
result.add(new TestCase(true, MultipleImplementer1.class, "testMethod"));
|
||||||
MultipleImplementer1.class, "testMethod"));
|
|
||||||
// default interface method not redefined in implementer
|
// default interface method not redefined in implementer
|
||||||
result.add(new TestCase(true, SingleImplementer.class,
|
// result.add(new TestCase(true, SingleImplementer.class,
|
||||||
SingleImplementerInterface.class, "defaultMethod"));
|
// SingleImplementerInterface.class, "defaultMethod"));
|
||||||
// static method
|
// static method
|
||||||
result.add(new TestCase(false, SingleSubclass.class,
|
result.add(new TestCase(false, SingleSubclass.class, "staticMethod"));
|
||||||
SingleSubclass.class, "staticMethod"));
|
|
||||||
// interface method
|
// interface method
|
||||||
result.add(new TestCase(false, MultipleSuperImplementers.class,
|
result.add(new TestCase(false, MultipleSuperImplementers.class,
|
||||||
DuplicateSimpleSingleImplementerInterface.class, "interfaceMethod", false));
|
DuplicateSimpleSingleImplementerInterface.class, "interfaceMethod"));
|
||||||
result.add(new TestCase(false, MultipleSuperImplementers.class,
|
result.add(new TestCase(false, MultipleSuperImplementers.class,
|
||||||
SimpleSingleImplementerInterface.class, "interfaceMethod", false));
|
SimpleSingleImplementerInterface.class, "interfaceMethod"));
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void runTest(TestCase tcase) throws NoSuchMethodException {
|
private void runTest(TestCase tcase) throws NoSuchMethodException {
|
||||||
System.out.println(tcase);
|
System.out.println(tcase);
|
||||||
Method method = tcase.holder.getDeclaredMethod(tcase.methodName);
|
Method method = tcase.holder.getDeclaredMethod(tcase.methodName);
|
||||||
HotSpotResolvedJavaMethod testMethod = CTVMUtilities
|
HotSpotResolvedJavaMethod testMethod = CTVMUtilities.getResolvedMethod(method);
|
||||||
.getResolvedMethod(tcase.methodFromReceiver ? tcase.receiver : tcase.holder, method);
|
|
||||||
HotSpotResolvedObjectType resolvedType = CompilerToVMHelper
|
HotSpotResolvedObjectType resolvedType = CompilerToVMHelper
|
||||||
.lookupType(Utils.toJVMTypeSignature(tcase.receiver), getClass(),
|
.lookupType(Utils.toJVMTypeSignature(tcase.receiver), getClass(),
|
||||||
/* resolve = */ true);
|
/* resolve = */ true);
|
||||||
|
@ -127,25 +119,23 @@ public class FindUniqueConcreteMethodTest {
|
||||||
public final Class<?> holder;
|
public final Class<?> holder;
|
||||||
public final String methodName;
|
public final String methodName;
|
||||||
public final boolean isPositive;
|
public final boolean isPositive;
|
||||||
public final boolean methodFromReceiver;
|
|
||||||
|
|
||||||
public TestCase(boolean isPositive, Class<?> clazz, Class<?> holder,
|
public TestCase(boolean isPositive, Class<?> clazz, Class<?> holder,
|
||||||
String methodName, boolean methodFromReceiver) {
|
String methodName) {
|
||||||
this.receiver = clazz;
|
this.receiver = clazz;
|
||||||
this.methodName = methodName;
|
this.methodName = methodName;
|
||||||
this.isPositive = isPositive;
|
this.isPositive = isPositive;
|
||||||
this.holder = holder;
|
this.holder = holder;
|
||||||
this.methodFromReceiver = methodFromReceiver;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public TestCase(boolean isPositive, Class<?> clazz, Class<?> holder, String methodName) {
|
public TestCase(boolean isPositive, Class<?> clazz, String methodName) {
|
||||||
this(isPositive, clazz, holder, methodName, true);
|
this(isPositive, clazz, clazz, methodName);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return String.format("CASE: receiver=%s, holder=%s, method=%s, isPositive=%s, methodFromReceiver=%s",
|
return String.format("CASE: receiver=%s, holder=%s, method=%s, isPositive=%s",
|
||||||
receiver.getName(), holder.getName(), methodName, isPositive, methodFromReceiver);
|
receiver.getName(), holder.getName(), methodName, isPositive);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -52,6 +52,7 @@ import jdk.vm.ci.hotspot.PublicMetaspaceWrapperObject;
|
||||||
import sun.hotspot.WhiteBox;
|
import sun.hotspot.WhiteBox;
|
||||||
|
|
||||||
import java.lang.reflect.Field;
|
import java.lang.reflect.Field;
|
||||||
|
import java.lang.reflect.Method;
|
||||||
|
|
||||||
public class GetResolvedJavaMethodTest {
|
public class GetResolvedJavaMethodTest {
|
||||||
private static enum TestCase {
|
private static enum TestCase {
|
||||||
|
@ -65,9 +66,7 @@ public class GetResolvedJavaMethodTest {
|
||||||
JAVA_METHOD_BASE {
|
JAVA_METHOD_BASE {
|
||||||
@Override
|
@Override
|
||||||
HotSpotResolvedJavaMethod getResolvedJavaMethod() {
|
HotSpotResolvedJavaMethod getResolvedJavaMethod() {
|
||||||
HotSpotResolvedJavaMethod methodInstance
|
HotSpotResolvedJavaMethod methodInstance = TEST_METHOD;
|
||||||
= CompilerToVMHelper.getResolvedJavaMethodAtSlot(
|
|
||||||
TEST_CLASS, 0);
|
|
||||||
try {
|
try {
|
||||||
METASPACE_METHOD_FIELD.set(methodInstance,
|
METASPACE_METHOD_FIELD.set(methodInstance,
|
||||||
getPtrToMethod());
|
getPtrToMethod());
|
||||||
|
@ -82,9 +81,7 @@ public class GetResolvedJavaMethodTest {
|
||||||
@Override
|
@Override
|
||||||
HotSpotResolvedJavaMethod getResolvedJavaMethod() {
|
HotSpotResolvedJavaMethod getResolvedJavaMethod() {
|
||||||
long ptr = getPtrToMethod();
|
long ptr = getPtrToMethod();
|
||||||
HotSpotResolvedJavaMethod methodInstance
|
HotSpotResolvedJavaMethod methodInstance = TEST_METHOD;
|
||||||
= CompilerToVMHelper.getResolvedJavaMethodAtSlot(
|
|
||||||
TEST_CLASS, 0);
|
|
||||||
try {
|
try {
|
||||||
METASPACE_METHOD_FIELD.set(methodInstance, ptr / 2L);
|
METASPACE_METHOD_FIELD.set(methodInstance, ptr / 2L);
|
||||||
} catch (ReflectiveOperationException e) {
|
} catch (ReflectiveOperationException e) {
|
||||||
|
@ -98,9 +95,7 @@ public class GetResolvedJavaMethodTest {
|
||||||
@Override
|
@Override
|
||||||
HotSpotResolvedJavaMethod getResolvedJavaMethod() {
|
HotSpotResolvedJavaMethod getResolvedJavaMethod() {
|
||||||
long ptr = getPtrToMethod();
|
long ptr = getPtrToMethod();
|
||||||
HotSpotResolvedJavaMethod methodInstance
|
HotSpotResolvedJavaMethod methodInstance = TEST_METHOD;
|
||||||
= CompilerToVMHelper.getResolvedJavaMethodAtSlot(
|
|
||||||
TEST_CLASS, 0);
|
|
||||||
try {
|
try {
|
||||||
METASPACE_METHOD_FIELD.set(methodInstance, 0L);
|
METASPACE_METHOD_FIELD.set(methodInstance, 0L);
|
||||||
} catch (ReflectiveOperationException e) {
|
} catch (ReflectiveOperationException e) {
|
||||||
|
@ -118,16 +113,21 @@ public class GetResolvedJavaMethodTest {
|
||||||
private static final WhiteBox WB = WhiteBox.getWhiteBox();
|
private static final WhiteBox WB = WhiteBox.getWhiteBox();
|
||||||
private static final Field METASPACE_METHOD_FIELD;
|
private static final Field METASPACE_METHOD_FIELD;
|
||||||
private static final Class<?> TEST_CLASS = GetResolvedJavaMethodTest.class;
|
private static final Class<?> TEST_CLASS = GetResolvedJavaMethodTest.class;
|
||||||
|
private static final HotSpotResolvedJavaMethod TEST_METHOD;
|
||||||
private static final long PTR;
|
private static final long PTR;
|
||||||
static {
|
static {
|
||||||
HotSpotResolvedJavaMethod method
|
try {
|
||||||
= CompilerToVMHelper.getResolvedJavaMethodAtSlot(TEST_CLASS, 0);
|
Method method = TEST_CLASS.getDeclaredMethod("test", TestCase.class);
|
||||||
|
TEST_METHOD = CompilerToVMHelper.asResolvedJavaMethod(method);
|
||||||
|
} catch (NoSuchMethodException e) {
|
||||||
|
throw new Error("TESTBUG : " + e, e);
|
||||||
|
}
|
||||||
try {
|
try {
|
||||||
// jdk.vm.ci.hotspot.HotSpotResolvedJavaMethodImpl.metaspaceMethod
|
// jdk.vm.ci.hotspot.HotSpotResolvedJavaMethodImpl.metaspaceMethod
|
||||||
METASPACE_METHOD_FIELD = method.getClass()
|
METASPACE_METHOD_FIELD = TEST_METHOD.getClass()
|
||||||
.getDeclaredField("metaspaceMethod");
|
.getDeclaredField("metaspaceMethod");
|
||||||
METASPACE_METHOD_FIELD.setAccessible(true);
|
METASPACE_METHOD_FIELD.setAccessible(true);
|
||||||
PTR = (long) METASPACE_METHOD_FIELD.get(method);
|
PTR = (long) METASPACE_METHOD_FIELD.get(TEST_METHOD);
|
||||||
} catch (ReflectiveOperationException e) {
|
} catch (ReflectiveOperationException e) {
|
||||||
throw new Error("TESTBUG : " + e, e);
|
throw new Error("TESTBUG : " + e, e);
|
||||||
}
|
}
|
||||||
|
|
|
@ -23,6 +23,10 @@
|
||||||
|
|
||||||
package jdk.vm.ci.hotspot.test;
|
package jdk.vm.ci.hotspot.test;
|
||||||
|
|
||||||
|
import java.lang.reflect.Field;
|
||||||
|
|
||||||
|
import org.testng.annotations.DataProvider;
|
||||||
|
|
||||||
import jdk.internal.misc.Unsafe;
|
import jdk.internal.misc.Unsafe;
|
||||||
import jdk.vm.ci.hotspot.HotSpotConstantReflectionProvider;
|
import jdk.vm.ci.hotspot.HotSpotConstantReflectionProvider;
|
||||||
import jdk.vm.ci.hotspot.HotSpotJVMCIRuntimeProvider;
|
import jdk.vm.ci.hotspot.HotSpotJVMCIRuntimeProvider;
|
||||||
|
@ -32,27 +36,14 @@ import jdk.vm.ci.meta.Constant;
|
||||||
import jdk.vm.ci.meta.JavaConstant;
|
import jdk.vm.ci.meta.JavaConstant;
|
||||||
import jdk.vm.ci.meta.JavaKind;
|
import jdk.vm.ci.meta.JavaKind;
|
||||||
import jdk.vm.ci.runtime.JVMCI;
|
import jdk.vm.ci.runtime.JVMCI;
|
||||||
import org.testng.annotations.DataProvider;
|
|
||||||
|
|
||||||
import java.lang.reflect.Field;
|
|
||||||
|
|
||||||
public class MemoryAccessProviderData {
|
public class MemoryAccessProviderData {
|
||||||
private static final Unsafe UNSAFE = getUnsafe();
|
private static final Unsafe UNSAFE = Unsafe.getUnsafe();
|
||||||
private static final HotSpotConstantReflectionProvider CONSTANT_REFLECTION = (HotSpotConstantReflectionProvider) JVMCI.getRuntime().getHostJVMCIBackend().getConstantReflection();
|
private static final HotSpotConstantReflectionProvider CONSTANT_REFLECTION = (HotSpotConstantReflectionProvider) JVMCI.getRuntime().getHostJVMCIBackend().getConstantReflection();
|
||||||
private static final TestClass TEST_OBJECT = new TestClass();
|
private static final TestClass TEST_OBJECT = new TestClass();
|
||||||
private static final JavaConstant TEST_CONSTANT = CONSTANT_REFLECTION.forObject(TEST_OBJECT);
|
private static final JavaConstant TEST_CONSTANT = CONSTANT_REFLECTION.forObject(TEST_OBJECT);
|
||||||
private static final JavaConstant TEST_CLASS_CONSTANT = CONSTANT_REFLECTION.forObject(TestClass.class);
|
private static final JavaConstant TEST_CLASS_CONSTANT = CONSTANT_REFLECTION.forObject(TestClass.class);
|
||||||
|
|
||||||
private static Unsafe getUnsafe() {
|
|
||||||
try {
|
|
||||||
Field f = Unsafe.class.getDeclaredField("theUnsafe");
|
|
||||||
f.setAccessible(true);
|
|
||||||
return (Unsafe) f.get(null);
|
|
||||||
} catch (NoSuchFieldException | IllegalAccessException e) {
|
|
||||||
throw new RuntimeException("Unable to get Unsafe instance.", e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@DataProvider(name = "positiveObject")
|
@DataProvider(name = "positiveObject")
|
||||||
public static Object[][] getPositiveObjectJavaKind() {
|
public static Object[][] getPositiveObjectJavaKind() {
|
||||||
HotSpotJVMCIRuntimeProvider runtime = (HotSpotJVMCIRuntimeProvider) JVMCI.getRuntime();
|
HotSpotJVMCIRuntimeProvider runtime = (HotSpotJVMCIRuntimeProvider) JVMCI.getRuntime();
|
||||||
|
|
|
@ -438,7 +438,6 @@ public class TestResolvedJavaMethod extends MethodUniverse {
|
||||||
|
|
||||||
// @formatter:off
|
// @formatter:off
|
||||||
private static final String[] untestedApiMethods = {
|
private static final String[] untestedApiMethods = {
|
||||||
"invoke",
|
|
||||||
"newInstance",
|
"newInstance",
|
||||||
"getDeclaringClass",
|
"getDeclaringClass",
|
||||||
"getEncoding",
|
"getEncoding",
|
||||||
|
|
|
@ -35,28 +35,6 @@
|
||||||
|
|
||||||
package jdk.vm.ci.runtime.test;
|
package jdk.vm.ci.runtime.test;
|
||||||
|
|
||||||
import jdk.internal.reflect.ConstantPool;
|
|
||||||
import jdk.vm.ci.common.JVMCIError;
|
|
||||||
import jdk.vm.ci.meta.Assumptions.AssumptionResult;
|
|
||||||
import jdk.vm.ci.meta.JavaConstant;
|
|
||||||
import jdk.vm.ci.meta.JavaKind;
|
|
||||||
import jdk.vm.ci.meta.ModifiersProvider;
|
|
||||||
import jdk.vm.ci.meta.ResolvedJavaField;
|
|
||||||
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
|
||||||
import jdk.vm.ci.meta.ResolvedJavaType;
|
|
||||||
import org.junit.Test;
|
|
||||||
|
|
||||||
import java.lang.annotation.Annotation;
|
|
||||||
import java.lang.reflect.Field;
|
|
||||||
import java.lang.reflect.Method;
|
|
||||||
import java.lang.reflect.Modifier;
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.Collections;
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.HashSet;
|
|
||||||
import java.util.Map;
|
|
||||||
import java.util.Set;
|
|
||||||
|
|
||||||
import static java.lang.reflect.Modifier.isAbstract;
|
import static java.lang.reflect.Modifier.isAbstract;
|
||||||
import static java.lang.reflect.Modifier.isFinal;
|
import static java.lang.reflect.Modifier.isFinal;
|
||||||
import static java.lang.reflect.Modifier.isPrivate;
|
import static java.lang.reflect.Modifier.isPrivate;
|
||||||
|
@ -70,6 +48,28 @@ import static org.junit.Assert.assertNotNull;
|
||||||
import static org.junit.Assert.assertNull;
|
import static org.junit.Assert.assertNull;
|
||||||
import static org.junit.Assert.assertTrue;
|
import static org.junit.Assert.assertTrue;
|
||||||
|
|
||||||
|
import java.lang.annotation.Annotation;
|
||||||
|
import java.lang.reflect.Field;
|
||||||
|
import java.lang.reflect.Method;
|
||||||
|
import java.lang.reflect.Modifier;
|
||||||
|
import java.util.Arrays;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
|
import org.junit.Test;
|
||||||
|
|
||||||
|
import jdk.internal.reflect.ConstantPool;
|
||||||
|
import jdk.vm.ci.common.JVMCIError;
|
||||||
|
import jdk.vm.ci.meta.Assumptions.AssumptionResult;
|
||||||
|
import jdk.vm.ci.meta.JavaConstant;
|
||||||
|
import jdk.vm.ci.meta.JavaKind;
|
||||||
|
import jdk.vm.ci.meta.ResolvedJavaField;
|
||||||
|
import jdk.vm.ci.meta.ResolvedJavaMethod;
|
||||||
|
import jdk.vm.ci.meta.ResolvedJavaType;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Tests for {@link ResolvedJavaType}.
|
* Tests for {@link ResolvedJavaType}.
|
||||||
*/
|
*/
|
||||||
|
@ -146,8 +146,9 @@ public class TestResolvedJavaType extends TypeUniverse {
|
||||||
public void getModifiersTest() {
|
public void getModifiersTest() {
|
||||||
for (Class<?> c : classes) {
|
for (Class<?> c : classes) {
|
||||||
ResolvedJavaType type = metaAccess.lookupJavaType(c);
|
ResolvedJavaType type = metaAccess.lookupJavaType(c);
|
||||||
int expected = c.getModifiers() & ModifiersProvider.jvmClassModifiers();
|
int mask = Modifier.classModifiers() & ~Modifier.STATIC;
|
||||||
int actual = type.getModifiers() & ModifiersProvider.jvmClassModifiers();
|
int expected = c.getModifiers() & mask;
|
||||||
|
int actual = type.getModifiers() & mask;
|
||||||
Class<?> elementalType = c;
|
Class<?> elementalType = c;
|
||||||
while (elementalType.isArray()) {
|
while (elementalType.isArray()) {
|
||||||
elementalType = elementalType.getComponentType();
|
elementalType = elementalType.getComponentType();
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue