8041934: com/sun/jdi/RepStep.java fails in RT_Baseline on all platforms with assert(_cur_stack_depth == count_frames()) failed: cur_stack_depth out of sync
Missing call to jvmti_method_exit from native wrapper code Reviewed-by: twisti, dcubed, sspitsyn
This commit is contained in:
parent
ac6a099ed7
commit
f0baee0a2c
@ -2657,6 +2657,30 @@ nmethod* SharedRuntime::generate_native_wrapper(MacroAssembler* masm,
|
||||
__ bind(done);
|
||||
}
|
||||
|
||||
{
|
||||
// Normally we do not post method_entry and method_exit events from
|
||||
// compiled code, only from the interpreter. If method_entry/exit
|
||||
// events are switched on at runtime, we will deoptimize everything
|
||||
// (see VM_EnterInterpOnlyMode) on the stack and call method_entry/exit
|
||||
// from the interpreter. But when we do that, we will not deoptimize
|
||||
// this native wrapper frame. Thus we have an extra check here to see
|
||||
// if we are now in interp_only_mode and in that case we do the jvmti
|
||||
// callback.
|
||||
Label skip_jvmti_method_exit;
|
||||
__ ld(G2_thread, JavaThread::interp_only_mode_offset(), G3_scratch);
|
||||
__ cmp_and_br_short(G3_scratch, 0, Assembler::zero, Assembler::pt, skip_jvmti_method_exit);
|
||||
|
||||
save_native_result(masm, ret_type, stack_slots);
|
||||
__ set_metadata_constant(method(), G3_scratch);
|
||||
__ call_VM(
|
||||
noreg,
|
||||
CAST_FROM_FN_PTR(address, SharedRuntime::jvmti_method_exit),
|
||||
G2_thread, G3_scratch,
|
||||
true);
|
||||
restore_native_result(masm, ret_type, stack_slots);
|
||||
__ bind(skip_jvmti_method_exit);
|
||||
}
|
||||
|
||||
// Tell dtrace about this method exit
|
||||
{
|
||||
SkipIfEqual skip_if(
|
||||
|
@ -2238,6 +2238,30 @@ nmethod* SharedRuntime::generate_native_wrapper(MacroAssembler* masm,
|
||||
|
||||
}
|
||||
|
||||
{
|
||||
// Normally we do not post method_entry and method_exit events from
|
||||
// compiled code, only from the interpreter. If method_entry/exit
|
||||
// events are switched on at runtime, we will deoptimize everything
|
||||
// (see VM_EnterInterpOnlyMode) on the stack and call method_entry/exit
|
||||
// from the interpreter. But when we do that, we will not deoptimize
|
||||
// this native wrapper frame. Thus we have an extra check here to see
|
||||
// if we are now in interp_only_mode and in that case we do the jvmti
|
||||
// callback.
|
||||
Label skip_jvmti_method_exit;
|
||||
__ cmpl(Address(thread, JavaThread::interp_only_mode_offset()), 0);
|
||||
__ jcc(Assembler::zero, skip_jvmti_method_exit, true);
|
||||
|
||||
save_native_result(masm, ret_type, stack_slots);
|
||||
__ mov_metadata(rax, method());
|
||||
__ call_VM(
|
||||
noreg,
|
||||
CAST_FROM_FN_PTR(address, SharedRuntime::jvmti_method_exit),
|
||||
thread, rax,
|
||||
true);
|
||||
restore_native_result(masm, ret_type, stack_slots);
|
||||
__ bind(skip_jvmti_method_exit);
|
||||
}
|
||||
|
||||
{
|
||||
SkipIfEqual skip_if(masm, &DTraceMethodProbes, 0);
|
||||
// Tell dtrace about this method exit
|
||||
|
@ -2484,6 +2484,31 @@ nmethod* SharedRuntime::generate_native_wrapper(MacroAssembler* masm,
|
||||
__ bind(done);
|
||||
|
||||
}
|
||||
|
||||
{
|
||||
// Normally we do not post method_entry and method_exit events from
|
||||
// compiled code, only from the interpreter. If method_entry/exit
|
||||
// events are switched on at runtime, we will deoptimize everything
|
||||
// (see VM_EnterInterpOnlyMode) on the stack and call method_entry/exit
|
||||
// from the interpreter. But when we do that, we will not deoptimize
|
||||
// this native wrapper frame. Thus we have an extra check here to see
|
||||
// if we are now in interp_only_mode and in that case we do the jvmti
|
||||
// callback.
|
||||
Label skip_jvmti_method_exit;
|
||||
__ cmpl(Address(r15_thread, JavaThread::interp_only_mode_offset()), 0);
|
||||
__ jcc(Assembler::zero, skip_jvmti_method_exit, true);
|
||||
|
||||
save_native_result(masm, ret_type, stack_slots);
|
||||
__ mov_metadata(c_rarg1, method());
|
||||
__ call_VM(
|
||||
noreg,
|
||||
CAST_FROM_FN_PTR(address, SharedRuntime::jvmti_method_exit),
|
||||
r15_thread, c_rarg1,
|
||||
true);
|
||||
restore_native_result(masm, ret_type, stack_slots);
|
||||
__ bind(skip_jvmti_method_exit);
|
||||
}
|
||||
|
||||
{
|
||||
SkipIfEqual skip(masm, &DTraceMethodProbes, false);
|
||||
save_native_result(masm, ret_type, stack_slots);
|
||||
|
@ -993,6 +993,12 @@ JRT_LEAF(int, SharedRuntime::dtrace_method_exit(
|
||||
return 0;
|
||||
JRT_END
|
||||
|
||||
JRT_ENTRY(int, SharedRuntime::jvmti_method_exit(
|
||||
JavaThread* thread, Method* method))
|
||||
JvmtiExport::post_method_exit(thread, method, thread->last_frame());
|
||||
return 0;
|
||||
JRT_END
|
||||
|
||||
|
||||
// Finds receiver, CallInfo (i.e. receiver method), and calling bytecode)
|
||||
// for a call current in progress, i.e., arguments has been pushed on stack
|
||||
|
@ -263,6 +263,9 @@ class SharedRuntime: AllStatic {
|
||||
static int dtrace_method_entry(JavaThread* thread, Method* m);
|
||||
static int dtrace_method_exit(JavaThread* thread, Method* m);
|
||||
|
||||
// jvmti notification
|
||||
static int jvmti_method_exit(JavaThread* thread, Method* m);
|
||||
|
||||
// Utility method for retrieving the Java thread id, returns 0 if the
|
||||
// thread is not a well formed Java thread.
|
||||
static jlong get_java_tid(Thread* thread);
|
||||
|
Loading…
x
Reference in New Issue
Block a user