Search in sources :

Example 1 with JNI

use of org.graalvm.jniutils.JNI in project graal by oracle.

the class LibGraalUtil method checkToLibGraalCalls.

/*----------------- CHECKING ------------------*/
/**
 * Checks that all {@code ToLibGraal}s are implemented and their HotSpot/libgraal ends points
 * match.
 */
@Platforms(Platform.HOSTED_ONLY.class)
public static void checkToLibGraalCalls(Class<?> toLibGraalEntryPointsClass, Class<?> toLibGraalCallsClass, Class<? extends Annotation> annotationClass) throws InternalError {
    try {
        Method valueMethod = annotationClass.getDeclaredMethod("value");
        Type t = valueMethod.getGenericReturnType();
        check(t instanceof Class<?> && ((Class<?>) t).isEnum(), "Annotation value must be enum.");
        @SuppressWarnings("unchecked") Set<? extends Enum<?>> unimplemented = EnumSet.allOf(((Class<?>) t).asSubclass(Enum.class));
        for (Method libGraalMethod : toLibGraalEntryPointsClass.getDeclaredMethods()) {
            Annotation call = libGraalMethod.getAnnotation(annotationClass);
            if (call != null) {
                check(Modifier.isStatic(libGraalMethod.getModifiers()), "Method annotated by %s must be static: %s", annotationClass, libGraalMethod);
                CEntryPoint ep = libGraalMethod.getAnnotation(CEntryPoint.class);
                check(ep != null, "Method annotated by %s must also be annotated by %s: %s", annotationClass, CEntryPoint.class, libGraalMethod);
                String name = ep.name();
                String prefix = "Java_" + toLibGraalCallsClass.getName().replace('.', '_') + '_';
                check(name.startsWith(prefix), "Method must be a JNI entry point for a method in %s: %s", toLibGraalCallsClass, libGraalMethod);
                name = name.substring(prefix.length());
                Method hsMethod = findHSMethod(toLibGraalCallsClass, name, annotationClass);
                Class<?>[] libGraalParameters = libGraalMethod.getParameterTypes();
                Class<?>[] hsParameters = hsMethod.getParameterTypes();
                check(hsParameters.length + 2 == libGraalParameters.length, "%s should have 2 more parameters than %s", libGraalMethod, hsMethod);
                check(libGraalParameters.length >= 3, "Expect at least 3 parameters: %s", libGraalMethod);
                check(libGraalParameters[0] == JNI.JNIEnv.class, "Parameter 0 must be of type %s: %s", JNI.JNIEnv.class, libGraalMethod);
                check(libGraalParameters[1] == JNI.JClass.class, "Parameter 1 must be of type %s: %s", JNI.JClass.class, libGraalMethod);
                check(libGraalParameters[2] == long.class, "Parameter 2 must be of type long: %s", libGraalMethod);
                check(hsParameters[0] == long.class, "Parameter 0 must be of type long: %s", hsMethod);
                for (int i = 3, j = 1; i < libGraalParameters.length; i++, j++) {
                    Class<?> libgraal = libGraalParameters[i];
                    Class<?> hs = hsParameters[j];
                    Class<?> hsExpect;
                    if (hs.isPrimitive()) {
                        hsExpect = libgraal;
                    } else {
                        if (libgraal == JNI.JString.class) {
                            hsExpect = String.class;
                        } else if (libgraal == JNI.JByteArray.class) {
                            hsExpect = byte[].class;
                        } else if (libgraal == JNI.JLongArray.class) {
                            hsExpect = long[].class;
                        } else if (libgraal == JNI.JObjectArray.class) {
                            hsExpect = Object[].class;
                        } else {
                            check(libgraal == JNI.JObject.class, "must be");
                            hsExpect = Object.class;
                        }
                    }
                    check(hsExpect.isAssignableFrom(hs), "HotSpot parameter %d (%s) incompatible with libgraal parameter %d (%s): %s", j, hs.getName(), i, libgraal.getName(), hsMethod);
                }
                unimplemented.remove(valueMethod.invoke(call));
            }
        }
        check(unimplemented.isEmpty(), "Unimplemented libgraal calls: %s", unimplemented);
    } catch (ReflectiveOperationException e) {
        throw new InternalError(e);
    }
}
Also used : JNI(org.graalvm.jniutils.JNI) Method(java.lang.reflect.Method) Annotation(java.lang.annotation.Annotation) CEntryPoint(org.graalvm.nativeimage.c.function.CEntryPoint) Type(java.lang.reflect.Type) CEntryPoint(org.graalvm.nativeimage.c.function.CEntryPoint) JNIEnv(org.graalvm.jniutils.JNI.JNIEnv) Platforms(org.graalvm.nativeimage.Platforms)

Example 2 with JNI

use of org.graalvm.jniutils.JNI in project graal by oracle.

the class MBeanProxy method defineClassesInHotSpot.

/**
 * Uses JNI to define the classes in HotSpot heap.
 */
private static void defineClassesInHotSpot(JNI.JNIEnv env) {
    Pointer barrier = getDefineClassesStatePointer();
    JNI.JObject classLoader = JNIUtil.getJVMCIClassLoader(env);
    Runnable defineAction = () -> {
        defineClassInHotSpot(env, classLoader, HS_CALLS_CLASS);
        long entryPoints = defineClassInHotSpot(env, classLoader, HS_ENTRYPOINTS_CLASS).rawValue();
        defineClassInHotSpot(env, classLoader, HS_BEAN_CLASS);
        defineClassInHotSpot(env, classLoader, HS_BEAN_FACTORY_CLASS);
        defineClassInHotSpot(env, classLoader, HS_PUSHBACK_ITER_CLASS);
        defineClassInHotSpot(env, classLoader, HS_AGGREGATED_MEMORY_POOL_BEAN_CLASS);
        fromLibGraalEntryPoints = JNIUtil.NewGlobalRef(env, WordFactory.pointer(entryPoints), "Class<" + HS_ENTRYPOINTS_CLASS.binaryName + ">");
    };
    Runnable loadAction = () -> {
        long entryPoints = JNIUtil.findClass(env, classLoader, HS_ENTRYPOINTS_CLASS.binaryName, true).rawValue();
        fromLibGraalEntryPoints = JNIUtil.NewGlobalRef(env, WordFactory.pointer(entryPoints), "Class<" + HS_ENTRYPOINTS_CLASS.binaryName + ">");
    };
    runGuarded(barrier, defineAction, loadAction);
}
Also used : JNI(org.graalvm.jniutils.JNI) Pointer(org.graalvm.word.Pointer) CCharPointer(org.graalvm.nativeimage.c.type.CCharPointer)

Example 3 with JNI

use of org.graalvm.jniutils.JNI in project graal by oracle.

the class MBeanProxy method defineClassInHotSpot.

/**
 * Defines a class in HotSpot heap using JNI.
 *
 * @param env the {@code JNIEnv}
 * @param classLoader the class loader to define class in.
 * @param classData the class to define in HotSpot
 * @return the defined class
 */
private static JNI.JClass defineClassInHotSpot(JNI.JNIEnv env, JNI.JObject classLoader, ClassData classData) {
    CCharPointer classDataPointer = UnmanagedMemory.malloc(classData.byteCode.length);
    ByteBuffer buffer = CTypeConversion.asByteBuffer(classDataPointer, classData.byteCode.length);
    buffer.put(classData.byteCode);
    try (CTypeConversion.CCharPointerHolder className = CTypeConversion.toCString(classData.binaryName)) {
        JNI.JClass definedClass = JNIUtil.DefineClass(env, className.get(), classLoader, classDataPointer, classData.byteCode.length);
        return definedClass;
    } finally {
        UnmanagedMemory.free(classDataPointer);
        // LinkageError is allowed, the class may be already defined
        JNIExceptionWrapper.wrapAndThrowPendingJNIException(env, ExceptionHandler.allowExceptions(LinkageError.class));
    }
}
Also used : JNI(org.graalvm.jniutils.JNI) CTypeConversion(org.graalvm.nativeimage.c.type.CTypeConversion) ByteBuffer(java.nio.ByteBuffer) CCharPointer(org.graalvm.nativeimage.c.type.CCharPointer)

Example 4 with JNI

use of org.graalvm.jniutils.JNI in project graal by oracle.

the class JMXToLibGraalEntryPoints method mapToRaw.

/**
 * Encodes a {@link Map} of properties into JNI byte array using {@link OptionsEncoder}.
 */
private static JNI.JByteArray mapToRaw(JNI.JNIEnv env, Map<String, Object> map) {
    byte[] serialized = OptionsEncoder.encode(map);
    JNI.JByteArray res = JNIUtil.NewByteArray(env, serialized.length);
    CCharPointer elems = JNIUtil.GetByteArrayElements(env, res, WordFactory.nullPointer());
    try {
        CTypeConversion.asByteBuffer(elems, serialized.length).put(serialized);
    } finally {
        JNIUtil.ReleaseByteArrayElements(env, res, elems, JNI.JArray.MODE_WRITE_RELEASE);
    }
    return res;
}
Also used : JNI(org.graalvm.jniutils.JNI) CCharPointer(org.graalvm.nativeimage.c.type.CCharPointer)

Aggregations

JNI (org.graalvm.jniutils.JNI)4 CCharPointer (org.graalvm.nativeimage.c.type.CCharPointer)3 Annotation (java.lang.annotation.Annotation)1 Method (java.lang.reflect.Method)1 Type (java.lang.reflect.Type)1 ByteBuffer (java.nio.ByteBuffer)1 JNIEnv (org.graalvm.jniutils.JNI.JNIEnv)1 Platforms (org.graalvm.nativeimage.Platforms)1 CEntryPoint (org.graalvm.nativeimage.c.function.CEntryPoint)1 CTypeConversion (org.graalvm.nativeimage.c.type.CTypeConversion)1 Pointer (org.graalvm.word.Pointer)1