Mercurial > hg > graal-compiler
diff src/share/vm/classfile/classFileParser.cpp @ 938:b37c246bf7ce
6861660: OopMapBlock count/size confusion
Reviewed-by: tonyp, iveresov
author | jcoomes |
---|---|
date | Tue, 11 Aug 2009 15:37:23 -0700 |
parents | 494244ae0171 |
children | 9eebd3ac74cf |
line wrap: on
line diff
--- a/src/share/vm/classfile/classFileParser.cpp Mon Aug 24 13:52:42 2009 -0700 +++ b/src/share/vm/classfile/classFileParser.cpp Tue Aug 11 15:37:23 2009 -0700 @@ -2924,12 +2924,12 @@ // Prepare list of oops for oop maps generation. u2* nonstatic_oop_offsets; - u2* nonstatic_oop_length; + u2* nonstatic_oop_counts; int nonstatic_oop_map_count = 0; nonstatic_oop_offsets = NEW_RESOURCE_ARRAY_IN_THREAD( THREAD, u2, nonstatic_oop_count+1); - nonstatic_oop_length = NEW_RESOURCE_ARRAY_IN_THREAD( + nonstatic_oop_counts = NEW_RESOURCE_ARRAY_IN_THREAD( THREAD, u2, nonstatic_oop_count+1); // Add fake fields for java.lang.Class instances (also see above). @@ -2939,7 +2939,7 @@ nonstatic_oop_offsets[0] = (u2)first_nonstatic_field_offset; int fake_oop_count = (( next_nonstatic_field_offset - first_nonstatic_field_offset ) / heapOopSize); - nonstatic_oop_length [0] = (u2)fake_oop_count; + nonstatic_oop_counts [0] = (u2)fake_oop_count; nonstatic_oop_map_count = 1; nonstatic_oop_count -= fake_oop_count; first_nonstatic_oop_offset = first_nonstatic_field_offset; @@ -3119,13 +3119,13 @@ // Update oop maps if( nonstatic_oop_map_count > 0 && nonstatic_oop_offsets[nonstatic_oop_map_count - 1] == - (u2)(real_offset - nonstatic_oop_length[nonstatic_oop_map_count - 1] * heapOopSize) ) { + (u2)(real_offset - nonstatic_oop_counts[nonstatic_oop_map_count - 1] * heapOopSize) ) { // Extend current oop map - nonstatic_oop_length[nonstatic_oop_map_count - 1] += 1; + nonstatic_oop_counts[nonstatic_oop_map_count - 1] += 1; } else { // Create new oop map nonstatic_oop_offsets[nonstatic_oop_map_count] = (u2)real_offset; - nonstatic_oop_length [nonstatic_oop_map_count] = 1; + nonstatic_oop_counts [nonstatic_oop_map_count] = 1; nonstatic_oop_map_count += 1; if( first_nonstatic_oop_offset == 0 ) { // Undefined first_nonstatic_oop_offset = real_offset; @@ -3182,8 +3182,10 @@ assert(instance_size == align_object_size(align_size_up((instanceOopDesc::base_offset_in_bytes() + nonstatic_field_size*heapOopSize), wordSize) / wordSize), "consistent layout helper value"); - // Size of non-static oop map blocks (in words) allocated at end of klass - int nonstatic_oop_map_size = compute_oop_map_size(super_klass, nonstatic_oop_map_count, first_nonstatic_oop_offset); + // Number of non-static oop map blocks allocated at end of klass. + int total_oop_map_count = compute_oop_map_count(super_klass, + nonstatic_oop_map_count, + first_nonstatic_oop_offset); // Compute reference type ReferenceType rt; @@ -3196,12 +3198,13 @@ // We can now create the basic klassOop for this klass klassOop ik = oopFactory::new_instanceKlass( vtable_size, itable_size, - static_field_size, nonstatic_oop_map_size, + static_field_size, total_oop_map_count, rt, CHECK_(nullHandle)); instanceKlassHandle this_klass (THREAD, ik); - assert(this_klass->static_field_size() == static_field_size && - this_klass->nonstatic_oop_map_size() == nonstatic_oop_map_size, "sanity check"); + assert(this_klass->static_field_size() == static_field_size, "sanity"); + assert(this_klass->nonstatic_oop_map_count() == total_oop_map_count, + "sanity"); // Fill in information already parsed this_klass->set_access_flags(access_flags); @@ -3282,7 +3285,7 @@ klassItable::setup_itable_offset_table(this_klass); // Do final class setup - fill_oop_maps(this_klass, nonstatic_oop_map_count, nonstatic_oop_offsets, nonstatic_oop_length); + fill_oop_maps(this_klass, nonstatic_oop_map_count, nonstatic_oop_offsets, nonstatic_oop_counts); set_precomputed_flags(this_klass); @@ -3375,66 +3378,71 @@ } -int ClassFileParser::compute_oop_map_size(instanceKlassHandle super, int nonstatic_oop_map_count, int first_nonstatic_oop_offset) { - int map_size = super.is_null() ? 0 : super->nonstatic_oop_map_size(); +int ClassFileParser::compute_oop_map_count(instanceKlassHandle super, + int nonstatic_oop_map_count, + int first_nonstatic_oop_offset) { + int map_count = super.is_null() ? 0 : super->nonstatic_oop_map_count(); if (nonstatic_oop_map_count > 0) { // We have oops to add to map - if (map_size == 0) { - map_size = nonstatic_oop_map_count; + if (map_count == 0) { + map_count = nonstatic_oop_map_count; } else { - // Check whether we should add a new map block or whether the last one can be extended - OopMapBlock* first_map = super->start_of_nonstatic_oop_maps(); - OopMapBlock* last_map = first_map + map_size - 1; - - int next_offset = last_map->offset() + (last_map->length() * heapOopSize); + // Check whether we should add a new map block or whether the last one can + // be extended + OopMapBlock* const first_map = super->start_of_nonstatic_oop_maps(); + OopMapBlock* const last_map = first_map + map_count - 1; + + int next_offset = last_map->offset() + last_map->count() * heapOopSize; if (next_offset == first_nonstatic_oop_offset) { // There is no gap bettwen superklass's last oop field and first // local oop field, merge maps. nonstatic_oop_map_count -= 1; } else { // Superklass didn't end with a oop field, add extra maps - assert(next_offset<first_nonstatic_oop_offset, "just checking"); + assert(next_offset < first_nonstatic_oop_offset, "just checking"); } - map_size += nonstatic_oop_map_count; + map_count += nonstatic_oop_map_count; } } - return map_size; + return map_count; } void ClassFileParser::fill_oop_maps(instanceKlassHandle k, - int nonstatic_oop_map_count, - u2* nonstatic_oop_offsets, u2* nonstatic_oop_length) { + int nonstatic_oop_map_count, + u2* nonstatic_oop_offsets, + u2* nonstatic_oop_counts) { OopMapBlock* this_oop_map = k->start_of_nonstatic_oop_maps(); - OopMapBlock* last_oop_map = this_oop_map + k->nonstatic_oop_map_size(); - instanceKlass* super = k->superklass(); - if (super != NULL) { - int super_oop_map_size = super->nonstatic_oop_map_size(); + const instanceKlass* const super = k->superklass(); + const int super_count = super != NULL ? super->nonstatic_oop_map_count() : 0; + if (super_count > 0) { + // Copy maps from superklass OopMapBlock* super_oop_map = super->start_of_nonstatic_oop_maps(); - // Copy maps from superklass - while (super_oop_map_size-- > 0) { + for (int i = 0; i < super_count; ++i) { *this_oop_map++ = *super_oop_map++; } } + if (nonstatic_oop_map_count > 0) { - if (this_oop_map + nonstatic_oop_map_count > last_oop_map) { - // Calculated in compute_oop_map_size() number of oop maps is less then - // collected oop maps since there is no gap between superklass's last oop - // field and first local oop field. Extend the last oop map copied + if (super_count + nonstatic_oop_map_count > k->nonstatic_oop_map_count()) { + // The counts differ because there is no gap between superklass's last oop + // field and the first local oop field. Extend the last oop map copied // from the superklass instead of creating new one. nonstatic_oop_map_count--; nonstatic_oop_offsets++; this_oop_map--; - this_oop_map->set_length(this_oop_map->length() + *nonstatic_oop_length++); + this_oop_map->set_count(this_oop_map->count() + *nonstatic_oop_counts++); this_oop_map++; } - assert((this_oop_map + nonstatic_oop_map_count) == last_oop_map, "just checking"); + // Add new map blocks, fill them while (nonstatic_oop_map_count-- > 0) { this_oop_map->set_offset(*nonstatic_oop_offsets++); - this_oop_map->set_length(*nonstatic_oop_length++); + this_oop_map->set_count(*nonstatic_oop_counts++); this_oop_map++; } + assert(k->start_of_nonstatic_oop_maps() + k->nonstatic_oop_map_count() == + this_oop_map, "sanity"); } }