8294492: RISC-V: Use li instead of patchable movptr at non-patchable callsites

Reviewed-by: fyang
This commit is contained in:
Xiaolin Zheng 2022-09-29 07:21:07 +00:00 committed by Fei Yang
parent 8491fd5c12
commit 1decdcee71
8 changed files with 51 additions and 82 deletions

View file

@ -187,30 +187,6 @@ void Assembler::li32(Register Rd, int32_t imm) {
#undef INSN #undef INSN
void Assembler::ret() {
jalr(x0, x1, 0);
}
#define INSN(NAME, REGISTER) \
void Assembler::NAME(const address &dest, Register temp) { \
assert_cond(dest != NULL); \
assert(temp != noreg, "temp must not be empty register!"); \
int64_t distance = dest - pc(); \
if (is_offset_in_range(distance, 32)) { \
auipc(temp, distance + 0x800); \
jalr(REGISTER, temp, ((int32_t)distance << 20) >> 20); \
} else { \
int32_t offset = 0; \
movptr(temp, dest, offset); \
jalr(REGISTER, temp, offset); \
} \
}
INSN(call, x1);
INSN(tail, x0);
#undef INSN
#define INSN(NAME, REGISTER) \ #define INSN(NAME, REGISTER) \
void Assembler::NAME(const Address &adr, Register temp) { \ void Assembler::NAME(const Address &adr, Register temp) { \
switch (adr.getMode()) { \ switch (adr.getMode()) { \
@ -232,8 +208,6 @@ void Assembler::ret() {
INSN(j, x0); INSN(j, x0);
INSN(jal, x1); INSN(jal, x1);
INSN(call, x1);
INSN(tail, x0);
#undef INSN #undef INSN

View file

@ -302,7 +302,8 @@ public:
lui(Rd, upper); lui(Rd, upper);
offset = lower; offset = lower;
} else { } else {
movptr(Rd, (address)(uintptr_t)adr.offset(), offset); offset = ((int32_t)adr.offset() << 20) >> 20;
li(Rd, adr.offset() - offset);
} }
add(Rd, Rd, adr.base()); add(Rd, Rd, adr.base());
} }
@ -331,17 +332,6 @@ public:
void jal(const Address &adr, Register temp = t0); void jal(const Address &adr, Register temp = t0);
void jr(Register Rs); void jr(Register Rs);
void jalr(Register Rs); void jalr(Register Rs);
void ret();
void call(const address &dest, Register temp = t0);
void call(const Address &adr, Register temp = t0);
void tail(const address &dest, Register temp = t0);
void tail(const Address &adr, Register temp = t0);
void call(Label &l, Register temp) {
call(target(l), temp);
}
void tail(Label &l, Register temp) {
tail(target(l), temp);
}
static inline uint32_t extract(uint32_t val, unsigned msb, unsigned lsb) { static inline uint32_t extract(uint32_t val, unsigned msb, unsigned lsb) {
assert_cond(msb >= lsb && msb <= 31); assert_cond(msb >= lsb && msb <= 31);

View file

@ -282,24 +282,25 @@ void ShenandoahBarrierSetAssembler::load_reference_barrier(MacroAssembler* masm,
} }
__ push_call_clobbered_registers(); __ push_call_clobbered_registers();
address target = NULL;
if (is_strong) { if (is_strong) {
if (is_narrow) { if (is_narrow) {
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong_narrow)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong_narrow);
} else { } else {
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong);
} }
} else if (is_weak) { } else if (is_weak) {
if (is_narrow) { if (is_narrow) {
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak_narrow)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak_narrow);
} else { } else {
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak);
} }
} else { } else {
assert(is_phantom, "only remaining strength"); assert(is_phantom, "only remaining strength");
assert(!is_narrow, "phantom access cannot be narrow"); assert(!is_narrow, "phantom access cannot be narrow");
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak);
} }
__ jalr(ra); __ call(target);
__ mv(t0, x10); __ mv(t0, x10);
__ pop_call_clobbered_registers(); __ pop_call_clobbered_registers();
__ mv(x10, t0); __ mv(x10, t0);
@ -679,29 +680,30 @@ void ShenandoahBarrierSetAssembler::generate_c1_load_reference_barrier_runtime_s
bool is_weak = ShenandoahBarrierSet::is_weak_access(decorators); bool is_weak = ShenandoahBarrierSet::is_weak_access(decorators);
bool is_phantom = ShenandoahBarrierSet::is_phantom_access(decorators); bool is_phantom = ShenandoahBarrierSet::is_phantom_access(decorators);
bool is_native = ShenandoahBarrierSet::is_native_access(decorators); bool is_native = ShenandoahBarrierSet::is_native_access(decorators);
address target = NULL;
if (is_strong) { if (is_strong) {
if (is_native) { if (is_native) {
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong);
} else { } else {
if (UseCompressedOops) { if (UseCompressedOops) {
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong_narrow)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong_narrow);
} else { } else {
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_strong);
} }
} }
} else if (is_weak) { } else if (is_weak) {
assert(!is_native, "weak must not be called off-heap"); assert(!is_native, "weak must not be called off-heap");
if (UseCompressedOops) { if (UseCompressedOops) {
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak_narrow)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak_narrow);
} else { } else {
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_weak);
} }
} else { } else {
assert(is_phantom, "only remaining strength"); assert(is_phantom, "only remaining strength");
assert(is_native, "phantom must only be called off-heap"); assert(is_native, "phantom must only be called off-heap");
__ mv(ra, CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_phantom)); target = CAST_FROM_FN_PTR(address, ShenandoahRuntime::load_reference_barrier_phantom);
} }
__ jalr(ra); __ call(target);
__ mv(t0, x10); __ mv(t0, x10);
__ pop_call_clobbered_registers(); __ pop_call_clobbered_registers();
__ mv(x10, t0); __ mv(x10, t0);

View file

@ -563,10 +563,8 @@ void MacroAssembler::emit_static_call_stub() {
void MacroAssembler::call_VM_leaf_base(address entry_point, void MacroAssembler::call_VM_leaf_base(address entry_point,
int number_of_arguments, int number_of_arguments,
Label *retaddr) { Label *retaddr) {
int32_t offset = 0;
push_reg(RegSet::of(t0, xmethod), sp); // push << t0 & xmethod >> to sp push_reg(RegSet::of(t0, xmethod), sp); // push << t0 & xmethod >> to sp
movptr(t0, entry_point, offset); call(entry_point);
jalr(x1, t0, offset);
if (retaddr != NULL) { if (retaddr != NULL) {
bind(*retaddr); bind(*retaddr);
} }

View file

@ -527,12 +527,18 @@ public:
} }
// mv // mv
void mv(Register Rd, address addr) { li(Rd, (int64_t)addr); } void mv(Register Rd, address addr) { li(Rd, (int64_t)addr); }
void mv(Register Rd, address addr, int32_t &offset) {
// Split address into a lower 12-bit sign-extended offset and the remainder,
// so that the offset could be encoded in jalr or load/store instruction.
offset = ((int32_t)(int64_t)addr << 20) >> 20;
li(Rd, (int64_t)addr - offset);
}
template<typename T, ENABLE_IF(std::is_integral<T>::value)> template<typename T, ENABLE_IF(std::is_integral<T>::value)>
inline void mv(Register Rd, T o) { li(Rd, (int64_t)o); } inline void mv(Register Rd, T o) { li(Rd, (int64_t)o); }
inline void mvw(Register Rd, int32_t imm32) { mv(Rd, imm32); } inline void mvw(Register Rd, int32_t imm32) { mv(Rd, imm32); }
void mv(Register Rd, Address dest); void mv(Register Rd, Address dest);
void mv(Register Rd, RegisterOrConstant src); void mv(Register Rd, RegisterOrConstant src);
@ -890,6 +896,18 @@ public:
void rt_call(address dest, Register tmp = t0); void rt_call(address dest, Register tmp = t0);
void call(const address dest, Register temp = t0) {
assert_cond(dest != NULL);
assert(temp != noreg, "temp must not be empty register!");
int32_t offset = 0;
mv(temp, dest, offset);
jalr(x1, temp, offset);
}
void ret() {
jalr(x0, x1, 0);
}
private: private:
#ifdef ASSERT #ifdef ASSERT

View file

@ -651,9 +651,7 @@ class StubGenerator: public StubCodeGenerator {
assert(frame::arg_reg_save_area_bytes == 0, "not expecting frame reg save area"); assert(frame::arg_reg_save_area_bytes == 0, "not expecting frame reg save area");
#endif #endif
BLOCK_COMMENT("call MacroAssembler::debug"); BLOCK_COMMENT("call MacroAssembler::debug");
int32_t offset = 0; __ call(CAST_FROM_FN_PTR(address, MacroAssembler::debug64));
__ movptr(t0, CAST_FROM_FN_PTR(address, MacroAssembler::debug64), offset);
__ jalr(x1, t0, offset);
__ ebreak(); __ ebreak();
return start; return start;
@ -3740,9 +3738,7 @@ class StubGenerator: public StubCodeGenerator {
} }
__ mv(c_rarg0, xthread); __ mv(c_rarg0, xthread);
BLOCK_COMMENT("call runtime_entry"); BLOCK_COMMENT("call runtime_entry");
int32_t offset = 0; __ call(runtime_entry);
__ movptr(t0, runtime_entry, offset);
__ jalr(x1, t0, offset);
// Generate oop map // Generate oop map
OopMap* map = new OopMap(framesize, 0); OopMap* map = new OopMap(framesize, 0);

View file

@ -190,8 +190,7 @@ address TemplateInterpreterGenerator::generate_math_entry(AbstractInterpreter::M
} else { } else {
fn = CAST_FROM_FN_PTR(address, StubRoutines::dsin()); fn = CAST_FROM_FN_PTR(address, StubRoutines::dsin());
} }
__ mv(t0, fn); __ call(fn);
__ jalr(t0);
break; break;
case Interpreter::java_lang_math_cos : case Interpreter::java_lang_math_cos :
entry_point = __ pc(); entry_point = __ pc();
@ -204,8 +203,7 @@ address TemplateInterpreterGenerator::generate_math_entry(AbstractInterpreter::M
} else { } else {
fn = CAST_FROM_FN_PTR(address, StubRoutines::dcos()); fn = CAST_FROM_FN_PTR(address, StubRoutines::dcos());
} }
__ mv(t0, fn); __ call(fn);
__ jalr(t0);
break; break;
case Interpreter::java_lang_math_tan : case Interpreter::java_lang_math_tan :
entry_point = __ pc(); entry_point = __ pc();
@ -218,8 +216,7 @@ address TemplateInterpreterGenerator::generate_math_entry(AbstractInterpreter::M
} else { } else {
fn = CAST_FROM_FN_PTR(address, StubRoutines::dtan()); fn = CAST_FROM_FN_PTR(address, StubRoutines::dtan());
} }
__ mv(t0, fn); __ call(fn);
__ jalr(t0);
break; break;
case Interpreter::java_lang_math_log : case Interpreter::java_lang_math_log :
entry_point = __ pc(); entry_point = __ pc();
@ -232,8 +229,7 @@ address TemplateInterpreterGenerator::generate_math_entry(AbstractInterpreter::M
} else { } else {
fn = CAST_FROM_FN_PTR(address, StubRoutines::dlog()); fn = CAST_FROM_FN_PTR(address, StubRoutines::dlog());
} }
__ mv(t0, fn); __ call(fn);
__ jalr(t0);
break; break;
case Interpreter::java_lang_math_log10 : case Interpreter::java_lang_math_log10 :
entry_point = __ pc(); entry_point = __ pc();
@ -246,8 +242,7 @@ address TemplateInterpreterGenerator::generate_math_entry(AbstractInterpreter::M
} else { } else {
fn = CAST_FROM_FN_PTR(address, StubRoutines::dlog10()); fn = CAST_FROM_FN_PTR(address, StubRoutines::dlog10());
} }
__ mv(t0, fn); __ call(fn);
__ jalr(t0);
break; break;
case Interpreter::java_lang_math_exp : case Interpreter::java_lang_math_exp :
entry_point = __ pc(); entry_point = __ pc();
@ -260,8 +255,7 @@ address TemplateInterpreterGenerator::generate_math_entry(AbstractInterpreter::M
} else { } else {
fn = CAST_FROM_FN_PTR(address, StubRoutines::dexp()); fn = CAST_FROM_FN_PTR(address, StubRoutines::dexp());
} }
__ mv(t0, fn); __ call(fn);
__ jalr(t0);
break; break;
case Interpreter::java_lang_math_pow : case Interpreter::java_lang_math_pow :
entry_point = __ pc(); entry_point = __ pc();
@ -275,8 +269,7 @@ address TemplateInterpreterGenerator::generate_math_entry(AbstractInterpreter::M
} else { } else {
fn = CAST_FROM_FN_PTR(address, StubRoutines::dpow()); fn = CAST_FROM_FN_PTR(address, StubRoutines::dpow());
} }
__ mv(t0, fn); __ call(fn);
__ jalr(t0);
break; break;
case Interpreter::java_lang_math_fmaD : case Interpreter::java_lang_math_fmaD :
if (UseFMA) { if (UseFMA) {
@ -1169,8 +1162,7 @@ address TemplateInterpreterGenerator::generate_native_entry(bool synchronized) {
// hand. // hand.
// //
__ mv(c_rarg0, xthread); __ mv(c_rarg0, xthread);
__ mv(t1, CAST_FROM_FN_PTR(address, JavaThread::check_special_condition_for_native_trans)); __ call(CAST_FROM_FN_PTR(address, JavaThread::check_special_condition_for_native_trans));
__ jalr(t1);
__ get_method(xmethod); __ get_method(xmethod);
__ reinit_heapbase(); __ reinit_heapbase();
__ bind(Continue); __ bind(Continue);
@ -1219,8 +1211,7 @@ address TemplateInterpreterGenerator::generate_native_entry(bool synchronized) {
__ push_call_clobbered_registers(); __ push_call_clobbered_registers();
__ mv(c_rarg0, xthread); __ mv(c_rarg0, xthread);
__ mv(t1, CAST_FROM_FN_PTR(address, SharedRuntime::reguard_yellow_pages)); __ call(CAST_FROM_FN_PTR(address, SharedRuntime::reguard_yellow_pages));
__ jalr(t1);
__ pop_call_clobbered_registers(); __ pop_call_clobbered_registers();
__ bind(no_reguard); __ bind(no_reguard);
} }

View file

@ -387,7 +387,7 @@ void TemplateTable::fast_aldc(bool wide) {
// Stash null_sentinel address to get its value later // Stash null_sentinel address to get its value later
int32_t offset = 0; int32_t offset = 0;
__ movptr(rarg, Universe::the_null_sentinel_addr(), offset); __ mv(rarg, Universe::the_null_sentinel_addr(), offset);
__ ld(tmp, Address(rarg, offset)); __ ld(tmp, Address(rarg, offset));
__ resolve_oop_handle(tmp, x15, t1); __ resolve_oop_handle(tmp, x15, t1);
__ bne(result, tmp, notNull); __ bne(result, tmp, notNull);