--- old/src/share/vm/classfile/verifier.hpp 2017-09-07 12:10:53.745714468 -0400 +++ new/src/share/vm/classfile/verifier.hpp 2017-09-07 12:10:52.596868743 -0400 @@ -33,6 +33,10 @@ #include "utilities/exceptions.hpp" #include "utilities/growableArray.hpp" +// For bit tests involving JVM_CONSTANT_Value during verification, +// define a "safe" number to avoid integer overflow of types +#define SAFE_JVM_CONSTANT_Value JVM_CONSTANT_ExternalMax + // The verifier class class Verifier : AllStatic { public: @@ -40,7 +44,9 @@ STRICTER_ACCESS_CTRL_CHECK_VERSION = 49, STACKMAP_ATTRIBUTE_MAJOR_VERSION = 50, INVOKEDYNAMIC_MAJOR_VERSION = 51, - NO_RELAX_ACCESS_CTRL_CHECK_VERSION = 52 + NO_RELAX_ACCESS_CTRL_CHECK_VERSION = 52, + VALUETYPE_MAJOR_VERSION = 53, + VALUETYPE_MINOR_VERSION = 1 }; typedef enum { ThrowException, NoException } Mode; @@ -271,7 +277,12 @@ VerificationType cp_ref_index_to_type( int index, const constantPoolHandle& cp, TRAPS) { - return cp_index_to_type(cp->klass_ref_index_at(index), cp, THREAD); + return cp_index_to_reference_type(cp->klass_ref_index_at(index), cp, THREAD); + } + + VerificationType cp_value_index_to_type( + int index, const constantPoolHandle& cp, TRAPS) { + return cp_index_to_valuetype(cp->klass_ref_index_at(index), cp, THREAD); } bool is_protected_access( @@ -282,6 +293,8 @@ void verify_cp_type(u2 bci, int index, const constantPoolHandle& cp, unsigned int types, TRAPS); void verify_cp_class_type(u2 bci, int index, const constantPoolHandle& cp, TRAPS); + void verify_cp_value_type(u2 bci, int index, const constantPoolHandle& cp, TRAPS); + void verify_cp_class_or_value_type(u2 bci, int index, const constantPoolHandle& cp, TRAPS); u2 verify_stackmap_table( u2 stackmap_index, u2 bci, StackMapFrame* current_frame, @@ -303,6 +316,10 @@ RawBytecodeStream* bcs, StackMapFrame* current_frame, const constantPoolHandle& cp, bool allow_arrays, TRAPS); + void verify_vwithfield( + RawBytecodeStream* bcs, StackMapFrame* current_frame, + const constantPoolHandle& cp, TRAPS); + void verify_invoke_init( RawBytecodeStream* bcs, u2 ref_index, VerificationType ref_class_type, StackMapFrame* current_frame, u4 code_length, bool in_try_block, @@ -337,16 +354,19 @@ void verify_fload (u2 index, StackMapFrame* current_frame, TRAPS); void verify_dload (u2 index, StackMapFrame* current_frame, TRAPS); void verify_aload (u2 index, StackMapFrame* current_frame, TRAPS); + void verify_vload (u2 index, StackMapFrame* current_frame, TRAPS); void verify_istore(u2 index, StackMapFrame* current_frame, TRAPS); void verify_lstore(u2 index, StackMapFrame* current_frame, TRAPS); void verify_fstore(u2 index, StackMapFrame* current_frame, TRAPS); void verify_dstore(u2 index, StackMapFrame* current_frame, TRAPS); void verify_astore(u2 index, StackMapFrame* current_frame, TRAPS); + void verify_vstore(u2 index, StackMapFrame* current_frame, TRAPS); void verify_iinc (u2 index, StackMapFrame* current_frame, TRAPS); bool name_in_supers(Symbol* ref_name, InstanceKlass* current); VerificationType object_type() const; + VerificationType __value_type() const; InstanceKlass* _klass; // the class being verified methodHandle _method; // current method being verified @@ -407,10 +427,14 @@ int change_sig_to_verificationType( SignatureStream* sig_type, VerificationType* inference_type, TRAPS); - VerificationType cp_index_to_type(int index, const constantPoolHandle& cp, TRAPS) { + VerificationType cp_index_to_reference_type(int index, const constantPoolHandle& cp, TRAPS) { return VerificationType::reference_type(cp->klass_name_at(index)); } + VerificationType cp_index_to_valuetype(int index, const constantPoolHandle& cp, TRAPS) { + return VerificationType::valuetype_type(cp->klass_name_at(index)); + } + // Keep a list of temporary symbols created during verification because // their reference counts need to be decremented when the verifier object // goes out of scope. Since these symbols escape the scope in which they're @@ -427,6 +451,7 @@ } TypeOrigin ref_ctx(const char* str, TRAPS); + TypeOrigin valuetype_ctx(const char* str, TRAPS); }; @@ -436,13 +461,14 @@ switch (bt) { case T_OBJECT: case T_ARRAY: + case T_VALUETYPE: { Symbol* name = sig_type->as_symbol(CHECK_0); // Create another symbol to save as signature stream unreferences this symbol. Symbol* name_copy = create_temporary_symbol(name); assert(name_copy == name, "symbols don't match"); - *inference_type = - VerificationType::reference_type(name_copy); + *inference_type = ((bt == T_VALUETYPE) ? VerificationType::valuetype_type(name_copy) : + VerificationType::reference_type(name_copy)); return 1; } case T_LONG: