< prev index next > src/hotspot/cpu/x86/interp_masm_x86.cpp
Print this page
// interpreter specific
restore_bcp();
restore_locals();
}
+ #ifdef _LP64
+ void InterpreterMacroAssembler::call_VM_preemptable(Register oop_result,
+ address entry_point,
+ Register arg_1) {
+ assert(arg_1 == c_rarg1, "");
+ Label resume_pc, not_preempted;
+
+ push_cont_fastpath();
+
+ // Make VM call. In case of preemption set last_pc to
+ // the one we want to resume to.
+ lea(rscratch1, resume_pc);
+ push(rscratch1);
+ MacroAssembler::call_VM_helper(oop_result, entry_point, 1, false /*check_exceptions*/);
+ pop(rscratch1);
+
+ pop_cont_fastpath();
+
+ // Check if preempted
+ movptr(rscratch1, Address(r15_thread, JavaThread::preempt_alternate_return_offset()));
+ cmpptr(rscratch1, NULL_WORD);
+ jccb(Assembler::zero, not_preempted);
+ movptr(Address(r15_thread, JavaThread::preempt_alternate_return_offset()), NULL_WORD);
+ jmp(rscratch1);
+
+ bind(resume_pc);
+ restore_after_resume(false /* is_native */);
+
+ bind(not_preempted);
+ }
+
+ void InterpreterMacroAssembler::restore_after_resume(bool is_native) {
+ lea(rscratch1, ExternalAddress(Interpreter::cont_resume_interpreter_adapter()));
+ call(rscratch1);
+ if (is_native) {
+ // On resume we need to set up stack as expected
+ push(dtos);
+ push(ltos);
+ }
+ }
+ #else
+ void InterpreterMacroAssembler::call_VM_preemptable(Register oop_result,
+ address entry_point,
+ Register arg_1) {
+ MacroAssembler::call_VM(oop_result, entry_point, arg_1);
+ }
+ #endif // _LP64
+
void InterpreterMacroAssembler::check_and_handle_popframe(Register java_thread) {
if (JvmtiExport::can_pop_frame()) {
Label L;
// Initiate popframe handling only if it is not already being
// processed. If the flag has the popframe_processing bit set, it
void InterpreterMacroAssembler::lock_object(Register lock_reg) {
assert(lock_reg == LP64_ONLY(c_rarg1) NOT_LP64(rdx),
"The argument is only for looks. It must be c_rarg1");
if (LockingMode == LM_MONITOR) {
- call_VM(noreg,
+ call_VM_preemptable(noreg,
CAST_FROM_FN_PTR(address, InterpreterRuntime::monitorenter),
lock_reg);
} else {
Label count_locking, done, slow_case;
// Save the test result, for recursive case, the result is zero
movptr(Address(lock_reg, mark_offset), swap_reg);
jcc(Assembler::notZero, slow_case);
bind(count_locking);
+ inc_held_monitor_count();
}
- inc_held_monitor_count();
jmp(done);
bind(slow_case);
// Call the runtime routine for slow case
- call_VM(noreg,
+ call_VM_preemptable(noreg,
CAST_FROM_FN_PTR(address, InterpreterRuntime::monitorenter),
lock_reg);
bind(done);
}
}
// zero for simple unlock of a stack-lock case
jcc(Assembler::notZero, slow_case);
bind(count_locking);
+ dec_held_monitor_count();
}
- dec_held_monitor_count();
jmp(done);
bind(slow_case);
// Call the runtime routine for slow case.
movptr(Address(lock_reg, BasicObjectLock::obj_offset()), obj_reg); // restore obj
< prev index next >