< prev index next > src/hotspot/cpu/x86/interp_masm_x86.cpp
Print this page
// interpreter specific
restore_bcp();
restore_locals();
}
! void InterpreterMacroAssembler::call_VM_preemptable(Register oop_result,
! address entry_point,
! Register arg_1) {
! assert(arg_1 == c_rarg1, "");
Label resume_pc, not_preempted;
#ifdef ASSERT
{
Label L;
// interpreter specific
restore_bcp();
restore_locals();
}
! void InterpreterMacroAssembler::call_VM_preemptable_helper(Register oop_result,
! address entry_point,
! int number_of_arguments,
! bool check_exceptions) {
Label resume_pc, not_preempted;
#ifdef ASSERT
{
Label L;
// Make VM call. In case of preemption set last_pc to the one we want to resume to.
// Note: call_VM_helper requires last_Java_pc for anchor to be at the top of the stack.
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.
// Make VM call. In case of preemption set last_pc to the one we want to resume to.
// Note: call_VM_helper requires last_Java_pc for anchor to be at the top of the stack.
lea(rscratch1, resume_pc);
push(rscratch1);
! MacroAssembler::call_VM_helper(oop_result, entry_point, number_of_arguments, check_exceptions);
pop(rscratch1);
pop_cont_fastpath();
// Check if preempted.
// In case of preemption, this is where we will resume once we finally acquire the monitor.
bind(resume_pc);
restore_after_resume(false /* is_native */);
+ if (check_exceptions) {
+ // check for pending exceptions (java_thread is set upon return)
+ cmpptr(Address(r15_thread, Thread::pending_exception_offset()), NULL_WORD);
+ Label ok;
+ jcc(Assembler::equal, ok);
+ jump(RuntimeAddress(StubRoutines::forward_exception_entry()));
+ bind(ok);
+ }
+
+ // get oop result if there is one and reset the value in the thread
+ if (oop_result->is_valid()) {
+ get_vm_result_oop(oop_result);
+ }
+
bind(not_preempted);
}
+ static void pass_arg1(MacroAssembler* masm, Register arg) {
+ if (c_rarg1 != arg ) {
+ masm->mov(c_rarg1, arg);
+ }
+ }
+
+ static void pass_arg2(MacroAssembler* masm, Register arg) {
+ if (c_rarg2 != arg ) {
+ masm->mov(c_rarg2, arg);
+ }
+ }
+
+ void InterpreterMacroAssembler::call_VM_preemptable(Register oop_result,
+ address entry_point,
+ Register arg_1,
+ bool check_exceptions) {
+ pass_arg1(this, arg_1);
+ call_VM_preemptable_helper(oop_result, entry_point, 1, check_exceptions);
+ }
+
+ void InterpreterMacroAssembler::call_VM_preemptable(Register oop_result,
+ address entry_point,
+ Register arg_1,
+ Register arg_2,
+ bool check_exceptions) {
+ LP64_ONLY(assert_different_registers(arg_1, c_rarg2));
+ pass_arg2(this, arg_2);
+ pass_arg1(this, arg_1);
+ call_VM_preemptable_helper(oop_result, entry_point, 2, check_exceptions);
+ }
+
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.
< prev index next >