Mercurial > hg > truffle
comparison src/share/vm/classfile/classFileParser.cpp @ 974:26b774d693aa
Merge
author | acorn |
---|---|
date | Wed, 16 Sep 2009 09:10:57 -0400 |
parents | ad6585fd4087 9eebd3ac74cf |
children | 83c29a26f67c |
comparison
equal
deleted
inserted
replaced
973:ad6585fd4087 | 974:26b774d693aa |
---|---|
764 NONSTATIC_ALIGNED_DOUBLE | 764 NONSTATIC_ALIGNED_DOUBLE |
765 }; | 765 }; |
766 | 766 |
767 | 767 |
768 struct FieldAllocationCount { | 768 struct FieldAllocationCount { |
769 int static_oop_count; | 769 unsigned int static_oop_count; |
770 int static_byte_count; | 770 unsigned int static_byte_count; |
771 int static_short_count; | 771 unsigned int static_short_count; |
772 int static_word_count; | 772 unsigned int static_word_count; |
773 int static_double_count; | 773 unsigned int static_double_count; |
774 int nonstatic_oop_count; | 774 unsigned int nonstatic_oop_count; |
775 int nonstatic_byte_count; | 775 unsigned int nonstatic_byte_count; |
776 int nonstatic_short_count; | 776 unsigned int nonstatic_short_count; |
777 int nonstatic_word_count; | 777 unsigned int nonstatic_word_count; |
778 int nonstatic_double_count; | 778 unsigned int nonstatic_double_count; |
779 }; | 779 }; |
780 | 780 |
781 typeArrayHandle ClassFileParser::parse_fields(constantPoolHandle cp, bool is_interface, | 781 typeArrayHandle ClassFileParser::parse_fields(constantPoolHandle cp, bool is_interface, |
782 struct FieldAllocationCount *fac, | 782 struct FieldAllocationCount *fac, |
783 objArrayHandle* fields_annotations, TRAPS) { | 783 objArrayHandle* fields_annotations, TRAPS) { |
2907 && class_loader.is_null()) { | 2907 && class_loader.is_null()) { |
2908 java_lang_ref_Reference_fix_pre(&fields, cp, &fac, CHECK_(nullHandle)); | 2908 java_lang_ref_Reference_fix_pre(&fields, cp, &fac, CHECK_(nullHandle)); |
2909 } | 2909 } |
2910 // end of "discovered" field compactibility fix | 2910 // end of "discovered" field compactibility fix |
2911 | 2911 |
2912 int nonstatic_double_count = fac.nonstatic_double_count; | 2912 unsigned int nonstatic_double_count = fac.nonstatic_double_count; |
2913 int nonstatic_word_count = fac.nonstatic_word_count; | 2913 unsigned int nonstatic_word_count = fac.nonstatic_word_count; |
2914 int nonstatic_short_count = fac.nonstatic_short_count; | 2914 unsigned int nonstatic_short_count = fac.nonstatic_short_count; |
2915 int nonstatic_byte_count = fac.nonstatic_byte_count; | 2915 unsigned int nonstatic_byte_count = fac.nonstatic_byte_count; |
2916 int nonstatic_oop_count = fac.nonstatic_oop_count; | 2916 unsigned int nonstatic_oop_count = fac.nonstatic_oop_count; |
2917 | 2917 |
2918 bool super_has_nonstatic_fields = | 2918 bool super_has_nonstatic_fields = |
2919 (super_klass() != NULL && super_klass->has_nonstatic_fields()); | 2919 (super_klass() != NULL && super_klass->has_nonstatic_fields()); |
2920 bool has_nonstatic_fields = super_has_nonstatic_fields || | 2920 bool has_nonstatic_fields = super_has_nonstatic_fields || |
2921 ((nonstatic_double_count + nonstatic_word_count + | 2921 ((nonstatic_double_count + nonstatic_word_count + |
2922 nonstatic_short_count + nonstatic_byte_count + | 2922 nonstatic_short_count + nonstatic_byte_count + |
2923 nonstatic_oop_count) != 0); | 2923 nonstatic_oop_count) != 0); |
2924 | 2924 |
2925 | 2925 |
2926 // Prepare list of oops for oop maps generation. | 2926 // Prepare list of oops for oop map generation. |
2927 u2* nonstatic_oop_offsets; | 2927 int* nonstatic_oop_offsets; |
2928 u2* nonstatic_oop_length; | 2928 unsigned int* nonstatic_oop_counts; |
2929 int nonstatic_oop_map_count = 0; | 2929 unsigned int nonstatic_oop_map_count = 0; |
2930 | 2930 |
2931 nonstatic_oop_offsets = NEW_RESOURCE_ARRAY_IN_THREAD( | 2931 nonstatic_oop_offsets = NEW_RESOURCE_ARRAY_IN_THREAD( |
2932 THREAD, u2, nonstatic_oop_count+1); | 2932 THREAD, int, nonstatic_oop_count + 1); |
2933 nonstatic_oop_length = NEW_RESOURCE_ARRAY_IN_THREAD( | 2933 nonstatic_oop_counts = NEW_RESOURCE_ARRAY_IN_THREAD( |
2934 THREAD, u2, nonstatic_oop_count+1); | 2934 THREAD, unsigned int, nonstatic_oop_count + 1); |
2935 | 2935 |
2936 // Add fake fields for java.lang.Class instances (also see above). | 2936 // Add fake fields for java.lang.Class instances (also see above). |
2937 // FieldsAllocationStyle and CompactFields values will be reset to default. | 2937 // FieldsAllocationStyle and CompactFields values will be reset to default. |
2938 if(class_name() == vmSymbols::java_lang_Class() && class_loader.is_null()) { | 2938 if(class_name() == vmSymbols::java_lang_Class() && class_loader.is_null()) { |
2939 java_lang_Class_fix_post(&next_nonstatic_field_offset); | 2939 java_lang_Class_fix_post(&next_nonstatic_field_offset); |
2940 nonstatic_oop_offsets[0] = (u2)first_nonstatic_field_offset; | 2940 nonstatic_oop_offsets[0] = first_nonstatic_field_offset; |
2941 int fake_oop_count = (( next_nonstatic_field_offset - | 2941 const uint fake_oop_count = (next_nonstatic_field_offset - |
2942 first_nonstatic_field_offset ) / heapOopSize); | 2942 first_nonstatic_field_offset) / heapOopSize; |
2943 nonstatic_oop_length [0] = (u2)fake_oop_count; | 2943 nonstatic_oop_counts[0] = fake_oop_count; |
2944 nonstatic_oop_map_count = 1; | 2944 nonstatic_oop_map_count = 1; |
2945 nonstatic_oop_count -= fake_oop_count; | 2945 nonstatic_oop_count -= fake_oop_count; |
2946 first_nonstatic_oop_offset = first_nonstatic_field_offset; | 2946 first_nonstatic_oop_offset = first_nonstatic_field_offset; |
2947 } else { | 2947 } else { |
2948 first_nonstatic_oop_offset = 0; // will be set for first oop field | 2948 first_nonstatic_oop_offset = 0; // will be set for first oop field |
2949 } | 2949 } |
2950 | 2950 |
3118 next_nonstatic_oop_offset += heapOopSize; | 3118 next_nonstatic_oop_offset += heapOopSize; |
3119 } | 3119 } |
3120 // Update oop maps | 3120 // Update oop maps |
3121 if( nonstatic_oop_map_count > 0 && | 3121 if( nonstatic_oop_map_count > 0 && |
3122 nonstatic_oop_offsets[nonstatic_oop_map_count - 1] == | 3122 nonstatic_oop_offsets[nonstatic_oop_map_count - 1] == |
3123 (u2)(real_offset - nonstatic_oop_length[nonstatic_oop_map_count - 1] * heapOopSize) ) { | 3123 real_offset - |
3124 int(nonstatic_oop_counts[nonstatic_oop_map_count - 1]) * | |
3125 heapOopSize ) { | |
3124 // Extend current oop map | 3126 // Extend current oop map |
3125 nonstatic_oop_length[nonstatic_oop_map_count - 1] += 1; | 3127 nonstatic_oop_counts[nonstatic_oop_map_count - 1] += 1; |
3126 } else { | 3128 } else { |
3127 // Create new oop map | 3129 // Create new oop map |
3128 nonstatic_oop_offsets[nonstatic_oop_map_count] = (u2)real_offset; | 3130 nonstatic_oop_offsets[nonstatic_oop_map_count] = real_offset; |
3129 nonstatic_oop_length [nonstatic_oop_map_count] = 1; | 3131 nonstatic_oop_counts [nonstatic_oop_map_count] = 1; |
3130 nonstatic_oop_map_count += 1; | 3132 nonstatic_oop_map_count += 1; |
3131 if( first_nonstatic_oop_offset == 0 ) { // Undefined | 3133 if( first_nonstatic_oop_offset == 0 ) { // Undefined |
3132 first_nonstatic_oop_offset = real_offset; | 3134 first_nonstatic_oop_offset = real_offset; |
3133 } | 3135 } |
3134 } | 3136 } |
3181 next_nonstatic_type_offset = align_size_up(notaligned_offset, wordSize ); | 3183 next_nonstatic_type_offset = align_size_up(notaligned_offset, wordSize ); |
3182 instance_size = align_object_size(next_nonstatic_type_offset / wordSize); | 3184 instance_size = align_object_size(next_nonstatic_type_offset / wordSize); |
3183 | 3185 |
3184 assert(instance_size == align_object_size(align_size_up((instanceOopDesc::base_offset_in_bytes() + nonstatic_field_size*heapOopSize), wordSize) / wordSize), "consistent layout helper value"); | 3186 assert(instance_size == align_object_size(align_size_up((instanceOopDesc::base_offset_in_bytes() + nonstatic_field_size*heapOopSize), wordSize) / wordSize), "consistent layout helper value"); |
3185 | 3187 |
3186 // Size of non-static oop map blocks (in words) allocated at end of klass | 3188 // Number of non-static oop map blocks allocated at end of klass. |
3187 int nonstatic_oop_map_size = compute_oop_map_size(super_klass, nonstatic_oop_map_count, first_nonstatic_oop_offset); | 3189 const unsigned int total_oop_map_count = |
3190 compute_oop_map_count(super_klass, nonstatic_oop_map_count, | |
3191 first_nonstatic_oop_offset); | |
3188 | 3192 |
3189 // Compute reference type | 3193 // Compute reference type |
3190 ReferenceType rt; | 3194 ReferenceType rt; |
3191 if (super_klass() == NULL) { | 3195 if (super_klass() == NULL) { |
3192 rt = REF_NONE; | 3196 rt = REF_NONE; |
3193 } else { | 3197 } else { |
3194 rt = super_klass->reference_type(); | 3198 rt = super_klass->reference_type(); |
3195 } | 3199 } |
3196 | 3200 |
3197 // We can now create the basic klassOop for this klass | 3201 // We can now create the basic klassOop for this klass |
3198 klassOop ik = oopFactory::new_instanceKlass( | 3202 klassOop ik = oopFactory::new_instanceKlass(vtable_size, itable_size, |
3199 vtable_size, itable_size, | 3203 static_field_size, |
3200 static_field_size, nonstatic_oop_map_size, | 3204 total_oop_map_count, |
3201 rt, CHECK_(nullHandle)); | 3205 rt, CHECK_(nullHandle)); |
3202 instanceKlassHandle this_klass (THREAD, ik); | 3206 instanceKlassHandle this_klass (THREAD, ik); |
3203 | 3207 |
3204 assert(this_klass->static_field_size() == static_field_size && | 3208 assert(this_klass->static_field_size() == static_field_size, "sanity"); |
3205 this_klass->nonstatic_oop_map_size() == nonstatic_oop_map_size, "sanity check"); | 3209 assert(this_klass->nonstatic_oop_map_count() == total_oop_map_count, |
3210 "sanity"); | |
3206 | 3211 |
3207 // Fill in information already parsed | 3212 // Fill in information already parsed |
3208 this_klass->set_access_flags(access_flags); | 3213 this_klass->set_access_flags(access_flags); |
3209 if (verify) { | 3214 if (verify) { |
3210 this_klass->set_should_verify_class(); | 3215 this_klass->set_should_verify_class(); |
3286 | 3291 |
3287 // Initialize itable offset tables | 3292 // Initialize itable offset tables |
3288 klassItable::setup_itable_offset_table(this_klass); | 3293 klassItable::setup_itable_offset_table(this_klass); |
3289 | 3294 |
3290 // Do final class setup | 3295 // Do final class setup |
3291 fill_oop_maps(this_klass, nonstatic_oop_map_count, nonstatic_oop_offsets, nonstatic_oop_length); | 3296 fill_oop_maps(this_klass, nonstatic_oop_map_count, nonstatic_oop_offsets, nonstatic_oop_counts); |
3292 | 3297 |
3293 set_precomputed_flags(this_klass); | 3298 set_precomputed_flags(this_klass); |
3294 | 3299 |
3295 // reinitialize modifiers, using the InnerClasses attribute | 3300 // reinitialize modifiers, using the InnerClasses attribute |
3296 int computed_modifiers = this_klass->compute_modifier_flags(CHECK_(nullHandle)); | 3301 int computed_modifiers = this_klass->compute_modifier_flags(CHECK_(nullHandle)); |
3379 | 3384 |
3380 return this_klass; | 3385 return this_klass; |
3381 } | 3386 } |
3382 | 3387 |
3383 | 3388 |
3384 int ClassFileParser::compute_oop_map_size(instanceKlassHandle super, int nonstatic_oop_map_count, int first_nonstatic_oop_offset) { | 3389 unsigned int |
3385 int map_size = super.is_null() ? 0 : super->nonstatic_oop_map_size(); | 3390 ClassFileParser::compute_oop_map_count(instanceKlassHandle super, |
3391 unsigned int nonstatic_oop_map_count, | |
3392 int first_nonstatic_oop_offset) { | |
3393 unsigned int map_count = | |
3394 super.is_null() ? 0 : super->nonstatic_oop_map_count(); | |
3386 if (nonstatic_oop_map_count > 0) { | 3395 if (nonstatic_oop_map_count > 0) { |
3387 // We have oops to add to map | 3396 // We have oops to add to map |
3388 if (map_size == 0) { | 3397 if (map_count == 0) { |
3389 map_size = nonstatic_oop_map_count; | 3398 map_count = nonstatic_oop_map_count; |
3390 } else { | 3399 } else { |
3391 // Check whether we should add a new map block or whether the last one can be extended | 3400 // Check whether we should add a new map block or whether the last one can |
3392 OopMapBlock* first_map = super->start_of_nonstatic_oop_maps(); | 3401 // be extended |
3393 OopMapBlock* last_map = first_map + map_size - 1; | 3402 OopMapBlock* const first_map = super->start_of_nonstatic_oop_maps(); |
3394 | 3403 OopMapBlock* const last_map = first_map + map_count - 1; |
3395 int next_offset = last_map->offset() + (last_map->length() * heapOopSize); | 3404 |
3405 int next_offset = last_map->offset() + last_map->count() * heapOopSize; | |
3396 if (next_offset == first_nonstatic_oop_offset) { | 3406 if (next_offset == first_nonstatic_oop_offset) { |
3397 // There is no gap bettwen superklass's last oop field and first | 3407 // There is no gap bettwen superklass's last oop field and first |
3398 // local oop field, merge maps. | 3408 // local oop field, merge maps. |
3399 nonstatic_oop_map_count -= 1; | 3409 nonstatic_oop_map_count -= 1; |
3400 } else { | 3410 } else { |
3401 // Superklass didn't end with a oop field, add extra maps | 3411 // Superklass didn't end with a oop field, add extra maps |
3402 assert(next_offset<first_nonstatic_oop_offset, "just checking"); | 3412 assert(next_offset < first_nonstatic_oop_offset, "just checking"); |
3403 } | 3413 } |
3404 map_size += nonstatic_oop_map_count; | 3414 map_count += nonstatic_oop_map_count; |
3405 } | 3415 } |
3406 } | 3416 } |
3407 return map_size; | 3417 return map_count; |
3408 } | 3418 } |
3409 | 3419 |
3410 | 3420 |
3411 void ClassFileParser::fill_oop_maps(instanceKlassHandle k, | 3421 void ClassFileParser::fill_oop_maps(instanceKlassHandle k, |
3412 int nonstatic_oop_map_count, | 3422 unsigned int nonstatic_oop_map_count, |
3413 u2* nonstatic_oop_offsets, u2* nonstatic_oop_length) { | 3423 int* nonstatic_oop_offsets, |
3424 unsigned int* nonstatic_oop_counts) { | |
3414 OopMapBlock* this_oop_map = k->start_of_nonstatic_oop_maps(); | 3425 OopMapBlock* this_oop_map = k->start_of_nonstatic_oop_maps(); |
3415 OopMapBlock* last_oop_map = this_oop_map + k->nonstatic_oop_map_size(); | 3426 const instanceKlass* const super = k->superklass(); |
3416 instanceKlass* super = k->superklass(); | 3427 const unsigned int super_count = super ? super->nonstatic_oop_map_count() : 0; |
3417 if (super != NULL) { | 3428 if (super_count > 0) { |
3418 int super_oop_map_size = super->nonstatic_oop_map_size(); | 3429 // Copy maps from superklass |
3419 OopMapBlock* super_oop_map = super->start_of_nonstatic_oop_maps(); | 3430 OopMapBlock* super_oop_map = super->start_of_nonstatic_oop_maps(); |
3420 // Copy maps from superklass | 3431 for (unsigned int i = 0; i < super_count; ++i) { |
3421 while (super_oop_map_size-- > 0) { | |
3422 *this_oop_map++ = *super_oop_map++; | 3432 *this_oop_map++ = *super_oop_map++; |
3423 } | 3433 } |
3424 } | 3434 } |
3435 | |
3425 if (nonstatic_oop_map_count > 0) { | 3436 if (nonstatic_oop_map_count > 0) { |
3426 if (this_oop_map + nonstatic_oop_map_count > last_oop_map) { | 3437 if (super_count + nonstatic_oop_map_count > k->nonstatic_oop_map_count()) { |
3427 // Calculated in compute_oop_map_size() number of oop maps is less then | 3438 // The counts differ because there is no gap between superklass's last oop |
3428 // collected oop maps since there is no gap between superklass's last oop | 3439 // field and the first local oop field. Extend the last oop map copied |
3429 // field and first local oop field. Extend the last oop map copied | |
3430 // from the superklass instead of creating new one. | 3440 // from the superklass instead of creating new one. |
3431 nonstatic_oop_map_count--; | 3441 nonstatic_oop_map_count--; |
3432 nonstatic_oop_offsets++; | 3442 nonstatic_oop_offsets++; |
3433 this_oop_map--; | 3443 this_oop_map--; |
3434 this_oop_map->set_length(this_oop_map->length() + *nonstatic_oop_length++); | 3444 this_oop_map->set_count(this_oop_map->count() + *nonstatic_oop_counts++); |
3435 this_oop_map++; | 3445 this_oop_map++; |
3436 } | 3446 } |
3437 assert((this_oop_map + nonstatic_oop_map_count) == last_oop_map, "just checking"); | 3447 |
3438 // Add new map blocks, fill them | 3448 // Add new map blocks, fill them |
3439 while (nonstatic_oop_map_count-- > 0) { | 3449 while (nonstatic_oop_map_count-- > 0) { |
3440 this_oop_map->set_offset(*nonstatic_oop_offsets++); | 3450 this_oop_map->set_offset(*nonstatic_oop_offsets++); |
3441 this_oop_map->set_length(*nonstatic_oop_length++); | 3451 this_oop_map->set_count(*nonstatic_oop_counts++); |
3442 this_oop_map++; | 3452 this_oop_map++; |
3443 } | 3453 } |
3454 assert(k->start_of_nonstatic_oop_maps() + k->nonstatic_oop_map_count() == | |
3455 this_oop_map, "sanity"); | |
3444 } | 3456 } |
3445 } | 3457 } |
3446 | 3458 |
3447 | 3459 |
3448 void ClassFileParser::set_precomputed_flags(instanceKlassHandle k) { | 3460 void ClassFileParser::set_precomputed_flags(instanceKlassHandle k) { |