64 65 assert(is_array_klass(), "sanity"); 66 assert(is_valueArray_klass(), "sanity"); 67 68 CMH("tweak name symbol refcnt ?") 69 #ifndef PRODUCT 70 if (PrintValueArrayLayout) { 71 print(); 72 } 73 #endif 74 } 75 76 ValueKlass* ValueArrayKlass::element_klass() const { 77 return ValueKlass::cast(_element_klass); 78 } 79 80 void ValueArrayKlass::set_element_klass(Klass* k) { 81 _element_klass = k; 82 } 83 84 ValueArrayKlass* ValueArrayKlass::allocate_klass(Klass* element_klass, 85 Symbol* name, 86 TRAPS) { 87 assert(ValueArrayFlatten, "Flatten array required"); 88 assert(ValueKlass::cast(element_klass)->is_atomic() || (!ValueArrayAtomicAccess), "Atomic by-default"); 89 90 /* 91 * MVT->LWorld, now need to allocate secondaries array types, just like objArrayKlass... 92 * ...so now we are trying out covariant array types, just copy objArrayKlass 93 * TODO refactor any remaining commonality 94 */ 95 96 // Eagerly allocate the direct array supertype. 97 Klass* super_klass = NULL; 98 if (!Universe::is_bootstrapping() || SystemDictionary::Object_klass_loaded()) { 99 Klass* element_super = element_klass->super(); 100 if (element_super != NULL) { 101 // The element type has a direct super. E.g., String[] has direct super of Object[]. 102 super_klass = element_super->array_klass_or_null(ArrayStorageProperties::empty); 103 bool supers_exist = super_klass != NULL; 104 // Also, see if the element has secondary supertypes. 105 // We need an array type for each. 106 Array<Klass*>* element_supers = element_klass->secondary_supers(); 107 for( int i = element_supers->length()-1; i >= 0; i-- ) { 108 Klass* elem_super = element_supers->at(i); 109 if (elem_super->array_klass_or_null(ArrayStorageProperties::empty) == NULL) { 110 supers_exist = false; 111 break; 112 } 113 } 114 if (!supers_exist) { 115 // Oops. Not allocated yet. Back out, allocate it, and retry. 116 Klass* ek = NULL; 117 { 118 MutexUnlocker mu(MultiArray_lock); 119 super_klass = element_super->array_klass(CHECK_0); 120 for( int i = element_supers->length()-1; i >= 0; i-- ) { 121 Klass* elem_super = element_supers->at(i); 122 elem_super->array_klass(CHECK_0); 123 } 124 // Now retry from the beginning 125 ek = element_klass->array_klass(ArrayStorageProperties::flattened_and_null_free, 1, CHECK_0); 126 } // re-lock 127 return ValueArrayKlass::cast(ek); 128 } 129 } else { 130 ShouldNotReachHere(); // Value array klass cannot be the object array klass 131 } 132 } 133 134 135 ClassLoaderData* loader_data = element_klass->class_loader_data(); 136 int size = ArrayKlass::static_size(ValueArrayKlass::header_size()); 137 ValueArrayKlass* vak = new (loader_data, size, THREAD) ValueArrayKlass(element_klass, name); 138 loader_data->add_class(vak); 139 140 ModuleEntry* module = vak->module(); 141 assert(module != NULL, "No module entry for array"); 142 complete_create_array_klass(vak, super_klass, module, CHECK_NULL); 143 return vak; 144 } 145 146 ValueArrayKlass* ValueArrayKlass::allocate_klass(ArrayStorageProperties storage_props, Klass* element_klass, TRAPS) { 147 assert(storage_props.is_flattened(), "Expected flat storage"); 148 Symbol* name = ArrayKlass::create_element_klass_array_name(true, element_klass, CHECK_NULL); 149 return allocate_klass(element_klass, name, THREAD); 150 } 151 152 void ValueArrayKlass::initialize(TRAPS) { 153 element_klass()->initialize(THREAD); 154 } 155 156 // Oops allocation... 157 valueArrayOop ValueArrayKlass::allocate(int length, TRAPS) { 158 if (length < 0) { 159 THROW_0(vmSymbols::java_lang_NegativeArraySizeException()); 160 } 161 if (length > max_elements()) { 162 report_java_out_of_memory("Requested array size exceeds VM limit"); 163 JvmtiExport::post_array_size_exhausted(); 164 THROW_OOP_0(Universe::out_of_memory_error_array_size()); 165 } 166 167 int size = valueArrayOopDesc::object_size(layout_helper(), length); 168 return (valueArrayOop) Universe::heap()->array_allocate(this, size, length, true, THREAD); 169 } | 64 65 assert(is_array_klass(), "sanity"); 66 assert(is_valueArray_klass(), "sanity"); 67 68 CMH("tweak name symbol refcnt ?") 69 #ifndef PRODUCT 70 if (PrintValueArrayLayout) { 71 print(); 72 } 73 #endif 74 } 75 76 ValueKlass* ValueArrayKlass::element_klass() const { 77 return ValueKlass::cast(_element_klass); 78 } 79 80 void ValueArrayKlass::set_element_klass(Klass* k) { 81 _element_klass = k; 82 } 83 84 ValueArrayKlass* ValueArrayKlass::allocate_klass(Klass* element_klass, TRAPS) { 85 assert(ValueArrayFlatten, "Flatten array required"); 86 assert(ValueKlass::cast(element_klass)->is_atomic() || (!ValueArrayAtomicAccess), "Atomic by-default"); 87 88 /* 89 * MVT->LWorld, now need to allocate secondaries array types, just like objArrayKlass... 90 * ...so now we are trying out covariant array types, just copy objArrayKlass 91 * TODO refactor any remaining commonality 92 */ 93 94 // Eagerly allocate the direct array supertype, which would be "[L<vt>;" for this "[Q<vt>;" 95 Klass* super_klass = element_klass->array_klass_or_null(ArrayStorageProperties::empty); 96 if (super_klass == NULL) { 97 MutexUnlocker mu(MultiArray_lock); 98 // allocate super...need to drop the lock 99 element_klass->array_klass(ArrayStorageProperties::empty, 1, CHECK_NULL); 100 // retry, start from the beginning since lock dropped... 101 Klass* ak = element_klass->array_klass(ArrayStorageProperties::flattened_and_null_free, 1, CHECK_NULL); 102 return ValueArrayKlass::cast(ak); 103 } 104 105 Symbol* name = ArrayKlass::create_element_klass_array_name(true, element_klass, CHECK_NULL); 106 ClassLoaderData* loader_data = element_klass->class_loader_data(); 107 int size = ArrayKlass::static_size(ValueArrayKlass::header_size()); 108 ValueArrayKlass* vak = new (loader_data, size, THREAD) ValueArrayKlass(element_klass, name); 109 loader_data->add_class(vak); 110 111 ModuleEntry* module = vak->module(); 112 assert(module != NULL, "No module entry for array"); 113 complete_create_array_klass(vak, super_klass, module, CHECK_NULL); 114 return vak; 115 } 116 117 ValueArrayKlass* ValueArrayKlass::allocate_klass(ArrayStorageProperties storage_props, Klass* element_klass, TRAPS) { 118 assert(storage_props.is_flattened(), "Expected flat storage"); 119 return allocate_klass(element_klass, THREAD); 120 } 121 122 void ValueArrayKlass::initialize(TRAPS) { 123 element_klass()->initialize(THREAD); 124 } 125 126 // Oops allocation... 127 valueArrayOop ValueArrayKlass::allocate(int length, TRAPS) { 128 if (length < 0) { 129 THROW_0(vmSymbols::java_lang_NegativeArraySizeException()); 130 } 131 if (length > max_elements()) { 132 report_java_out_of_memory("Requested array size exceeds VM limit"); 133 JvmtiExport::post_array_size_exhausted(); 134 THROW_OOP_0(Universe::out_of_memory_error_array_size()); 135 } 136 137 int size = valueArrayOopDesc::object_size(layout_helper(), length); 138 return (valueArrayOop) Universe::heap()->array_allocate(this, size, length, true, THREAD); 139 } |