classFileParser.hpp revision 1472:c18cbe5936b8
1126878Strhodes/* 2126878Strhodes * Copyright (c) 1997, 2009, Oracle and/or its affiliates. All rights reserved. 3126878Strhodes * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4126878Strhodes * 5126878Strhodes * This code is free software; you can redistribute it and/or modify it 6126878Strhodes * under the terms of the GNU General Public License version 2 only, as 7126878Strhodes * published by the Free Software Foundation. 8126878Strhodes * 9126878Strhodes * This code is distributed in the hope that it will be useful, but WITHOUT 10126878Strhodes * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11126878Strhodes * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12126878Strhodes * version 2 for more details (a copy is included in the LICENSE file that 13126878Strhodes * accompanied this code). 14126878Strhodes * 15126878Strhodes * You should have received a copy of the GNU General Public License version 16126878Strhodes * 2 along with this work; if not, write to the Free Software Foundation, 17126878Strhodes * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18126878Strhodes * 19126878Strhodes * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20126878Strhodes * or visit www.oracle.com if you need additional information or have any 21126878Strhodes * questions. 22126878Strhodes * 23126878Strhodes */ 24233258Sglebius 25126878Strhodes// Parser for for .class files 26126878Strhodes// 27126878Strhodes// The bytes describing the class file structure is read from a Stream object 28126878Strhodes 29130420Sruclass ClassFileParser VALUE_OBJ_CLASS_SPEC { 30130420Sru private: 31130420Sru bool _need_verify; 32126878Strhodes bool _relax_verify; 33126878Strhodes u2 _major_version; 34126878Strhodes u2 _minor_version; 35126878Strhodes symbolHandle _class_name; 36126878Strhodes KlassHandle _host_klass; 37126878Strhodes GrowableArray<Handle>* _cp_patches; // overrides for CP entries 38126878Strhodes 39126878Strhodes bool _has_finalizer; 40126878Strhodes bool _has_empty_finalizer; 41126878Strhodes bool _has_vanilla_constructor; 42126878Strhodes 43126878Strhodes enum { fixed_buffer_size = 128 }; 44126878Strhodes u_char linenumbertable_buffer[fixed_buffer_size]; 45126878Strhodes 46126878Strhodes ClassFileStream* _stream; // Actual input stream 47126878Strhodes 48126878Strhodes enum { LegalClass, LegalField, LegalMethod }; // used to verify unqualified names 49126878Strhodes 50130420Sru // Accessors 51126878Strhodes ClassFileStream* stream() { return _stream; } 52126878Strhodes void set_stream(ClassFileStream* st) { _stream = st; } 53130420Sru 54126878Strhodes // Constant pool parsing 55126878Strhodes void parse_constant_pool_entries(constantPoolHandle cp, int length, TRAPS); 56130420Sru 57126878Strhodes constantPoolHandle parse_constant_pool(TRAPS); 58130420Sru 59126878Strhodes // Interface parsing 60126878Strhodes objArrayHandle parse_interfaces(constantPoolHandle cp, 61130420Sru int length, 62126878Strhodes Handle class_loader, 63180019Ssobomax Handle protection_domain, 64126878Strhodes symbolHandle class_name, 65180019Ssobomax TRAPS); 66126878Strhodes 67130420Sru // Field parsing 68130420Sru void parse_field_attributes(constantPoolHandle cp, u2 attributes_count, 69126878Strhodes bool is_static, u2 signature_index, 70126878Strhodes u2* constantvalue_index_addr, 71126878Strhodes bool* is_synthetic_addr, 72208649Sgordon u2* generic_signature_index_addr, 73208649Sgordon typeArrayHandle* field_annotations, TRAPS); 74208649Sgordon typeArrayHandle parse_fields(constantPoolHandle cp, bool is_interface, 75208649Sgordon struct FieldAllocationCount *fac, 76208649Sgordon objArrayHandle* fields_annotations, TRAPS); 77126878Strhodes 78126878Strhodes // Method parsing 79126878Strhodes methodHandle parse_method(constantPoolHandle cp, bool is_interface, 80126878Strhodes AccessFlags* promoted_flags, 81126878Strhodes typeArrayHandle* method_annotations, 82208649Sgordon typeArrayHandle* method_parameter_annotations, 83208649Sgordon typeArrayHandle* method_default_annotations, 84126878Strhodes TRAPS); 85126878Strhodes objArrayHandle parse_methods (constantPoolHandle cp, bool is_interface, 86126878Strhodes AccessFlags* promoted_flags, 87130420Sru bool* has_final_method, 88126878Strhodes objArrayOop* methods_annotations_oop, 89126878Strhodes objArrayOop* methods_parameter_annotations_oop, 90126878Strhodes objArrayOop* methods_default_annotations_oop, 91126878Strhodes TRAPS); 92126878Strhodes typeArrayHandle sort_methods (objArrayHandle methods, 93126878Strhodes objArrayHandle methods_annotations, 94126878Strhodes objArrayHandle methods_parameter_annotations, 95126878Strhodes objArrayHandle methods_default_annotations, 96126878Strhodes TRAPS); 97126878Strhodes typeArrayHandle parse_exception_table(u4 code_length, u4 exception_table_length, 98126878Strhodes constantPoolHandle cp, TRAPS); 99126878Strhodes void parse_linenumber_table( 100126878Strhodes u4 code_attribute_length, u4 code_length, 101126878Strhodes CompressedLineNumberWriteStream** write_stream, TRAPS); 102126878Strhodes u2* parse_localvariable_table(u4 code_length, u2 max_locals, u4 code_attribute_length, 103126878Strhodes constantPoolHandle cp, u2* localvariable_table_length, 104126878Strhodes bool isLVTT, TRAPS); 105126878Strhodes u2* parse_checked_exceptions(u2* checked_exceptions_length, u4 method_attribute_length, 106126878Strhodes constantPoolHandle cp, TRAPS); 107130420Sru void parse_type_array(u2 array_length, u4 code_length, u4* u1_index, u4* u2_index, 108126878Strhodes u1* u1_array, u2* u2_array, constantPoolHandle cp, TRAPS); 109126878Strhodes typeArrayOop parse_stackmap_table(u4 code_attribute_length, TRAPS); 110126878Strhodes 111126878Strhodes // Classfile attribute parsing 112126878Strhodes void parse_classfile_sourcefile_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS); 113126878Strhodes void parse_classfile_source_debug_extension_attribute(constantPoolHandle cp, 114126878Strhodes instanceKlassHandle k, int length, TRAPS); 115126878Strhodes u2 parse_classfile_inner_classes_attribute(constantPoolHandle cp, 116130420Sru instanceKlassHandle k, TRAPS); 117126878Strhodes void parse_classfile_attributes(constantPoolHandle cp, instanceKlassHandle k, TRAPS); 118126878Strhodes void parse_classfile_synthetic_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS); 119126878Strhodes void parse_classfile_signature_attribute(constantPoolHandle cp, instanceKlassHandle k, TRAPS); 120126878Strhodes 121126878Strhodes // Annotations handling 122126878Strhodes typeArrayHandle assemble_annotations(u1* runtime_visible_annotations, 123126878Strhodes int runtime_visible_annotations_length, 124126878Strhodes u1* runtime_invisible_annotations, 125126878Strhodes int runtime_invisible_annotations_length, TRAPS); 126126878Strhodes 127126878Strhodes // Final setup 128126878Strhodes unsigned int compute_oop_map_count(instanceKlassHandle super, 129130420Sru unsigned int nonstatic_oop_count, 130130420Sru int first_nonstatic_oop_offset); 131130420Sru void fill_oop_maps(instanceKlassHandle k, 132126878Strhodes unsigned int nonstatic_oop_map_count, 133233258Sglebius int* nonstatic_oop_offsets, 134126878Strhodes unsigned int* nonstatic_oop_counts); 135126878Strhodes void set_precomputed_flags(instanceKlassHandle k); 136126878Strhodes objArrayHandle compute_transitive_interfaces(instanceKlassHandle super, 137126878Strhodes objArrayHandle local_ifs, TRAPS); 138126878Strhodes 139126878Strhodes // Special handling for certain classes. 140126878Strhodes // Add the "discovered" field to java.lang.ref.Reference if 141126878Strhodes // it does not exist. 142126878Strhodes void java_lang_ref_Reference_fix_pre(typeArrayHandle* fields_ptr, 143126878Strhodes constantPoolHandle cp, FieldAllocationCount *fac_ptr, TRAPS); 144126878Strhodes // Adjust the field allocation counts for java.lang.Class to add 145130420Sru // fake fields. 146126878Strhodes void java_lang_Class_fix_pre(objArrayHandle* methods_ptr, 147130420Sru FieldAllocationCount *fac_ptr, TRAPS); 148126878Strhodes // Adjust the next_nonstatic_oop_offset to place the fake fields 149126878Strhodes // before any Java fields. 150126878Strhodes void java_lang_Class_fix_post(int* next_nonstatic_oop_offset); 151126878Strhodes // Adjust the field allocation counts for java.dyn.MethodHandle to add 152130420Sru // a fake address (void*) field. 153130420Sru void java_dyn_MethodHandle_fix_pre(constantPoolHandle cp, 154126878Strhodes typeArrayHandle* fields_ptr, 155126878Strhodes FieldAllocationCount *fac_ptr, TRAPS); 156126878Strhodes 157126878Strhodes // Format checker methods 158236805Sjoel void classfile_parse_error(const char* msg, TRAPS); 159236805Sjoel void classfile_parse_error(const char* msg, int index, TRAPS); 160236805Sjoel void classfile_parse_error(const char* msg, const char *name, TRAPS); 161236805Sjoel void classfile_parse_error(const char* msg, int index, const char *name, TRAPS); 162236805Sjoel inline void guarantee_property(bool b, const char* msg, TRAPS) { 163126878Strhodes if (!b) { classfile_parse_error(msg, CHECK); } 164236805Sjoel } 165236805Sjoel 166236805Sjoel inline void assert_property(bool b, const char* msg, TRAPS) { 167236805Sjoel#ifdef ASSERT 168236805Sjoel if (!b) { fatal(msg); } 169126878Strhodes#endif 170126878Strhodes } 171126878Strhodes 172126878Strhodes inline void check_property(bool property, const char* msg, int index, TRAPS) { 173126878Strhodes if (_need_verify) { 174126878Strhodes guarantee_property(property, msg, index, CHECK); 175126878Strhodes } else { 176126878Strhodes assert_property(property, msg, CHECK); 177126878Strhodes } 178126878Strhodes } 179126878Strhodes 180126878Strhodes inline void check_property(bool property, const char* msg, TRAPS) { 181126878Strhodes if (_need_verify) { 182126878Strhodes guarantee_property(property, msg, CHECK); 183126878Strhodes } else { 184126878Strhodes assert_property(property, msg, CHECK); 185126878Strhodes } 186126878Strhodes } 187126878Strhodes 188126878Strhodes inline void guarantee_property(bool b, const char* msg, int index, TRAPS) { 189126878Strhodes if (!b) { classfile_parse_error(msg, index, CHECK); } 190126878Strhodes } 191126878Strhodes inline void guarantee_property(bool b, const char* msg, const char *name, TRAPS) { 192126878Strhodes if (!b) { classfile_parse_error(msg, name, CHECK); } 193130420Sru } 194126878Strhodes inline void guarantee_property(bool b, const char* msg, int index, const char *name, TRAPS) { 195126878Strhodes if (!b) { classfile_parse_error(msg, index, name, CHECK); } 196126878Strhodes } 197126878Strhodes 198126878Strhodes bool is_supported_version(u2 major, u2 minor); 199126878Strhodes bool has_illegal_visibility(jint flags); 200130420Sru 201130420Sru void verify_constantvalue(int constantvalue_index, int signature_index, constantPoolHandle cp, TRAPS); 202130420Sru void verify_legal_utf8(const unsigned char* buffer, int length, TRAPS); 203126878Strhodes void verify_legal_class_name(symbolHandle name, TRAPS); 204130420Sru void verify_legal_field_name(symbolHandle name, TRAPS); 205130420Sru void verify_legal_method_name(symbolHandle name, TRAPS); 206126878Strhodes void verify_legal_field_signature(symbolHandle fieldname, symbolHandle signature, TRAPS); 207130420Sru int verify_legal_method_signature(symbolHandle methodname, symbolHandle signature, TRAPS); 208126878Strhodes void verify_legal_class_modifiers(jint flags, TRAPS); 209126878Strhodes void verify_legal_field_modifiers(jint flags, bool is_interface, TRAPS); 210126878Strhodes void verify_legal_method_modifiers(jint flags, bool is_interface, symbolHandle name, TRAPS); 211126878Strhodes bool verify_unqualified_name(char* name, unsigned int length, int type); 212130420Sru char* skip_over_field_name(char* name, bool slash_ok, unsigned int length); 213126878Strhodes char* skip_over_field_signature(char* signature, bool void_ok, unsigned int length, TRAPS); 214130420Sru 215126878Strhodes bool is_anonymous() { 216130420Sru assert(AnonymousClasses || _host_klass.is_null(), ""); 217126878Strhodes return _host_klass.not_null(); 218130420Sru } 219130420Sru bool has_cp_patch_at(int index) { 220126878Strhodes assert(AnonymousClasses, ""); 221130420Sru assert(index >= 0, "oob"); 222126878Strhodes return (_cp_patches != NULL 223126878Strhodes && index < _cp_patches->length() 224126878Strhodes && _cp_patches->adr_at(index)->not_null()); 225126878Strhodes } 226126878Strhodes Handle cp_patch_at(int index) { 227130420Sru assert(has_cp_patch_at(index), "oob"); 228130420Sru return _cp_patches->at(index); 229126878Strhodes } 230126878Strhodes Handle clear_cp_patch_at(int index) { 231130420Sru Handle patch = cp_patch_at(index); 232130420Sru _cp_patches->at_put(index, Handle()); 233130420Sru assert(!has_cp_patch_at(index), ""); 234126878Strhodes return patch; 235130420Sru } 236130420Sru void patch_constant_pool(constantPoolHandle cp, int index, Handle patch, TRAPS); 237130420Sru 238130420Sru // Wrapper for constantTag.is_klass_[or_]reference. 239130420Sru // In older versions of the VM, klassOops cannot sneak into early phases of 240130420Sru // constant pool construction, but in later versions they can. 241126878Strhodes // %%% Let's phase out the old is_klass_reference. 242126878Strhodes bool is_klass_reference(constantPoolHandle cp, int index) { 243130420Sru return ((LinkWellKnownClasses || AnonymousClasses) 244130420Sru ? cp->tag_at(index).is_klass_or_reference() 245130420Sru : cp->tag_at(index).is_klass_reference()); 246126878Strhodes } 247130420Sru 248126878Strhodes public: 249126878Strhodes // Constructor 250126878Strhodes ClassFileParser(ClassFileStream* st) { set_stream(st); } 251126878Strhodes 252126878Strhodes // Parse .class file and return new klassOop. The klassOop is not hooked up 253126878Strhodes // to the system dictionary or any other structures, so a .class file can 254126878Strhodes // be loaded several times if desired. 255130420Sru // The system dictionary hookup is done by the caller. 256126878Strhodes // 257126878Strhodes // "parsed_name" is updated by this method, and is the name found 258126878Strhodes // while parsing the stream. 259126878Strhodes instanceKlassHandle parseClassFile(symbolHandle name, 260126878Strhodes Handle class_loader, 261126878Strhodes Handle protection_domain, 262126878Strhodes symbolHandle& parsed_name, 263126878Strhodes bool verify, 264126878Strhodes TRAPS) { 265126878Strhodes KlassHandle no_host_klass; 266130420Sru return parseClassFile(name, class_loader, protection_domain, no_host_klass, NULL, parsed_name, verify, THREAD); 267126878Strhodes } 268126878Strhodes instanceKlassHandle parseClassFile(symbolHandle name, 269130420Sru Handle class_loader, 270126878Strhodes Handle protection_domain, 271126878Strhodes KlassHandle host_klass, 272126878Strhodes GrowableArray<Handle>* cp_patches, 273126878Strhodes symbolHandle& parsed_name, 274130420Sru bool verify, 275130043Sgad TRAPS); 276130043Sgad 277130420Sru // Verifier checks 278130420Sru static void check_super_class_access(instanceKlassHandle this_klass, TRAPS); 279130420Sru static void check_super_interface_access(instanceKlassHandle this_klass, TRAPS); 280130043Sgad static void check_final_method_override(instanceKlassHandle this_klass, TRAPS); 281173971Sremko static void check_illegal_static_method(instanceKlassHandle this_klass, TRAPS); 282130043Sgad}; 283130043Sgad