< prev index next >

src/hotspot/cpu/riscv/interp_masm_riscv.cpp

Print this page

 761   leave();
 762   // If we're returning to interpreted code we will shortly be
 763   // adjusting SP to allow some space for ESP.  If we're returning to
 764   // compiled code the saved sender SP was saved in sender_sp, so this
 765   // restores it.
 766   andi(sp, esp, -16);
 767 }
 768 
 769 // Lock object
 770 //
 771 // Args:
 772 //      c_rarg1: BasicObjectLock to be used for locking
 773 //
 774 // Kills:
 775 //      x10
 776 //      c_rarg0, c_rarg1, c_rarg2, c_rarg3, .. (param regs)
 777 //      t0, t1 (temp regs)
 778 void InterpreterMacroAssembler::lock_object(Register lock_reg)
 779 {
 780   assert(lock_reg == c_rarg1, "The argument is only for looks. It must be c_rarg1");







 781   if (UseHeavyMonitors) {
 782     call_VM(noreg,
 783             CAST_FROM_FN_PTR(address, InterpreterRuntime::monitorenter),
 784             lock_reg);
 785   } else {
 786     Label done;
 787 
 788     const Register swap_reg = x10;
 789     const Register tmp = c_rarg2;
 790     const Register obj_reg = c_rarg3; // Will contain the oop
 791 
 792     const int obj_offset = BasicObjectLock::obj_offset_in_bytes();
 793     const int lock_offset = BasicObjectLock::lock_offset_in_bytes ();
 794     const int mark_offset = lock_offset +
 795                             BasicLock::displaced_header_offset_in_bytes();
 796 
 797     Label slow_case;
 798 
 799     // Load object pointer into obj_reg c_rarg3
 800     ld(obj_reg, Address(lock_reg, obj_offset));
 801 
 802     if (DiagnoseSyncOnValueBasedClasses != 0) {
 803       load_klass(tmp, obj_reg);
 804       lwu(tmp, Address(tmp, Klass::access_flags_offset()));
 805       andi(tmp, tmp, JVM_ACC_IS_VALUE_BASED_CLASS);
 806       bnez(tmp, slow_case);
 807     }
 808 
 809     // Load (object->mark() | 1) into swap_reg
 810     ld(t0, Address(obj_reg, oopDesc::mark_offset_in_bytes()));
 811     ori(swap_reg, t0, 1);
 812 
 813     // Save (object->mark() | 1) into BasicLock's displaced header
 814     sd(swap_reg, Address(lock_reg, mark_offset));
 815 
 816     assert(lock_offset == 0,
 817            "displached header must be first word in BasicObjectLock");
 818 
 819     cmpxchg_obj_header(swap_reg, lock_reg, obj_reg, t0, done, /*fallthrough*/NULL);
 820 
 821     // Test if the oopMark is an obvious stack pointer, i.e.,
 822     //  1) (mark & 7) == 0, and
 823     //  2) sp <= mark < mark + os::pagesize()
 824     //
 825     // These 3 tests can be done by evaluating the following
 826     // expression: ((mark - sp) & (7 - os::vm_page_size())),
 827     // assuming both stack pointer and pagesize have their
 828     // least significant 3 bits clear.
 829     // NOTE: the oopMark is in swap_reg x10 as the result of cmpxchg
 830     sub(swap_reg, swap_reg, sp);
 831     mv(t0, (int64_t)(7 - os::vm_page_size()));
 832     andr(swap_reg, swap_reg, t0);
 833 
 834     // Save the test result, for recursive case, the result is zero
 835     sd(swap_reg, Address(lock_reg, mark_offset));
 836     beqz(swap_reg, done);
 837 
 838     bind(slow_case);
 839 
 840     // Call the runtime routine for slow case
 841     call_VM(noreg,
 842             CAST_FROM_FN_PTR(address, InterpreterRuntime::monitorenter),
 843             lock_reg);
 844 
 845     bind(done);
 846   }
 847 }
 848 
 849 
 850 // Unlocks an object. Used in monitorexit bytecode and
 851 // remove_activation.  Throws an IllegalMonitorException if object is
 852 // not locked by current thread.
 853 //
 854 // Args:
 855 //      c_rarg1: BasicObjectLock for lock
 856 //
 857 // Kills:
 858 //      x10
 859 //      c_rarg0, c_rarg1, c_rarg2, c_rarg3, ... (param regs)
 860 //      t0, t1 (temp regs)
 861 void InterpreterMacroAssembler::unlock_object(Register lock_reg)
 862 {
 863   assert(lock_reg == c_rarg1, "The argument is only for looks. It must be rarg1");
 864 








 865   if (UseHeavyMonitors) {
 866     call_VM_leaf(CAST_FROM_FN_PTR(address, InterpreterRuntime::monitorexit), lock_reg);
 867   } else {
 868     Label done;
 869 
 870     const Register swap_reg   = x10;
 871     const Register header_reg = c_rarg2;  // Will contain the old oopMark
 872     const Register obj_reg    = c_rarg3;  // Will contain the oop
 873 
 874     save_bcp(); // Save in case of exception
 875 
 876     // Convert from BasicObjectLock structure to object and BasicLock
 877     // structure Store the BasicLock address into x10
 878     la(swap_reg, Address(lock_reg, BasicObjectLock::lock_offset_in_bytes()));
 879 
 880     // Load oop into obj_reg(c_rarg3)
 881     ld(obj_reg, Address(lock_reg, BasicObjectLock::obj_offset_in_bytes()));
 882 
 883     // Free entry
 884     sd(zr, Address(lock_reg, BasicObjectLock::obj_offset_in_bytes()));
 885 
 886     // Load the old header from BasicLock structure
 887     ld(header_reg, Address(swap_reg,
 888                            BasicLock::displaced_header_offset_in_bytes()));
 889 
 890     // Test for recursion
 891     beqz(header_reg, done);
 892 
 893     // Atomic swap back the old header
 894     cmpxchg_obj_header(swap_reg, header_reg, obj_reg, t0, done, /*fallthrough*/NULL);
 895 
 896     // Call the runtime routine for slow case.
 897     sd(obj_reg, Address(lock_reg, BasicObjectLock::obj_offset_in_bytes())); // restore obj
 898     call_VM_leaf(CAST_FROM_FN_PTR(address, InterpreterRuntime::monitorexit), lock_reg);
 899 
 900     bind(done);
 901 
 902     restore_bcp();
 903   }
 904 }
 905 
 906 
 907 void InterpreterMacroAssembler::test_method_data_pointer(Register mdp,
 908                                                          Label& zero_continue) {
 909   assert(ProfileInterpreter, "must be profiling interpreter");
 910   ld(mdp, Address(fp, frame::interpreter_frame_mdp_offset * wordSize));
 911   beqz(mdp, zero_continue);
 912 }
 913 
 914 // Set the method data pointer for the current bcp.
 915 void InterpreterMacroAssembler::set_method_data_pointer_for_bcp() {
 916   assert(ProfileInterpreter, "must be profiling interpreter");
 917   Label set_mdp;
 918   push_reg(RegSet::of(x10, x11), sp); // save x10, x11
 919 
 920   // Test MDO to avoid the call if it is NULL.
 921   ld(x10, Address(xmethod, in_bytes(Method::method_data_offset())));

 761   leave();
 762   // If we're returning to interpreted code we will shortly be
 763   // adjusting SP to allow some space for ESP.  If we're returning to
 764   // compiled code the saved sender SP was saved in sender_sp, so this
 765   // restores it.
 766   andi(sp, esp, -16);
 767 }
 768 
 769 // Lock object
 770 //
 771 // Args:
 772 //      c_rarg1: BasicObjectLock to be used for locking
 773 //
 774 // Kills:
 775 //      x10
 776 //      c_rarg0, c_rarg1, c_rarg2, c_rarg3, .. (param regs)
 777 //      t0, t1 (temp regs)
 778 void InterpreterMacroAssembler::lock_object(Register lock_reg)
 779 {
 780   assert(lock_reg == c_rarg1, "The argument is only for looks. It must be c_rarg1");
 781 
 782   const Register obj_reg = c_rarg3; // Will contain the oop
 783   const int obj_offset = BasicObjectLock::obj_offset_in_bytes();
 784 
 785   // Load object pointer into obj_reg c_rarg3
 786   ld(obj_reg, Address(lock_reg, obj_offset));
 787 
 788   if (UseHeavyMonitors) {
 789     call_VM(noreg,
 790             CAST_FROM_FN_PTR(address, InterpreterRuntime::monitorenter),
 791             obj_reg);
 792   } else {
 793     Label done;
 794 
 795     const Register swap_reg = x10;
 796     const Register tmp = c_rarg2;






 797 
 798     Label slow_case;
 799 



 800     if (DiagnoseSyncOnValueBasedClasses != 0) {
 801       load_klass(tmp, obj_reg);
 802       lwu(tmp, Address(tmp, Klass::access_flags_offset()));
 803       andi(tmp, tmp, JVM_ACC_IS_VALUE_BASED_CLASS);
 804       bnez(tmp, slow_case);
 805     }
 806 
 807     ld(tmp, Address(obj_reg, oopDesc::mark_offset_in_bytes()));
 808     fast_lock(obj_reg, tmp, t0, swap_reg, t1, slow_case);
 809     j(done);

























 810 
 811     bind(slow_case);
 812 
 813     // Call the runtime routine for slow case
 814     call_VM(noreg,
 815             CAST_FROM_FN_PTR(address, InterpreterRuntime::monitorenter),
 816             obj_reg);
 817 
 818     bind(done);
 819   }
 820 }
 821 
 822 
 823 // Unlocks an object. Used in monitorexit bytecode and
 824 // remove_activation.  Throws an IllegalMonitorException if object is
 825 // not locked by current thread.
 826 //
 827 // Args:
 828 //      c_rarg1: BasicObjectLock for lock
 829 //
 830 // Kills:
 831 //      x10
 832 //      c_rarg0, c_rarg1, c_rarg2, c_rarg3, ... (param regs)
 833 //      t0, t1 (temp regs)
 834 void InterpreterMacroAssembler::unlock_object(Register lock_reg)
 835 {
 836   assert(lock_reg == c_rarg1, "The argument is only for looks. It must be rarg1");
 837 
 838   const Register obj_reg = c_rarg3; // Will contain the oop
 839 
 840   // Load oop into obj_reg(c_rarg3)
 841   ld(obj_reg, Address(lock_reg, BasicObjectLock::obj_offset_in_bytes()));
 842 
 843   // Free entry
 844   sd(zr, Address(lock_reg, BasicObjectLock::obj_offset_in_bytes()));
 845 
 846   if (UseHeavyMonitors) {
 847     call_VM_leaf(CAST_FROM_FN_PTR(address, InterpreterRuntime::monitorexit), obj_reg);
 848   } else {
 849     Label done, slow_case;
 850 
 851     const Register swap_reg   = x10;
 852     const Register header_reg = c_rarg2;  // Will contain the old oopMark

 853 
 854     save_bcp(); // Save in case of exception
 855 
 856     // Check for non-symmetric locking. This is allowed by the spec and the interpreter
 857     // must handle it.
 858     ld(header_reg, Address(xthread, Thread::lock_stack_current_offset()));
 859     bne(header_reg, obj_reg, slow_case);


 860 
 861     ld(header_reg, Address(obj_reg, oopDesc::mark_offset_in_bytes()));
 862     fast_unlock(obj_reg, header_reg, swap_reg, t0, slow_case);
 863     j(done);









 864 
 865     // Call the runtime routine for slow case.
 866     bind(slow_case);
 867     call_VM_leaf(CAST_FROM_FN_PTR(address, InterpreterRuntime::monitorexit), obj_reg);
 868 
 869     bind(done);

 870     restore_bcp();
 871   }
 872 }
 873 
 874 
 875 void InterpreterMacroAssembler::test_method_data_pointer(Register mdp,
 876                                                          Label& zero_continue) {
 877   assert(ProfileInterpreter, "must be profiling interpreter");
 878   ld(mdp, Address(fp, frame::interpreter_frame_mdp_offset * wordSize));
 879   beqz(mdp, zero_continue);
 880 }
 881 
 882 // Set the method data pointer for the current bcp.
 883 void InterpreterMacroAssembler::set_method_data_pointer_for_bcp() {
 884   assert(ProfileInterpreter, "must be profiling interpreter");
 885   Label set_mdp;
 886   push_reg(RegSet::of(x10, x11), sp); // save x10, x11
 887 
 888   // Test MDO to avoid the call if it is NULL.
 889   ld(x10, Address(xmethod, in_bytes(Method::method_data_offset())));
< prev index next >