Hi,
This patch adds support for move an immediate DImode value into an AdvSIMD
scalar D register. i.e. movi Dd, #imm.
Regression-tested on aarch64-none-elf. OK for aarch64-branch?
Thanks,
Tejas Belagod.
ARM.
Changelog:
2012-09-10 Tejas Belagod <tejas.bela...@arm.com>
gcc/
* config/aarch64/aarch64-protos.h (aarch64_simd_imm_scalar_p): Declare.
* config/aarch64/aarch64.c (aarch64_simd_imm_scalar_p): New.
* config/aarch64/aarch64.md (*movdi_aarch64): Add alternative for moving
valid scalar immediate into a Advanved SIMD D-register.
* config/aarch64/constraints.md (Dd): New.
diff --git a/gcc/config/aarch64/aarch64-protos.h
b/gcc/config/aarch64/aarch64-protos.h
index afb8b1e..e6d35e4 100644
--- a/gcc/config/aarch64/aarch64-protos.h
+++ b/gcc/config/aarch64/aarch64-protos.h
@@ -178,6 +178,7 @@ bool aarch64_pad_arg_upward (enum machine_mode, const_tree);
bool aarch64_pad_reg_upward (enum machine_mode, const_tree, bool);
bool aarch64_regno_ok_for_base_p (int, bool);
bool aarch64_regno_ok_for_index_p (int, bool);
+bool aarch64_simd_imm_scalar_p (rtx x, enum machine_mode mode);
bool aarch64_simd_imm_zero_p (rtx, enum machine_mode);
bool aarch64_simd_shift_imm_p (rtx, enum machine_mode, bool);
bool aarch64_symbolic_address_p (rtx);
diff --git a/gcc/config/aarch64/aarch64.c b/gcc/config/aarch64/aarch64.c
index 10af252..b90be6d 100644
--- a/gcc/config/aarch64/aarch64.c
+++ b/gcc/config/aarch64/aarch64.c
@@ -6508,6 +6508,23 @@ aarch64_simd_imm_zero_p (rtx x, enum machine_mode mode)
return true;
}
+bool
+aarch64_simd_imm_scalar_p (rtx x, enum machine_mode mode ATTRIBUTE_UNUSED)
+{
+ HOST_WIDE_INT imm = INTVAL (x);
+ int i;
+
+ for (i = 0; i < 8; i++)
+ {
+ unsigned int byte = imm & 0xff;
+ if (byte != 0xff && byte != 0)
+ return false;
+ imm >>= 8;
+ }
+
+ return true;
+}
+
/* Return a const_int vector of VAL. */
rtx
aarch64_simd_gen_const_vector_dup (enum machine_mode mode, int val)
diff --git a/gcc/config/aarch64/aarch64.md b/gcc/config/aarch64/aarch64.md
index 8f52ed4..78a71fe 100644
--- a/gcc/config/aarch64/aarch64.md
+++ b/gcc/config/aarch64/aarch64.md
@@ -950,8 +950,8 @@
)
(define_insn "*movdi_aarch64"
- [(set (match_operand:DI 0 "nonimmediate_operand" "=r,k,r,r,r,m, r, r, *w,
r,*w")
- (match_operand:DI 1 "aarch64_mov_operand" "
r,r,k,N,m,rZ,Usa,Ush,rZ,*w,*w"))]
+ [(set (match_operand:DI 0 "nonimmediate_operand" "=r,k,r,r,r,m, r, r, *w,
r,*w,w")
+ (match_operand:DI 1 "aarch64_mov_operand" "
r,r,k,N,m,rZ,Usa,Ush,rZ,*w,*w,Dd"))]
"(register_operand (operands[0], DImode)
|| aarch64_reg_or_zero (operands[1], DImode))"
"@
@@ -965,10 +965,11 @@
adrp\\t%x0, %A1
fmov\\t%d0, %x1
fmov\\t%x0, %d1
- fmov\\t%d0, %d1"
- [(set_attr "v8type" "move,move,move,alu,load1,store1,adr,adr,fmov,fmov,fmov")
+ fmov\\t%d0, %d1
+ movi\\t%d0, %1"
+ [(set_attr "v8type"
"move,move,move,alu,load1,store1,adr,adr,fmov,fmov,fmov,fmov")
(set_attr "mode" "DI")
- (set_attr "fp" "*,*,*,*,*,*,*,*,yes,yes,yes")]
+ (set_attr "fp" "*,*,*,*,*,*,*,*,yes,yes,yes,yes")]
)
(define_insn "insv_imm<mode>"
diff --git a/gcc/config/aarch64/constraints.md
b/gcc/config/aarch64/constraints.md
index 267b0b8..fe61307 100644
--- a/gcc/config/aarch64/constraints.md
+++ b/gcc/config/aarch64/constraints.md
@@ -159,3 +159,9 @@
A constraint that matches vector of immediate zero."
(and (match_code "const_vector")
(match_test "aarch64_simd_imm_zero_p (op, GET_MODE (op))")))
+
+(define_constraint "Dd"
+ "@internal
+ A constraint that matches an immediate operand valid for AdvSIMD scalar."
+ (and (match_code "const_int")
+ (match_test "aarch64_simd_imm_scalar_p (op, GET_MODE (op))")))