< prev index next >
src/cpu/aarch64/vm/macroAssembler_aarch64.hpp
Print this page
rev 8690 : 8131362: aarch64: C2 does not handle large stack offsets
Summary: change spill code to allow large offsets
Reviewed-by: duke
@@ -466,10 +466,14 @@
void movptr(Register r, uintptr_t imm64);
void mov(FloatRegister Vd, SIMD_Arrangement T, u_int32_t imm32);
+ void mov(FloatRegister Vd, SIMD_Arrangement T, FloatRegister Vn) {
+ orr(Vd, T, Vn, Vn);
+ }
+
// macro instructions for accessing and updating floating point
// status register
//
// FPSR : op1 == 011
// CRn == 0100
@@ -1159,10 +1163,49 @@
private:
// Return the effective address r + (r1 << ext) + offset.
// Uses rscratch2.
Address offsetted_address(Register r, Register r1, Address::extend ext,
int offset, int size);
+
+private:
+ // Returns an address on the stack which is reachable with a ldr/str of size
+ // Uses rscratch2 if the address is not directly reachable
+ Address spill_address(int size, int offset);
+
+public:
+ void spill(Register Rx, bool is64, int offset) {
+ if (is64) {
+ str(Rx, spill_address(8, offset));
+ } else {
+ strw(Rx, spill_address(4, offset));
+ }
+ }
+ void spill(FloatRegister Vx, SIMD_RegVariant T, int offset) {
+ str(Vx, T, spill_address(1 << (int)T, offset));
+ }
+ void unspill(Register Rx, bool is64, int offset) {
+ if (is64) {
+ ldr(Rx, spill_address(8, offset));
+ } else {
+ ldrw(Rx, spill_address(4, offset));
+ }
+ }
+ void unspill(FloatRegister Vx, SIMD_RegVariant T, int offset) {
+ ldr(Vx, T, spill_address(1 << (int)T, offset));
+ }
+ void spill_copy128(int src_offset, int dst_offset) {
+ if (src_offset < 512 && (src_offset & 7) == 0 &&
+ dst_offset < 512 && (dst_offset & 7) == 0) {
+ ldp(rscratch1, rscratch2, Address(sp, src_offset));
+ stp(rscratch1, rscratch2, Address(sp, dst_offset));
+ } else {
+ unspill(rscratch1, true, src_offset);
+ spill(rscratch1, true, dst_offset);
+ unspill(rscratch1, true, src_offset+4);
+ spill(rscratch1, true, dst_offset+4);
+ }
+ }
};
#ifdef ASSERT
inline bool AbstractAssembler::pd_check_instruction_mark() { return false; }
#endif
< prev index next >