API Updates: 8191116: [Nestmates] Update core reflection, MethodHandle and varhandle APIs to allow for nestmate access

David Holmes david.holmes at oracle.com
Tue Jan 30 09:55:23 UTC 2018


I've gone through the API specifications for core reflection, 
MethodHandles and VarHandles to see what changes are needed to 
accommodate nestmates and the related invocation rule changes. Turns out 
there is very little needed and most of what there is is non-normative, 
just correcting or clarifying particular things. For VarHandle nothing 
is needed as it defers all access checking to MethodHandle.Lookup.

Bug: https://bugs.openjdk.java.net/browse/JDK-8191116

Webrev: http://cr.openjdk.java.net/~dholmes/8191116/webrev/


      Core reflection changes:

These are minimal as core reflection already expresses all access 
control in terms of "Java language access control" which already allows 
for nestmate access.

- java/lang/reflect/AccessibleObject.java

   * <p> Java language access control prevents use of private members outside
- * their class; package access members outside their package; protected members
+ * their top-level class; package access members outside their package; protected members

This corrects the definition of private access in the Java language.

- java/lang/reflect/Method.java

   * using dynamic method lookup as documented in The Java Language
- * Specification, Second Edition, section 15.12.4.4; in particular,
- * overriding based on the runtime type of the target object will occur.
+ * Specification, section 15.12.4.4; in particular,
+ * overriding based on the runtime type of the target object may occur.

Removed unnecessary reference to "Second Edition". Changed 'will occur' 
to 'may occur' to account for the different forms of invocation that may 
apply.


      MethodHandle API Changes:

- java/lang/invoke/MethodHandle.java

   * A non-virtual method handle to a specific virtual method implementation
   * can also be created.  These do not perform virtual lookup based on
   * receiver type.  Such a method handle simulates the effect of
- * an {@code invokespecial} instruction to the same method.
+ * an {@code invokespecial} instruction to the same non-private method;
+ * or an {@code invokevirtual} or {@code invokeinterface} instruction to the
+ * same private method (as applicable).

I tried to clarify that non-virtual invocations are not limited to 
invokespecial - as private invocations via invokevirtual or 
invokeinterface are also non-virtual.

- java/lang/invoke/MethodHandles.java

       * <p>
-     * In some cases, access between nested classes is obtained by the Java compiler by creating
-     * an wrapper method to access a private method of another class
-     * in the same top-level declaration.
+     * Since JDK 11 the relationship between nested types can be expressed directly through the
+     * {@code NestHost} and {@code NestMembers} attributes.
+     * (See the Java Virtual Machine Specification, sections 4.7.28 and 4.7.29.)
+     * In that case, the lookup class has direct access to private members of all its nestmates, and
+     * that is true of the associated {@code Lookup} object as well.
+     * Otherwise, access between nested classes is obtained by the Java compiler creating
+     * a wrapper method to access a private method of another class in the same nest.
       * For example, a nested class {@code C.D}

Updated the nested classes description to cover legacy approach and new 
nestmate approach.

-     * {@code C.E} would be unable to those private members.
+     * {@code C.E} would be unable to access those private members.

Fixed typo: "access" was missing.

       * <em>Discussion of private access:</em>
       * We say that a lookup has <em>private access</em>
       * if its {@linkplain #lookupModes lookup modes}
-     * include the possibility of accessing {@code private} members.
+     * include the possibility of accessing {@code private} members
+     * (which includes the private members of nestmates).
       * As documented in the relevant methods elsewhere,
       * only lookups with private access possess the following capabilities:
       * <ul style="font-size:smaller;">
-     * <li>access private fields, methods, and constructors of the lookup class
+     * <li>access private fields, methods, and constructors of the lookup class and its nestmates

Clarify that private access includes nestmate access.

-     *  access all members of the caller's class, all public types in the caller's module,
+     *  access all members of the caller's class and nestmates, all public types in the caller's module,

Ditto.

       * When called, the handle will treat the first argument as a receiver
-     * and dispatch on the receiver's type to determine which method
+     * and, for non-private methods, dispatch on the receiver's type to determine which method
       * implementation to enter.
+     * For private methods the named method in {@code refc} will be invoked on the receiver.

Clarify dispatch process for private versus non-private.

       * @throws IllegalAccessException if access checking fails,
       *                                or if the method is {@code static},
-     *                                or if the method is {@code private} method of interface,

This is the only actual spec change - it's no longer illegal for 
findVirtual to be used to find a private interface method.

Thanks,

David



More information about the valhalla-spec-observers mailing list