aarch64: Use VCodeConstant for f64/v128 constants (#5997)
* aarch64: Translate float and splat lowering to ISLE
I was looking into `constant_f128` and its fallback lowering into memory
and to get familiar with the code I figured it'd be good to port some
Rust logic to ISLE. This commit ports the `constant_{f128,f64,f32}`
helpers into ISLE from Rust as well as the `splat_const` helper which
ended up being closely related.
Tests reflect a number of regalloc changes that happened but also namely
one major difference is that in the lowering of `f32` a 32-bit immediate
is created now instead of a 64-bit immediate (in a GP register before
it's moved into a FP register). This semantically has no change but the
generated code is slightly different in a few minor cases.
* aarch64: Load f64/v128 constants from a pool
This commit removes the `LoadFpuConst64` and `LoadFpuConst128`
pseudo-instructions from the AArch64 backend which internally loaded a
nearby constant and then jumped over it. Constants now go through the
`VCodeConstant` infrastructure which gets placed at the end of the
function similar to how x64 works. Some minor support was added in as
well to add a new addressing mode for a `MachLabel`-relative load.
This commit is contained in:
@@ -896,7 +896,7 @@
|
||||
(CallInd
|
||||
(link WritableReg)
|
||||
(info BoxCallIndInfo))
|
||||
|
||||
|
||||
;; A pseudo-instruction that captures register arguments in vregs.
|
||||
(Args
|
||||
(args VecArgPair))
|
||||
@@ -1555,8 +1555,8 @@
|
||||
(decl u8_as_u16 (u8) u16)
|
||||
(extern constructor u8_as_u16 u8_as_u16)
|
||||
|
||||
(decl u64_as_u32 (u64) u32)
|
||||
(extern constructor u64_as_u32 u64_as_u32)
|
||||
(decl u64_truncate_to_u32 (u64) u32)
|
||||
(extern constructor u64_truncate_to_u32 u64_truncate_to_u32)
|
||||
|
||||
(decl u64_as_i16 (u64) i16)
|
||||
(extern constructor u64_as_i16 u64_as_i16)
|
||||
@@ -3000,7 +3000,7 @@
|
||||
;; 32-bit result type, any value
|
||||
(rule 5 (imm (gpr32_ty ty) n)
|
||||
(let ((dst WritableReg (temp_writable_reg ty))
|
||||
(_ Unit (emit (MInst.Mov32Imm dst (u64_as_u32 n)))))
|
||||
(_ Unit (emit (MInst.Mov32Imm dst (u64_truncate_to_u32 n)))))
|
||||
dst))
|
||||
|
||||
;; 64-bit result type, value fits in i16
|
||||
@@ -3051,7 +3051,7 @@
|
||||
;; TODO: use LZER to load 0.0
|
||||
(rule 8 (imm $F32 n)
|
||||
(let ((dst WritableReg (temp_writable_reg $F32))
|
||||
(_ Unit (emit (MInst.LoadFpuConst32 dst (u64_as_u32 n)))))
|
||||
(_ Unit (emit (MInst.LoadFpuConst32 dst (u64_truncate_to_u32 n)))))
|
||||
dst))
|
||||
|
||||
;; 64-bit floating-point type, any value. Loaded from literal pool.
|
||||
|
||||
@@ -18,7 +18,7 @@
|
||||
|
||||
;;;; Rules for `f32const` ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
|
||||
|
||||
(rule (lower (f32const (u64_from_ieee32 x)))
|
||||
(rule (lower (f32const (u32_from_ieee32 x)))
|
||||
(imm $F32 x))
|
||||
|
||||
|
||||
|
||||
@@ -436,7 +436,7 @@ impl generated_code::Context for IsleContext<'_, '_, MInst, S390xBackend> {
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn u64_as_u32(&mut self, n: u64) -> u32 {
|
||||
fn u64_truncate_to_u32(&mut self, n: u64) -> u32 {
|
||||
n as u32
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user