Mercurial > hg > truffle
comparison src/share/vm/classfile/classFileParser.cpp @ 7983:24a91505f9d5
8006949: Update hotspot for MethodParameters format change
8006907: Hotspot should reject classfiles with multiple MethodParameters attributes
Summary: Update to Hotspot's processing of MethodParameters attributes in classfiles
Reviewed-by: coleenp, jrose
author | emc |
---|---|
date | Mon, 04 Feb 2013 13:05:32 -0500 |
parents | 22ead76da3f4 |
children | 927a311d00f9 |
comparison
equal
deleted
inserted
replaced
7981:ce5467120c84 | 7983:24a91505f9d5 |
---|---|
1945 u2** localvariable_table_start; | 1945 u2** localvariable_table_start; |
1946 u2* localvariable_type_table_length; | 1946 u2* localvariable_type_table_length; |
1947 u2** localvariable_type_table_start; | 1947 u2** localvariable_type_table_start; |
1948 u2 method_parameters_length = 0; | 1948 u2 method_parameters_length = 0; |
1949 u1* method_parameters_data = NULL; | 1949 u1* method_parameters_data = NULL; |
1950 bool method_parameters_seen = false; | |
1951 bool method_parameters_four_byte_flags; | |
1950 bool parsed_code_attribute = false; | 1952 bool parsed_code_attribute = false; |
1951 bool parsed_checked_exceptions_attribute = false; | 1953 bool parsed_checked_exceptions_attribute = false; |
1952 bool parsed_stackmap_attribute = false; | 1954 bool parsed_stackmap_attribute = false; |
1953 // stackmap attribute - JDK1.5 | 1955 // stackmap attribute - JDK1.5 |
1954 Array<u1>* stackmap_data = NULL; | 1956 Array<u1>* stackmap_data = NULL; |
2155 checked_exceptions_start = | 2157 checked_exceptions_start = |
2156 parse_checked_exceptions(&checked_exceptions_length, | 2158 parse_checked_exceptions(&checked_exceptions_length, |
2157 method_attribute_length, | 2159 method_attribute_length, |
2158 cp, CHECK_(nullHandle)); | 2160 cp, CHECK_(nullHandle)); |
2159 } else if (method_attribute_name == vmSymbols::tag_method_parameters()) { | 2161 } else if (method_attribute_name == vmSymbols::tag_method_parameters()) { |
2162 // reject multiple method parameters | |
2163 if (method_parameters_seen) { | |
2164 classfile_parse_error("Multiple MethodParameters attributes in class file %s", CHECK_(nullHandle)); | |
2165 } | |
2166 method_parameters_seen = true; | |
2160 method_parameters_length = cfs->get_u1_fast(); | 2167 method_parameters_length = cfs->get_u1_fast(); |
2161 // Track the actual size (note: this is written for clarity; a | 2168 // Track the actual size (note: this is written for clarity; a |
2162 // decent compiler will CSE and constant-fold this into a single | 2169 // decent compiler will CSE and constant-fold this into a single |
2163 // expression) | 2170 // expression) |
2164 u2 actual_size = 1; | 2171 // Use the attribute length to figure out the size of flags |
2172 if (method_attribute_length == (method_parameters_length * 6u) + 1u) { | |
2173 method_parameters_four_byte_flags = true; | |
2174 } else if (method_attribute_length == (method_parameters_length * 4u) + 1u) { | |
2175 method_parameters_four_byte_flags = false; | |
2176 } else { | |
2177 classfile_parse_error( | |
2178 "Invalid MethodParameters method attribute length %u in class file", | |
2179 method_attribute_length, CHECK_(nullHandle)); | |
2180 } | |
2165 method_parameters_data = cfs->get_u1_buffer(); | 2181 method_parameters_data = cfs->get_u1_buffer(); |
2166 actual_size += 2 * method_parameters_length; | |
2167 cfs->skip_u2_fast(method_parameters_length); | 2182 cfs->skip_u2_fast(method_parameters_length); |
2168 actual_size += 4 * method_parameters_length; | 2183 if (method_parameters_four_byte_flags) { |
2169 cfs->skip_u4_fast(method_parameters_length); | 2184 cfs->skip_u4_fast(method_parameters_length); |
2170 // Enforce attribute length | 2185 } else { |
2171 if (method_attribute_length != actual_size) { | 2186 cfs->skip_u2_fast(method_parameters_length); |
2172 classfile_parse_error( | |
2173 "Invalid MethodParameters method attribute length %u in class file %s", | |
2174 method_attribute_length, CHECK_(nullHandle)); | |
2175 } | 2187 } |
2176 // ignore this attribute if it cannot be reflected | 2188 // ignore this attribute if it cannot be reflected |
2177 if (!SystemDictionary::Parameter_klass_loaded()) | 2189 if (!SystemDictionary::Parameter_klass_loaded()) |
2178 method_parameters_length = 0; | 2190 method_parameters_length = 0; |
2179 } else if (method_attribute_name == vmSymbols::tag_synthetic()) { | 2191 } else if (method_attribute_name == vmSymbols::tag_synthetic()) { |
2314 } | 2326 } |
2315 | 2327 |
2316 // Copy method parameters | 2328 // Copy method parameters |
2317 if (method_parameters_length > 0) { | 2329 if (method_parameters_length > 0) { |
2318 MethodParametersElement* elem = m->constMethod()->method_parameters_start(); | 2330 MethodParametersElement* elem = m->constMethod()->method_parameters_start(); |
2319 for(int i = 0; i < method_parameters_length; i++) { | 2331 for (int i = 0; i < method_parameters_length; i++) { |
2320 elem[i].name_cp_index = | 2332 elem[i].name_cp_index = Bytes::get_Java_u2(method_parameters_data); |
2321 Bytes::get_Java_u2(method_parameters_data); | |
2322 method_parameters_data += 2; | 2333 method_parameters_data += 2; |
2323 u4 flags = Bytes::get_Java_u4(method_parameters_data); | 2334 if (method_parameters_four_byte_flags) { |
2324 // This caused an alignment fault on Sparc, if flags was a u4 | 2335 elem[i].flags = Bytes::get_Java_u4(method_parameters_data); |
2325 elem[i].flags_lo = extract_low_short_from_int(flags); | 2336 method_parameters_data += 4; |
2326 elem[i].flags_hi = extract_high_short_from_int(flags); | 2337 } else { |
2327 method_parameters_data += 4; | 2338 elem[i].flags = Bytes::get_Java_u2(method_parameters_data); |
2339 method_parameters_data += 2; | |
2340 } | |
2328 } | 2341 } |
2329 } | 2342 } |
2330 | 2343 |
2331 // Copy checked exceptions | 2344 // Copy checked exceptions |
2332 if (checked_exceptions_length > 0) { | 2345 if (checked_exceptions_length > 0) { |