-
Bug
-
Resolution: Fixed
-
P4
-
8
Method handle resolution is not specified to perform checks of ACC_STATIC flag of the target field or method. Yet, HotSpot performs checks as follows:
- If method handle kind is one of REF_getField, REF_putField, REF_invokeVirtual, REF_invokeSpecial or REF_invokeInterface and the referenced field or method IS static then IllegalAccessError is thrown.
- If method handle kind is one of REF_getStatic, REF_putStatic or REF_invokeStatic and the referenced field or method IS NOT static then IllegalAccessError is thrown.
These rules are akin to ACC_STATIC checks in the corresponding instructions throwing IncompatibleClassChangeError.
Note that there is no need for the check for REF_newInvokeSpecial because it cannot refer to a static method <init>:()V due to the following restrictions:
- JVMS 4.4.8 only permits method of a class (not an interface) named <init> to be referenced by REF_newInvokeSpecial.
- JVMS 4.4.2 only permits CONSTANT_Methodref_info to refer method <init> if it has a return type void.
- JVMS 2.9 (of version presented inJDK-8122940) defines all methods <init>:()V declared in a class (not interface) to be instance initialization methods.
- JVMS 4.6 prohibits setting ACC_STATIC for instance initialization methods.
Example:
public class StaticTest version 52:0 {
public static Method main:"([Ljava/lang/String;)V" stack 10 locals 1 {
// Each ldc instruction throws IllegalAccessError
ldc MethodHandle REF_getField:staticF:I;
ldc MethodHandle REF_putField:staticF:I;
ldc MethodHandle REF_getStatic:f:I;
ldc MethodHandle REF_putStatic:f:I;
ldc MethodHandle REF_invokeVirtual:staticM:"()V";
ldc MethodHandle REF_invokeSpecial:staticM:"()V";
ldc MethodHandle REF_invokeStatic:m:"()V";
ldc MethodHandle REF_invokeInterface:Intf.staticIntfM:"()V";
return;
}
public Field f:I;
public static Field staticF:I;
public Method m:"()V" stack 0 locals 1 { return; }
public static Method staticM:"()V" stack 0 locals 1 { return; }
}
interface Intf version 52:0 {
public static Method staticIntfM:"()V" stack 0 locals 1 { return; }
}
- If method handle kind is one of REF_getField, REF_putField, REF_invokeVirtual, REF_invokeSpecial or REF_invokeInterface and the referenced field or method IS static then IllegalAccessError is thrown.
- If method handle kind is one of REF_getStatic, REF_putStatic or REF_invokeStatic and the referenced field or method IS NOT static then IllegalAccessError is thrown.
These rules are akin to ACC_STATIC checks in the corresponding instructions throwing IncompatibleClassChangeError.
Note that there is no need for the check for REF_newInvokeSpecial because it cannot refer to a static method <init>:()V due to the following restrictions:
- JVMS 4.4.8 only permits method of a class (not an interface) named <init> to be referenced by REF_newInvokeSpecial.
- JVMS 4.4.2 only permits CONSTANT_Methodref_info to refer method <init> if it has a return type void.
- JVMS 2.9 (of version presented in
- JVMS 4.6 prohibits setting ACC_STATIC for instance initialization methods.
Example:
public class StaticTest version 52:0 {
public static Method main:"([Ljava/lang/String;)V" stack 10 locals 1 {
// Each ldc instruction throws IllegalAccessError
ldc MethodHandle REF_getField:staticF:I;
ldc MethodHandle REF_putField:staticF:I;
ldc MethodHandle REF_getStatic:f:I;
ldc MethodHandle REF_putStatic:f:I;
ldc MethodHandle REF_invokeVirtual:staticM:"()V";
ldc MethodHandle REF_invokeSpecial:staticM:"()V";
ldc MethodHandle REF_invokeStatic:m:"()V";
ldc MethodHandle REF_invokeInterface:Intf.staticIntfM:"()V";
return;
}
public Field f:I;
public static Field staticF:I;
public Method m:"()V" stack 0 locals 1 { return; }
public static Method staticM:"()V" stack 0 locals 1 { return; }
}
interface Intf version 52:0 {
public static Method staticIntfM:"()V" stack 0 locals 1 { return; }
}
- relates to
-
JDK-8081349 5.4.3.5: Clarify that method handle resolution is protected-aware
-
- Closed
-
-
JDK-8138883 5.4.3.5: Clarify that method handle resolution of REF_invokeInterface is private-aware
-
- Closed
-
-
JDK-8138578 MethodHandles.Lookup.findSpecial() Javadoc fails to consider static methods
-
- Closed
-