HotSpot and IBM's J9 behave a little different when verifying this class
Yuting Chen
chenyt.cs.sjtu at gmail.com
Thu Apr 13 21:48:59 UTC 2017
I recently found an interesting class. Hope that I can get answers here.
The bytecode is shown as follows. Hotspot can catch some
inconsistencies here (Reason: Current frame's flags are not assignable
to stack map frame's), while J9 cannot.
I thought J9 was wrong until I went into HotSpot's source code and saw
some comments in share/vm/classfile/verifier.cpp. It says that the
verifier "Return TRUE if all code paths starting with start_bc_offset
end in bytecode athrow or loop" (a comment before bool
ClassVerifier::ends_in_athrow(u4 start_bc_offset)). Clearly the paths
in Vector1(int, int) end in athrow, and the verifier fails.
Can anyone explain the reason why the class still cannot pass the
verification, and which verifier needs to be fixed.
****************
public class Vector1 extends java.util.AbstractList
minor version: 0
major version: 52
flags: ACC_PUBLIC, ACC_SUPER
Constant pool:
#1 = Utf8 Vector1
#2 = Class #1 // Vector1
#3 = Utf8 java/util/AbstractList
#4 = Class #3 // java/util/AbstractList
#5 = Utf8 <init>
#6 = Utf8 (II)V
#7 = Utf8 ()V
#8 = NameAndType #5:#7 // "<init>":()V
#9 = Methodref #4.#8 // java/util/AbstractList."<init>":()V
#10 = Utf8 java/lang/Exception
#11 = Class #10 // java/lang/Exception
#12 = Methodref #11.#8 // java/lang/Exception."<init>":()V
#13 = Utf8 main
#14 = Utf8 ([Ljava/lang/String;)V
#15 = NameAndType #5:#6 // "<init>":(II)V
#16 = Methodref #2.#15 // Vector1."<init>":(II)V
#17 = Utf8 Code
#18 = Utf8 StackMapTable
{
public Vector1(int, int);
descriptor: (II)V
flags: ACC_PUBLIC
Code:
stack=2, locals=3, args_size=3
0: iload_1
1: iflt 11
4: aload_0
5: invokespecial #9 // Method
java/util/AbstractList."<init>":()V
8: goto 11
11: new #11 // class java/lang/Exception
14: dup
15: invokespecial #12 // Method
java/lang/Exception."<init>":()V
18: athrow
StackMapTable: number_of_entries = 1
frame_type = 255 /* full_frame */
offset_delta = 11
locals = [ top, int, int ]
stack = []
public static void main(java.lang.String[]);
descriptor: ([Ljava/lang/String;)V
flags: ACC_PUBLIC, ACC_STATIC
Code:
stack=3, locals=1, args_size=1
0: new #2 // class Vector1
3: bipush 10
5: iconst_0
6: invokespecial #16 // Method "<init>":(II)V
9: return
}
HotSpot reports the next verifyerror, while J9 does not:
Exception in thread "main" java.lang.VerifyError: Inconsistent
stackmap frames at branch target 11
Exception Details:
Location:
Vector1.<init>(II)V @11: new
Reason:
Current frame's flags are not assignable to stack map frame's.
Current Frame:
bci: @1
flags: { flagThisUninit }
locals: { uninitializedThis, integer, integer }
stack: { integer }
Stackmap Frame:
bci: @11
flags: { }
locals: { top, integer, integer }
stack: { }
Bytecode:
0000000: 1b9b 000a 2ab7 0009 a700 03bb 000b 59b7
0000010: 000c bf
Stackmap Table:
full_frame(@11,{Top,Integer,Integer},{})
More information about the hotspot-dev
mailing list