Search in sources :

Example 1 with IllegalAccessLogger

use of jdk.internal.module.IllegalAccessLogger in project Bytecoder by mirkosertic.

the class MethodHandles method privateLookupIn.

/**
 * Returns a {@link Lookup lookup object} with full capabilities to emulate all
 * supported bytecode behaviors, including <a href="MethodHandles.Lookup.html#privacc">
 * private access</a>, on a target class.
 * This method checks that a caller, specified as a {@code Lookup} object, is allowed to
 * do <em>deep reflection</em> on the target class. If {@code m1} is the module containing
 * the {@link Lookup#lookupClass() lookup class}, and {@code m2} is the module containing
 * the target class, then this check ensures that
 * <ul>
 *     <li>{@code m1} {@link Module#canRead reads} {@code m2}.</li>
 *     <li>{@code m2} {@link Module#isOpen(String,Module) opens} the package containing
 *     the target class to at least {@code m1}.</li>
 *     <li>The lookup has the {@link Lookup#MODULE MODULE} lookup mode.</li>
 * </ul>
 * <p>
 * If there is a security manager, its {@code checkPermission} method is called to
 * check {@code ReflectPermission("suppressAccessChecks")}.
 * @apiNote The {@code MODULE} lookup mode serves to authenticate that the lookup object
 * was created by code in the caller module (or derived from a lookup object originally
 * created by the caller). A lookup object with the {@code MODULE} lookup mode can be
 * shared with trusted parties without giving away {@code PRIVATE} and {@code PACKAGE}
 * access to the caller.
 * @param targetClass the target class
 * @param lookup the caller lookup object
 * @return a lookup object for the target class, with private access
 * @throws IllegalArgumentException if {@code targetClass} is a primitve type or array class
 * @throws NullPointerException if {@code targetClass} or {@code caller} is {@code null}
 * @throws IllegalAccessException if the access check specified above fails
 * @throws SecurityException if denied by the security manager
 * @since 9
 * @spec JPMS
 * @see Lookup#dropLookupMode
 */
public static Lookup privateLookupIn(Class<?> targetClass, Lookup lookup) throws IllegalAccessException {
    SecurityManager sm = System.getSecurityManager();
    if (sm != null)
        sm.checkPermission(ACCESS_PERMISSION);
    if (targetClass.isPrimitive())
        throw new IllegalArgumentException(targetClass + " is a primitive class");
    if (targetClass.isArray())
        throw new IllegalArgumentException(targetClass + " is an array class");
    Module targetModule = targetClass.getModule();
    Module callerModule = lookup.lookupClass().getModule();
    if (!callerModule.canRead(targetModule))
        throw new IllegalAccessException(callerModule + " does not read " + targetModule);
    if (targetModule.isNamed()) {
        String pn = targetClass.getPackageName();
        assert pn.length() > 0 : "unnamed package cannot be in named module";
        if (!targetModule.isOpen(pn, callerModule))
            throw new IllegalAccessException(targetModule + " does not open " + pn + " to " + callerModule);
    }
    if ((lookup.lookupModes() & Lookup.MODULE) == 0)
        throw new IllegalAccessException("lookup does not have MODULE lookup mode");
    if (!callerModule.isNamed() && targetModule.isNamed()) {
        IllegalAccessLogger logger = IllegalAccessLogger.illegalAccessLogger();
        if (logger != null) {
            logger.logIfOpenedForIllegalAccess(lookup, targetClass);
        }
    }
    return new Lookup(targetClass);
}
Also used : IllegalAccessLogger(jdk.internal.module.IllegalAccessLogger) MethodHandleStatics.newIllegalArgumentException(java.lang.invoke.MethodHandleStatics.newIllegalArgumentException)

Example 2 with IllegalAccessLogger

use of jdk.internal.module.IllegalAccessLogger in project Bytecoder by mirkosertic.

the class AccessibleObject method logIfOpenedForIllegalAccess.

private void logIfOpenedForIllegalAccess(Class<?> caller, Class<?> declaringClass) {
    Module callerModule = caller.getModule();
    Module targetModule = declaringClass.getModule();
    // callerModule is null during early startup
    if (callerModule != null && !callerModule.isNamed() && targetModule.isNamed()) {
        IllegalAccessLogger logger = IllegalAccessLogger.illegalAccessLogger();
        if (logger != null) {
            logger.logIfOpenedForIllegalAccess(caller, declaringClass, this::toShortString);
        }
    }
}
Also used : IllegalAccessLogger(jdk.internal.module.IllegalAccessLogger)

Example 3 with IllegalAccessLogger

use of jdk.internal.module.IllegalAccessLogger in project Bytecoder by mirkosertic.

the class AccessibleObject method logIfExportedForIllegalAccess.

private void logIfExportedForIllegalAccess(Class<?> caller, Class<?> declaringClass) {
    Module callerModule = caller.getModule();
    Module targetModule = declaringClass.getModule();
    // callerModule is null during early startup
    if (callerModule != null && !callerModule.isNamed() && targetModule.isNamed()) {
        IllegalAccessLogger logger = IllegalAccessLogger.illegalAccessLogger();
        if (logger != null) {
            logger.logIfExportedForIllegalAccess(caller, declaringClass, this::toShortString);
        }
    }
}
Also used : IllegalAccessLogger(jdk.internal.module.IllegalAccessLogger)

Example 4 with IllegalAccessLogger

use of jdk.internal.module.IllegalAccessLogger in project Bytecoder by mirkosertic.

the class Module method implAddExportsOrOpens.

/**
 * Updates a module to export or open a module to another module.
 *
 * If {@code syncVM} is {@code true} then the VM is notified.
 */
private void implAddExportsOrOpens(String pn, Module other, boolean open, boolean syncVM) {
    Objects.requireNonNull(other);
    Objects.requireNonNull(pn);
    // all packages are open in unnamed, open, and automatic modules
    if (!isNamed() || descriptor.isOpen() || descriptor.isAutomatic())
        return;
    // check if the package is already exported/open to other
    if (implIsExportedOrOpen(pn, other, open)) {
        // if the package is exported/open for illegal access then we need
        // to record that it has also been exported/opened reflectively so
        // that the IllegalAccessLogger doesn't emit a warning.
        boolean needToAdd = false;
        if (!other.isNamed()) {
            IllegalAccessLogger l = IllegalAccessLogger.illegalAccessLogger();
            if (l != null) {
                if (open) {
                    needToAdd = l.isOpenForIllegalAccess(this, pn);
                } else {
                    needToAdd = l.isExportedForIllegalAccess(this, pn);
                }
            }
        }
        if (!needToAdd) {
            // nothing to do
            return;
        }
    }
    // can only export a package in the module
    if (!descriptor.packages().contains(pn)) {
        throw new IllegalArgumentException("package " + pn + " not in contents");
    }
    // update VM first, just in case it fails
    if (syncVM) {
        if (other == EVERYONE_MODULE) {
            addExportsToAll0(this, pn);
        } else if (other == ALL_UNNAMED_MODULE) {
            addExportsToAllUnnamed0(this, pn);
        } else {
            addExports0(this, pn, other);
        }
    }
    // add package name to exports if absent
    Map<String, Boolean> map = ReflectionData.exports.computeIfAbsent(this, other, (m1, m2) -> new ConcurrentHashMap<>());
    if (open) {
        // may need to promote from FALSE to TRUE
        map.put(pn, Boolean.TRUE);
    } else {
        map.putIfAbsent(pn, Boolean.FALSE);
    }
}
Also used : IllegalAccessLogger(jdk.internal.module.IllegalAccessLogger)

Aggregations

IllegalAccessLogger (jdk.internal.module.IllegalAccessLogger)4 MethodHandleStatics.newIllegalArgumentException (java.lang.invoke.MethodHandleStatics.newIllegalArgumentException)1