51 #include "oops/method.hpp" |
51 #include "oops/method.hpp" |
52 #include "oops/oop.inline.hpp" |
52 #include "oops/oop.inline.hpp" |
53 #include "oops/symbol.hpp" |
53 #include "oops/symbol.hpp" |
54 #include "prims/jvmtiExport.hpp" |
54 #include "prims/jvmtiExport.hpp" |
55 #include "prims/jvmtiRedefineClasses.hpp" |
55 #include "prims/jvmtiRedefineClasses.hpp" |
56 #include "prims/jvmtiRedefineClassesTrace.hpp" |
|
57 #include "prims/jvmtiThreadState.hpp" |
56 #include "prims/jvmtiThreadState.hpp" |
58 #include "prims/methodComparator.hpp" |
57 #include "prims/methodComparator.hpp" |
59 #include "runtime/atomic.inline.hpp" |
58 #include "runtime/atomic.inline.hpp" |
60 #include "runtime/fieldDescriptor.hpp" |
59 #include "runtime/fieldDescriptor.hpp" |
61 #include "runtime/handles.inline.hpp" |
60 #include "runtime/handles.inline.hpp" |
2572 |
2571 |
2573 assert(new_method != NULL, "method_with_idnum() should not be NULL"); |
2572 assert(new_method != NULL, "method_with_idnum() should not be NULL"); |
2574 assert(old_method != new_method, "sanity check"); |
2573 assert(old_method != new_method, "sanity check"); |
2575 |
2574 |
2576 default_methods()->at_put(index, new_method); |
2575 default_methods()->at_put(index, new_method); |
2577 if (RC_TRACE_IN_RANGE(0x00100000, 0x00400000)) { |
2576 if (log_is_enabled(Info, redefine, class, update)) { |
|
2577 ResourceMark rm; |
2578 if (!(*trace_name_printed)) { |
2578 if (!(*trace_name_printed)) { |
2579 // RC_TRACE_MESG macro has an embedded ResourceMark |
2579 log_info(redefine, class, update) |
2580 RC_TRACE_MESG(("adjust: klassname=%s default methods from name=%s", |
2580 ("adjust: klassname=%s default methods from name=%s", |
2581 external_name(), |
2581 external_name(), old_method->method_holder()->external_name()); |
2582 old_method->method_holder()->external_name())); |
|
2583 *trace_name_printed = true; |
2582 *trace_name_printed = true; |
2584 } |
2583 } |
2585 RC_TRACE(0x00100000, ("default method update: %s(%s) ", |
2584 log_debug(redefine, class, update, vtables) |
2586 new_method->name()->as_C_string(), |
2585 ("default method update: %s(%s) ", |
2587 new_method->signature()->as_C_string())); |
2586 new_method->name()->as_C_string(), new_method->signature()->as_C_string()); |
2588 } |
2587 } |
2589 } |
2588 } |
2590 } |
2589 } |
2591 } |
2590 } |
2592 #endif // INCLUDE_JVMTI |
2591 #endif // INCLUDE_JVMTI |
3351 int deleted_count = 0; // leave debugging breadcrumbs |
3350 int deleted_count = 0; // leave debugging breadcrumbs |
3352 int live_count = 0; |
3351 int live_count = 0; |
3353 ClassLoaderData* loader_data = ik->class_loader_data(); |
3352 ClassLoaderData* loader_data = ik->class_loader_data(); |
3354 assert(loader_data != NULL, "should never be null"); |
3353 assert(loader_data != NULL, "should never be null"); |
3355 |
3354 |
3356 // RC_TRACE macro has an embedded ResourceMark |
3355 ResourceMark rm; |
3357 RC_TRACE(0x00000200, ("purge: %s: previous versions", ik->external_name())); |
3356 log_trace(redefine, class, iklass, purge)("%s: previous versions", ik->external_name()); |
3358 |
3357 |
3359 // previous versions are linked together through the InstanceKlass |
3358 // previous versions are linked together through the InstanceKlass |
3360 InstanceKlass* pv_node = ik->previous_versions(); |
3359 InstanceKlass* pv_node = ik->previous_versions(); |
3361 InstanceKlass* last = ik; |
3360 InstanceKlass* last = ik; |
3362 int version = 0; |
3361 int version = 0; |
3370 if (!pvcp->on_stack()) { |
3369 if (!pvcp->on_stack()) { |
3371 // If the constant pool isn't on stack, none of the methods |
3370 // If the constant pool isn't on stack, none of the methods |
3372 // are executing. Unlink this previous_version. |
3371 // are executing. Unlink this previous_version. |
3373 // The previous version InstanceKlass is on the ClassLoaderData deallocate list |
3372 // The previous version InstanceKlass is on the ClassLoaderData deallocate list |
3374 // so will be deallocated during the next phase of class unloading. |
3373 // so will be deallocated during the next phase of class unloading. |
3375 RC_TRACE(0x00000200, ("purge: previous version " INTPTR_FORMAT " is dead", |
3374 log_trace(redefine, class, iklass, purge)("previous version " INTPTR_FORMAT " is dead", p2i(pv_node)); |
3376 p2i(pv_node))); |
|
3377 // For debugging purposes. |
3375 // For debugging purposes. |
3378 pv_node->set_is_scratch_class(); |
3376 pv_node->set_is_scratch_class(); |
3379 pv_node->class_loader_data()->add_to_deallocate_list(pv_node); |
3377 pv_node->class_loader_data()->add_to_deallocate_list(pv_node); |
3380 pv_node = pv_node->previous_versions(); |
3378 pv_node = pv_node->previous_versions(); |
3381 last->link_previous_versions(pv_node); |
3379 last->link_previous_versions(pv_node); |
3382 deleted_count++; |
3380 deleted_count++; |
3383 version++; |
3381 version++; |
3384 continue; |
3382 continue; |
3385 } else { |
3383 } else { |
3386 RC_TRACE(0x00000200, ("purge: previous version " INTPTR_FORMAT " is alive", |
3384 log_trace(redefine, class, iklass, purge)("previous version " INTPTR_FORMAT " is alive", p2i(pv_node)); |
3387 p2i(pv_node))); |
|
3388 assert(pvcp->pool_holder() != NULL, "Constant pool with no holder"); |
3385 assert(pvcp->pool_holder() != NULL, "Constant pool with no holder"); |
3389 guarantee (!loader_data->is_unloading(), "unloaded classes can't be on the stack"); |
3386 guarantee (!loader_data->is_unloading(), "unloaded classes can't be on the stack"); |
3390 live_count++; |
3387 live_count++; |
3391 } |
3388 } |
3392 |
3389 |
3394 // Reset dead EMCP methods not to get breakpoints. |
3391 // Reset dead EMCP methods not to get breakpoints. |
3395 // All methods are deallocated when all of the methods for this class are no |
3392 // All methods are deallocated when all of the methods for this class are no |
3396 // longer running. |
3393 // longer running. |
3397 Array<Method*>* method_refs = pv_node->methods(); |
3394 Array<Method*>* method_refs = pv_node->methods(); |
3398 if (method_refs != NULL) { |
3395 if (method_refs != NULL) { |
3399 RC_TRACE(0x00000200, ("purge: previous methods length=%d", |
3396 log_trace(redefine, class, iklass, purge)("previous methods length=%d", method_refs->length()); |
3400 method_refs->length())); |
|
3401 for (int j = 0; j < method_refs->length(); j++) { |
3397 for (int j = 0; j < method_refs->length(); j++) { |
3402 Method* method = method_refs->at(j); |
3398 Method* method = method_refs->at(j); |
3403 |
3399 |
3404 if (!method->on_stack()) { |
3400 if (!method->on_stack()) { |
3405 // no breakpoints for non-running methods |
3401 // no breakpoints for non-running methods |
3407 method->set_running_emcp(false); |
3403 method->set_running_emcp(false); |
3408 } |
3404 } |
3409 } else { |
3405 } else { |
3410 assert (method->is_obsolete() || method->is_running_emcp(), |
3406 assert (method->is_obsolete() || method->is_running_emcp(), |
3411 "emcp method cannot run after emcp bit is cleared"); |
3407 "emcp method cannot run after emcp bit is cleared"); |
3412 // RC_TRACE macro has an embedded ResourceMark |
3408 log_trace(redefine, class, iklass, purge) |
3413 RC_TRACE(0x00000200, |
|
3414 ("purge: %s(%s): prev method @%d in version @%d is alive", |
3409 ("purge: %s(%s): prev method @%d in version @%d is alive", |
3415 method->name()->as_C_string(), |
3410 method->name()->as_C_string(), method->signature()->as_C_string(), j, version); |
3416 method->signature()->as_C_string(), j, version)); |
|
3417 } |
3411 } |
3418 } |
3412 } |
3419 } |
3413 } |
3420 // next previous version |
3414 // next previous version |
3421 last = pv_node; |
3415 last = pv_node; |
3422 pv_node = pv_node->previous_versions(); |
3416 pv_node = pv_node->previous_versions(); |
3423 version++; |
3417 version++; |
3424 } |
3418 } |
3425 RC_TRACE(0x00000200, |
3419 log_trace(redefine, class, iklass, purge) |
3426 ("purge: previous version stats: live=%d, deleted=%d", live_count, |
3420 ("previous version stats: live=%d, deleted=%d", |
3427 deleted_count)); |
3421 live_count, deleted_count); |
3428 } |
3422 } |
3429 } |
3423 } |
3430 |
3424 |
3431 void InstanceKlass::mark_newly_obsolete_methods(Array<Method*>* old_methods, |
3425 void InstanceKlass::mark_newly_obsolete_methods(Array<Method*>* old_methods, |
3432 int emcp_method_count) { |
3426 int emcp_method_count) { |
3457 if (!method->is_obsolete() && |
3451 if (!method->is_obsolete() && |
3458 method->name() == m_name && |
3452 method->name() == m_name && |
3459 method->signature() == m_signature) { |
3453 method->signature() == m_signature) { |
3460 // The current RedefineClasses() call has made all EMCP |
3454 // The current RedefineClasses() call has made all EMCP |
3461 // versions of this method obsolete so mark it as obsolete |
3455 // versions of this method obsolete so mark it as obsolete |
3462 RC_TRACE(0x00000400, |
3456 log_trace(redefine, class, iklass, add) |
3463 ("add: %s(%s): flush obsolete method @%d in version @%d", |
3457 ("%s(%s): flush obsolete method @%d in version @%d", |
3464 m_name->as_C_string(), m_signature->as_C_string(), k, j)); |
3458 m_name->as_C_string(), m_signature->as_C_string(), k, j); |
3465 |
3459 |
3466 method->set_is_obsolete(); |
3460 method->set_is_obsolete(); |
3467 break; |
3461 break; |
3468 } |
3462 } |
3469 } |
3463 } |
3491 void InstanceKlass::add_previous_version(instanceKlassHandle scratch_class, |
3485 void InstanceKlass::add_previous_version(instanceKlassHandle scratch_class, |
3492 int emcp_method_count) { |
3486 int emcp_method_count) { |
3493 assert(Thread::current()->is_VM_thread(), |
3487 assert(Thread::current()->is_VM_thread(), |
3494 "only VMThread can add previous versions"); |
3488 "only VMThread can add previous versions"); |
3495 |
3489 |
3496 // RC_TRACE macro has an embedded ResourceMark |
3490 ResourceMark rm; |
3497 RC_TRACE(0x00000400, ("adding previous version ref for %s, EMCP_cnt=%d", |
3491 log_trace(redefine, class, iklass, add) |
3498 scratch_class->external_name(), emcp_method_count)); |
3492 ("adding previous version ref for %s, EMCP_cnt=%d", scratch_class->external_name(), emcp_method_count); |
3499 |
3493 |
3500 // Clean out old previous versions |
3494 // Clean out old previous versions |
3501 purge_previous_versions(this); |
3495 purge_previous_versions(this); |
3502 |
3496 |
3503 // Mark newly obsolete methods in remaining previous versions. An EMCP method from |
3497 // Mark newly obsolete methods in remaining previous versions. An EMCP method from |
3509 // is not marked as being on the stack, then none of the methods |
3503 // is not marked as being on the stack, then none of the methods |
3510 // in this previous version of the class are on the stack so |
3504 // in this previous version of the class are on the stack so |
3511 // we don't need to add this as a previous version. |
3505 // we don't need to add this as a previous version. |
3512 ConstantPool* cp_ref = scratch_class->constants(); |
3506 ConstantPool* cp_ref = scratch_class->constants(); |
3513 if (!cp_ref->on_stack()) { |
3507 if (!cp_ref->on_stack()) { |
3514 RC_TRACE(0x00000400, ("add: scratch class not added; no methods are running")); |
3508 log_trace(redefine, class, iklass, add)("scratch class not added; no methods are running"); |
3515 // For debugging purposes. |
3509 // For debugging purposes. |
3516 scratch_class->set_is_scratch_class(); |
3510 scratch_class->set_is_scratch_class(); |
3517 scratch_class->class_loader_data()->add_to_deallocate_list(scratch_class()); |
3511 scratch_class->class_loader_data()->add_to_deallocate_list(scratch_class()); |
3518 // Update count for class unloading. |
3512 // Update count for class unloading. |
3519 _previous_version_count--; |
3513 _previous_version_count--; |
3532 // and use this bit to set the is_running_emcp bit. |
3526 // and use this bit to set the is_running_emcp bit. |
3533 // After the safepoint, the on_stack bit is cleared and the running emcp |
3527 // After the safepoint, the on_stack bit is cleared and the running emcp |
3534 // method may exit. If so, we would set a breakpoint in a method that |
3528 // method may exit. If so, we would set a breakpoint in a method that |
3535 // is never reached, but this won't be noticeable to the programmer. |
3529 // is never reached, but this won't be noticeable to the programmer. |
3536 old_method->set_running_emcp(true); |
3530 old_method->set_running_emcp(true); |
3537 RC_TRACE(0x00000400, ("add: EMCP method %s is on_stack " INTPTR_FORMAT, |
3531 log_trace(redefine, class, iklass, add) |
3538 old_method->name_and_sig_as_C_string(), p2i(old_method))); |
3532 ("EMCP method %s is on_stack " INTPTR_FORMAT, old_method->name_and_sig_as_C_string(), p2i(old_method)); |
3539 } else if (!old_method->is_obsolete()) { |
3533 } else if (!old_method->is_obsolete()) { |
3540 RC_TRACE(0x00000400, ("add: EMCP method %s is NOT on_stack " INTPTR_FORMAT, |
3534 log_trace(redefine, class, iklass, add) |
3541 old_method->name_and_sig_as_C_string(), p2i(old_method))); |
3535 ("EMCP method %s is NOT on_stack " INTPTR_FORMAT, old_method->name_and_sig_as_C_string(), p2i(old_method)); |
3542 } |
3536 } |
3543 } |
3537 } |
3544 } |
3538 } |
3545 |
3539 |
3546 // Add previous version if any methods are still running. |
3540 // Add previous version if any methods are still running. |
3547 RC_TRACE(0x00000400, ("add: scratch class added; one of its methods is on_stack")); |
3541 log_trace(redefine, class, iklass, add)("scratch class added; one of its methods is on_stack"); |
3548 assert(scratch_class->previous_versions() == NULL, "shouldn't have a previous version"); |
3542 assert(scratch_class->previous_versions() == NULL, "shouldn't have a previous version"); |
3549 scratch_class->link_previous_versions(previous_versions()); |
3543 scratch_class->link_previous_versions(previous_versions()); |
3550 link_previous_versions(scratch_class()); |
3544 link_previous_versions(scratch_class()); |
3551 // Update count for class unloading. |
3545 // Update count for class unloading. |
3552 _previous_version_count++; |
3546 _previous_version_count++; |