183 #endif
184 }
185
186
187 //=============================================================================
188 // Opto compiler runtime routines
189 //=============================================================================
190
191
192 //=============================allocation======================================
193 // We failed the fast-path allocation. Now we need to do a scavenge or GC
194 // and try allocation again.
195
196 // object allocation
197 JRT_BLOCK_ENTRY(void, OptoRuntime::new_instance_C(Klass* klass, JavaThread* thread))
198 JRT_BLOCK;
199 #ifndef PRODUCT
200 SharedRuntime::_new_instance_ctr++; // new instance requires GC
201 #endif
202 assert(check_compiled_frame(thread), "incorrect caller");
203
204 // These checks are cheap to make and support reflective allocation.
205 int lh = klass->layout_helper();
206 if (Klass::layout_helper_needs_slow_path(lh) || !InstanceKlass::cast(klass)->is_initialized()) {
207 Handle holder(THREAD, klass->klass_holder()); // keep the klass alive
208 klass->check_valid_for_instantiation(false, THREAD);
209 if (!HAS_PENDING_EXCEPTION) {
210 InstanceKlass::cast(klass)->initialize(THREAD);
211 }
212 }
213
214 if (!HAS_PENDING_EXCEPTION) {
215 // Scavenge and allocate an instance.
216 Handle holder(THREAD, klass->klass_holder()); // keep the klass alive
217 oop result = InstanceKlass::cast(klass)->allocate_instance(THREAD);
218 thread->set_vm_result(result);
219
220 // Pass oops back through thread local storage. Our apparent type to Java
221 // is that we return an oop, but we can block on exit from this routine and
222 // a GC can trash the oop in C's return register. The generated stub will
223 // fetch the oop from TLS after any possible GC.
224 }
225
226 deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
227 JRT_BLOCK_END;
228
229 // inform GC that we won't do card marks for initializing writes.
230 SharedRuntime::on_slowpath_allocation_exit(thread);
231 JRT_END
232
233
234 // array allocation
235 JRT_BLOCK_ENTRY(void, OptoRuntime::new_array_C(Klass* array_type, int len, JavaThread *thread))
236 JRT_BLOCK;
237 #ifndef PRODUCT
238 SharedRuntime::_new_array_ctr++; // new array requires GC
239 #endif
240 assert(check_compiled_frame(thread), "incorrect caller");
241
242 // Scavenge and allocate an instance.
243 oop result;
244
245 if (array_type->is_typeArray_klass()) {
246 // The oopFactory likes to work with the element type.
247 // (We could bypass the oopFactory, since it doesn't add much value.)
248 BasicType elem_type = TypeArrayKlass::cast(array_type)->element_type();
249 result = oopFactory::new_typeArray(elem_type, len, THREAD);
250 } else {
251 // Although the oopFactory likes to work with the elem_type,
252 // the compiler prefers the array_type, since it must already have
253 // that latter value in hand for the fast path.
254 Handle holder(THREAD, array_type->klass_holder()); // keep the array klass alive
255 Klass* elem_type = ObjArrayKlass::cast(array_type)->element_klass();
256 result = oopFactory::new_objArray(elem_type, len, THREAD);
257 }
258
259 // Pass oops back through thread local storage. Our apparent type to Java
260 // is that we return an oop, but we can block on exit from this routine and
302 // Zero array here if the caller is deoptimized.
303 int size = ((typeArrayOop)result)->object_size();
304 BasicType elem_type = TypeArrayKlass::cast(array_type)->element_type();
305 const size_t hs = arrayOopDesc::header_size(elem_type);
306 // Align to next 8 bytes to avoid trashing arrays's length.
307 const size_t aligned_hs = align_object_offset(hs);
308 HeapWord* obj = (HeapWord*)result;
309 if (aligned_hs > hs) {
310 Copy::zero_to_words(obj+hs, aligned_hs-hs);
311 }
312 // Optimized zeroing.
313 Copy::fill_to_aligned_words(obj+aligned_hs, size-aligned_hs);
314 }
315
316 JRT_END
317
318 // Note: multianewarray for one dimension is handled inline by GraphKit::new_array.
319
320 // multianewarray for 2 dimensions
321 JRT_ENTRY(void, OptoRuntime::multianewarray2_C(Klass* elem_type, int len1, int len2, JavaThread *thread))
322 #ifndef PRODUCT
323 SharedRuntime::_multi2_ctr++; // multianewarray for 1 dimension
324 #endif
325 assert(check_compiled_frame(thread), "incorrect caller");
326 assert(elem_type->is_klass(), "not a class");
327 jint dims[2];
328 dims[0] = len1;
329 dims[1] = len2;
330 Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
331 oop obj = ArrayKlass::cast(elem_type)->multi_allocate(2, dims, THREAD);
332 deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
333 thread->set_vm_result(obj);
334 JRT_END
335
336 // multianewarray for 3 dimensions
337 JRT_ENTRY(void, OptoRuntime::multianewarray3_C(Klass* elem_type, int len1, int len2, int len3, JavaThread *thread))
338 #ifndef PRODUCT
339 SharedRuntime::_multi3_ctr++; // multianewarray for 1 dimension
340 #endif
341 assert(check_compiled_frame(thread), "incorrect caller");
342 assert(elem_type->is_klass(), "not a class");
343 jint dims[3];
344 dims[0] = len1;
345 dims[1] = len2;
346 dims[2] = len3;
347 Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
348 oop obj = ArrayKlass::cast(elem_type)->multi_allocate(3, dims, THREAD);
349 deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
350 thread->set_vm_result(obj);
351 JRT_END
352
353 // multianewarray for 4 dimensions
354 JRT_ENTRY(void, OptoRuntime::multianewarray4_C(Klass* elem_type, int len1, int len2, int len3, int len4, JavaThread *thread))
355 #ifndef PRODUCT
356 SharedRuntime::_multi4_ctr++; // multianewarray for 1 dimension
357 #endif
358 assert(check_compiled_frame(thread), "incorrect caller");
359 assert(elem_type->is_klass(), "not a class");
360 jint dims[4];
361 dims[0] = len1;
362 dims[1] = len2;
363 dims[2] = len3;
364 dims[3] = len4;
365 Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
366 oop obj = ArrayKlass::cast(elem_type)->multi_allocate(4, dims, THREAD);
367 deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
368 thread->set_vm_result(obj);
369 JRT_END
370
371 // multianewarray for 5 dimensions
372 JRT_ENTRY(void, OptoRuntime::multianewarray5_C(Klass* elem_type, int len1, int len2, int len3, int len4, int len5, JavaThread *thread))
373 #ifndef PRODUCT
374 SharedRuntime::_multi5_ctr++; // multianewarray for 1 dimension
375 #endif
376 assert(check_compiled_frame(thread), "incorrect caller");
377 assert(elem_type->is_klass(), "not a class");
378 jint dims[5];
379 dims[0] = len1;
380 dims[1] = len2;
381 dims[2] = len3;
382 dims[3] = len4;
383 dims[4] = len5;
384 Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
385 oop obj = ArrayKlass::cast(elem_type)->multi_allocate(5, dims, THREAD);
386 deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
387 thread->set_vm_result(obj);
388 JRT_END
389
390 JRT_ENTRY(void, OptoRuntime::multianewarrayN_C(Klass* elem_type, arrayOopDesc* dims, JavaThread *thread))
391 assert(check_compiled_frame(thread), "incorrect caller");
392 assert(elem_type->is_klass(), "not a class");
|
183 #endif
184 }
185
186
187 //=============================================================================
188 // Opto compiler runtime routines
189 //=============================================================================
190
191
192 //=============================allocation======================================
193 // We failed the fast-path allocation. Now we need to do a scavenge or GC
194 // and try allocation again.
195
196 // object allocation
197 JRT_BLOCK_ENTRY(void, OptoRuntime::new_instance_C(Klass* klass, JavaThread* thread))
198 JRT_BLOCK;
199 #ifndef PRODUCT
200 SharedRuntime::_new_instance_ctr++; // new instance requires GC
201 #endif
202 assert(check_compiled_frame(thread), "incorrect caller");
203 JvmtiSampledObjectAllocEventCollector collector;
204
205 // These checks are cheap to make and support reflective allocation.
206 int lh = klass->layout_helper();
207 if (Klass::layout_helper_needs_slow_path(lh) || !InstanceKlass::cast(klass)->is_initialized()) {
208 Handle holder(THREAD, klass->klass_holder()); // keep the klass alive
209 klass->check_valid_for_instantiation(false, THREAD);
210 if (!HAS_PENDING_EXCEPTION) {
211 InstanceKlass::cast(klass)->initialize(THREAD);
212 }
213 }
214
215 if (!HAS_PENDING_EXCEPTION) {
216 // Scavenge and allocate an instance.
217 Handle holder(THREAD, klass->klass_holder()); // keep the klass alive
218 oop result = InstanceKlass::cast(klass)->allocate_instance(THREAD);
219 thread->set_vm_result(result);
220
221 // Pass oops back through thread local storage. Our apparent type to Java
222 // is that we return an oop, but we can block on exit from this routine and
223 // a GC can trash the oop in C's return register. The generated stub will
224 // fetch the oop from TLS after any possible GC.
225 }
226
227 deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
228 JRT_BLOCK_END;
229
230 // inform GC that we won't do card marks for initializing writes.
231 SharedRuntime::on_slowpath_allocation_exit(thread);
232 JRT_END
233
234
235 // array allocation
236 JRT_BLOCK_ENTRY(void, OptoRuntime::new_array_C(Klass* array_type, int len, JavaThread *thread))
237 JRT_BLOCK;
238 #ifndef PRODUCT
239 SharedRuntime::_new_array_ctr++; // new array requires GC
240 #endif
241 assert(check_compiled_frame(thread), "incorrect caller");
242 JvmtiSampledObjectAllocEventCollector collector;
243
244 // Scavenge and allocate an instance.
245 oop result;
246
247 if (array_type->is_typeArray_klass()) {
248 // The oopFactory likes to work with the element type.
249 // (We could bypass the oopFactory, since it doesn't add much value.)
250 BasicType elem_type = TypeArrayKlass::cast(array_type)->element_type();
251 result = oopFactory::new_typeArray(elem_type, len, THREAD);
252 } else {
253 // Although the oopFactory likes to work with the elem_type,
254 // the compiler prefers the array_type, since it must already have
255 // that latter value in hand for the fast path.
256 Handle holder(THREAD, array_type->klass_holder()); // keep the array klass alive
257 Klass* elem_type = ObjArrayKlass::cast(array_type)->element_klass();
258 result = oopFactory::new_objArray(elem_type, len, THREAD);
259 }
260
261 // Pass oops back through thread local storage. Our apparent type to Java
262 // is that we return an oop, but we can block on exit from this routine and
304 // Zero array here if the caller is deoptimized.
305 int size = ((typeArrayOop)result)->object_size();
306 BasicType elem_type = TypeArrayKlass::cast(array_type)->element_type();
307 const size_t hs = arrayOopDesc::header_size(elem_type);
308 // Align to next 8 bytes to avoid trashing arrays's length.
309 const size_t aligned_hs = align_object_offset(hs);
310 HeapWord* obj = (HeapWord*)result;
311 if (aligned_hs > hs) {
312 Copy::zero_to_words(obj+hs, aligned_hs-hs);
313 }
314 // Optimized zeroing.
315 Copy::fill_to_aligned_words(obj+aligned_hs, size-aligned_hs);
316 }
317
318 JRT_END
319
320 // Note: multianewarray for one dimension is handled inline by GraphKit::new_array.
321
322 // multianewarray for 2 dimensions
323 JRT_ENTRY(void, OptoRuntime::multianewarray2_C(Klass* elem_type, int len1, int len2, JavaThread *thread))
324 JvmtiSampledObjectAllocEventCollector collector;
325 #ifndef PRODUCT
326 SharedRuntime::_multi2_ctr++; // multianewarray for 1 dimension
327 #endif
328 assert(check_compiled_frame(thread), "incorrect caller");
329 assert(elem_type->is_klass(), "not a class");
330 jint dims[2];
331 dims[0] = len1;
332 dims[1] = len2;
333 Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
334 oop obj = ArrayKlass::cast(elem_type)->multi_allocate(2, dims, THREAD);
335 deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
336 thread->set_vm_result(obj);
337 JRT_END
338
339 // multianewarray for 3 dimensions
340 JRT_ENTRY(void, OptoRuntime::multianewarray3_C(Klass* elem_type, int len1, int len2, int len3, JavaThread *thread))
341 JvmtiSampledObjectAllocEventCollector collector;
342 #ifndef PRODUCT
343 SharedRuntime::_multi3_ctr++; // multianewarray for 1 dimension
344 #endif
345 assert(check_compiled_frame(thread), "incorrect caller");
346 assert(elem_type->is_klass(), "not a class");
347 jint dims[3];
348 dims[0] = len1;
349 dims[1] = len2;
350 dims[2] = len3;
351 Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
352 oop obj = ArrayKlass::cast(elem_type)->multi_allocate(3, dims, THREAD);
353 deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
354 thread->set_vm_result(obj);
355 JRT_END
356
357 // multianewarray for 4 dimensions
358 JRT_ENTRY(void, OptoRuntime::multianewarray4_C(Klass* elem_type, int len1, int len2, int len3, int len4, JavaThread *thread))
359 JvmtiSampledObjectAllocEventCollector collector;
360 #ifndef PRODUCT
361 SharedRuntime::_multi4_ctr++; // multianewarray for 1 dimension
362 #endif
363 assert(check_compiled_frame(thread), "incorrect caller");
364 assert(elem_type->is_klass(), "not a class");
365 jint dims[4];
366 dims[0] = len1;
367 dims[1] = len2;
368 dims[2] = len3;
369 dims[3] = len4;
370 Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
371 oop obj = ArrayKlass::cast(elem_type)->multi_allocate(4, dims, THREAD);
372 deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
373 thread->set_vm_result(obj);
374 JRT_END
375
376 // multianewarray for 5 dimensions
377 JRT_ENTRY(void, OptoRuntime::multianewarray5_C(Klass* elem_type, int len1, int len2, int len3, int len4, int len5, JavaThread *thread))
378 JvmtiSampledObjectAllocEventCollector collector;
379 #ifndef PRODUCT
380 SharedRuntime::_multi5_ctr++; // multianewarray for 1 dimension
381 #endif
382 assert(check_compiled_frame(thread), "incorrect caller");
383 assert(elem_type->is_klass(), "not a class");
384 jint dims[5];
385 dims[0] = len1;
386 dims[1] = len2;
387 dims[2] = len3;
388 dims[3] = len4;
389 dims[4] = len5;
390 Handle holder(THREAD, elem_type->klass_holder()); // keep the klass alive
391 oop obj = ArrayKlass::cast(elem_type)->multi_allocate(5, dims, THREAD);
392 deoptimize_caller_frame(thread, HAS_PENDING_EXCEPTION);
393 thread->set_vm_result(obj);
394 JRT_END
395
396 JRT_ENTRY(void, OptoRuntime::multianewarrayN_C(Klass* elem_type, arrayOopDesc* dims, JavaThread *thread))
397 assert(check_compiled_frame(thread), "incorrect caller");
398 assert(elem_type->is_klass(), "not a class");
|