8301036: RISC-V: Factor out functions baseOffset & baseOffset32 from MacroAssembler
Reviewed-by: luhenry, fjiang, shade
This commit is contained in:
parent
61a5f114ee
commit
ebb84ad70d
@ -260,7 +260,7 @@ void InterpreterMacroAssembler::get_cache_entry_pointer_at_bcp(Register cache,
|
||||
Register tmp,
|
||||
int bcp_offset,
|
||||
size_t index_size) {
|
||||
assert(cache != tmp, "must use different register");
|
||||
assert_different_registers(cache, tmp);
|
||||
get_cache_index_at_bcp(tmp, bcp_offset, index_size);
|
||||
assert(sizeof(ConstantPoolCacheEntry) == 4 * wordSize, "adjust code below");
|
||||
// Convert from field index to ConstantPoolCacheEntry index
|
||||
|
@ -713,33 +713,6 @@ void MacroAssembler::super_call_VM_leaf(address entry_point, Register arg_0, Reg
|
||||
MacroAssembler::call_VM_leaf_base(entry_point, 4);
|
||||
}
|
||||
|
||||
void MacroAssembler::baseOffset32(Register Rd, const Address &adr, int32_t &offset) {
|
||||
assert(Rd != noreg, "Rd must not be empty register!");
|
||||
guarantee(Rd != adr.base(), "should use different registers!");
|
||||
if (is_offset_in_range(adr.offset(), 32)) {
|
||||
int32_t imm = adr.offset();
|
||||
int32_t upper = imm, lower = imm;
|
||||
lower = (imm << 20) >> 20;
|
||||
upper -= lower;
|
||||
lui(Rd, upper);
|
||||
offset = lower;
|
||||
} else {
|
||||
offset = ((int32_t)adr.offset() << 20) >> 20;
|
||||
li(Rd, adr.offset() - offset);
|
||||
}
|
||||
add(Rd, Rd, adr.base());
|
||||
}
|
||||
|
||||
void MacroAssembler::baseOffset(Register Rd, const Address &adr, int32_t &offset) {
|
||||
if (is_offset_in_range(adr.offset(), 12)) {
|
||||
assert(Rd != noreg, "Rd must not be empty register!");
|
||||
addi(Rd, adr.base(), adr.offset());
|
||||
offset = 0;
|
||||
} else {
|
||||
baseOffset32(Rd, adr, offset);
|
||||
}
|
||||
}
|
||||
|
||||
void MacroAssembler::la(Register Rd, const address dest) {
|
||||
int64_t offset = dest - pc();
|
||||
if (is_offset_in_range(offset, 32)) {
|
||||
@ -764,9 +737,10 @@ void MacroAssembler::la(Register Rd, const Address &adr) {
|
||||
break;
|
||||
}
|
||||
case Address::base_plus_offset: {
|
||||
int32_t offset = 0;
|
||||
baseOffset(Rd, adr, offset);
|
||||
addi(Rd, Rd, offset);
|
||||
Address new_adr = legitimize_address(Rd, adr);
|
||||
if (!(new_adr.base() == Rd && new_adr.offset() == 0)) {
|
||||
addi(Rd, new_adr.base(), new_adr.offset());
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
@ -863,7 +837,7 @@ void MacroAssembler::li(Register Rd, int64_t imm) {
|
||||
if (is_imm_in_range(distance, 20, 1)) { \
|
||||
Assembler::jal(REGISTER, distance); \
|
||||
} else { \
|
||||
assert(temp != noreg, "temp must not be empty register!"); \
|
||||
assert(temp != noreg, "expecting a register"); \
|
||||
int32_t offset = 0; \
|
||||
movptr(temp, dest, offset); \
|
||||
Assembler::jalr(REGISTER, temp, offset); \
|
||||
@ -885,8 +859,8 @@ void MacroAssembler::li(Register Rd, int64_t imm) {
|
||||
break; \
|
||||
} \
|
||||
case Address::base_plus_offset: { \
|
||||
int32_t offset = 0; \
|
||||
baseOffset(temp, adr, offset); \
|
||||
int32_t offset = ((int32_t)adr.offset() << 20) >> 20; \
|
||||
la(temp, Address(adr.base(), adr.offset() - offset)); \
|
||||
Assembler::jalr(REGISTER, temp, offset); \
|
||||
break; \
|
||||
} \
|
||||
@ -2411,11 +2385,13 @@ void MacroAssembler::membar(uint32_t order_constraint) {
|
||||
// actually be used: you must use the Address that is returned. It
|
||||
// is up to you to ensure that the shift provided matches the size
|
||||
// of your data.
|
||||
Address MacroAssembler::form_address(Register Rd, Register base, long byte_offset) {
|
||||
Address MacroAssembler::form_address(Register Rd, Register base, int64_t byte_offset) {
|
||||
if (is_offset_in_range(byte_offset, 12)) { // 12: imm in range 2^12
|
||||
return Address(base, byte_offset);
|
||||
}
|
||||
|
||||
assert_different_registers(Rd, base, noreg);
|
||||
|
||||
// Do it the hard way
|
||||
mv(Rd, byte_offset);
|
||||
add(Rd, base, Rd);
|
||||
|
@ -264,7 +264,18 @@ class MacroAssembler: public Assembler {
|
||||
// actually be used: you must use the Address that is returned. It
|
||||
// is up to you to ensure that the shift provided matches the size
|
||||
// of your data.
|
||||
Address form_address(Register Rd, Register base, long byte_offset);
|
||||
Address form_address(Register Rd, Register base, int64_t byte_offset);
|
||||
|
||||
// Sometimes we get misaligned loads and stores, usually from Unsafe
|
||||
// accesses, and these can exceed the offset range.
|
||||
Address legitimize_address(Register Rd, const Address &adr) {
|
||||
if (adr.getMode() == Address::base_plus_offset) {
|
||||
if (!is_offset_in_range(adr.offset(), 12)) {
|
||||
return form_address(Rd, adr.base(), adr.offset());
|
||||
}
|
||||
}
|
||||
return adr;
|
||||
}
|
||||
|
||||
// allocation
|
||||
void tlab_allocate(
|
||||
@ -672,9 +683,6 @@ public:
|
||||
compare_and_branch_insn insn,
|
||||
compare_and_branch_label_insn neg_insn, bool is_far = false);
|
||||
|
||||
void baseOffset(Register Rd, const Address &adr, int32_t &offset);
|
||||
void baseOffset32(Register Rd, const Address &adr, int32_t &offset);
|
||||
|
||||
void la(Register Rd, Label &label);
|
||||
void la(Register Rd, const address dest);
|
||||
void la(Register Rd, const Address &adr);
|
||||
@ -797,12 +805,12 @@ public:
|
||||
if (is_offset_in_range(adr.offset(), 12)) { \
|
||||
Assembler::NAME(Rd, adr.base(), adr.offset()); \
|
||||
} else { \
|
||||
int32_t offset = 0; \
|
||||
int32_t offset = ((int32_t)adr.offset() << 20) >> 20; \
|
||||
if (Rd == adr.base()) { \
|
||||
baseOffset32(temp, adr, offset); \
|
||||
la(temp, Address(adr.base(), adr.offset() - offset)); \
|
||||
Assembler::NAME(Rd, temp, offset); \
|
||||
} else { \
|
||||
baseOffset32(Rd, adr, offset); \
|
||||
la(Rd, Address(adr.base(), adr.offset() - offset)); \
|
||||
Assembler::NAME(Rd, Rd, offset); \
|
||||
} \
|
||||
} \
|
||||
@ -855,8 +863,8 @@ public:
|
||||
if (is_offset_in_range(adr.offset(), 12)) { \
|
||||
Assembler::NAME(Rd, adr.base(), adr.offset()); \
|
||||
} else { \
|
||||
int32_t offset = 0; \
|
||||
baseOffset32(temp, adr, offset); \
|
||||
int32_t offset = ((int32_t)adr.offset() << 20) >> 20; \
|
||||
la(temp, Address(adr.base(), adr.offset() - offset)); \
|
||||
Assembler::NAME(Rd, temp, offset); \
|
||||
} \
|
||||
break; \
|
||||
@ -913,9 +921,9 @@ public:
|
||||
if (is_offset_in_range(adr.offset(), 12)) { \
|
||||
Assembler::NAME(Rs, adr.base(), adr.offset()); \
|
||||
} else { \
|
||||
int32_t offset = 0; \
|
||||
assert_different_registers(Rs, temp); \
|
||||
baseOffset32(temp, adr, offset); \
|
||||
int32_t offset = ((int32_t)adr.offset() << 20) >> 20; \
|
||||
la(temp, Address(adr.base(), adr.offset() - offset)); \
|
||||
Assembler::NAME(Rs, temp, offset); \
|
||||
} \
|
||||
break; \
|
||||
@ -957,8 +965,8 @@ public:
|
||||
if (is_offset_in_range(adr.offset(), 12)) { \
|
||||
Assembler::NAME(Rs, adr.base(), adr.offset()); \
|
||||
} else { \
|
||||
int32_t offset = 0; \
|
||||
baseOffset32(temp, adr, offset); \
|
||||
int32_t offset = ((int32_t)adr.offset() << 20) >> 20; \
|
||||
la(temp, Address(adr.base(), adr.offset() - offset)); \
|
||||
Assembler::NAME(Rs, temp, offset); \
|
||||
} \
|
||||
break; \
|
||||
@ -1322,7 +1330,7 @@ public:
|
||||
|
||||
void call(const address dest, Register temp = t0) {
|
||||
assert_cond(dest != NULL);
|
||||
assert(temp != noreg, "temp must not be empty register!");
|
||||
assert(temp != noreg, "expecting a register");
|
||||
int32_t offset = 0;
|
||||
mv(temp, dest, offset);
|
||||
jalr(x1, temp, offset);
|
||||
|
Loading…
Reference in New Issue
Block a user