aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorKyrylo Tkachov <kyrylo.tkachov@arm.com>2023-04-26 15:11:11 +0100
committerKyrylo Tkachov <kyrylo.tkachov@arm.com>2023-04-26 15:11:11 +0100
commitb4c69e6b663753f41259e2e19ad03cfc11457534 (patch)
tree1330d95886c6b98ba8889abf2460a052537b1f1f /gcc
parent80afac3121778e509e1847be90a1999236cff03a (diff)
downloadgcc-b4c69e6b663753f41259e2e19ad03cfc11457534.zip
gcc-b4c69e6b663753f41259e2e19ad03cfc11457534.tar.gz
gcc-b4c69e6b663753f41259e2e19ad03cfc11457534.tar.bz2
aarch64: Reimplement RSHRN2 intrinsic patterns with standard RTL codes
Similar to the previous patch, we can reimplement the rshrn2 patterns using standard RTL codes for shift, truncate and plus with the appropriate constants. This allows us to get rid of UNSPEC_RSHRN entirely. Bootstrapped and tested on aarch64-none-linux-gnu. gcc/ChangeLog: * config/aarch64/aarch64-simd.md (aarch64_rshrn2<mode>_insn_le): Reimplement using standard RTL codes instead of unspec. (aarch64_rshrn2<mode>_insn_be): Likewise. (aarch64_rshrn2<mode>): Adjust for the above. * config/aarch64/aarch64.md (UNSPEC_RSHRN): Delete.
Diffstat (limited to 'gcc')
-rw-r--r--gcc/config/aarch64/aarch64-simd.md35
-rw-r--r--gcc/config/aarch64/aarch64.md1
2 files changed, 25 insertions, 11 deletions
diff --git a/gcc/config/aarch64/aarch64-simd.md b/gcc/config/aarch64/aarch64-simd.md
index f891310..1e72954 100644
--- a/gcc/config/aarch64/aarch64-simd.md
+++ b/gcc/config/aarch64/aarch64-simd.md
@@ -2107,23 +2107,31 @@
[(set (match_operand:<VNARROWQ2> 0 "register_operand" "=w")
(vec_concat:<VNARROWQ2>
(match_operand:<VNARROWQ> 1 "register_operand" "0")
- (unspec:<VNARROWQ> [(match_operand:VQN 2 "register_operand" "w")
- (match_operand:VQN 3 "aarch64_simd_shift_imm_vec_<vn_mode>")]
- UNSPEC_RSHRN)))]
- "TARGET_SIMD && !BYTES_BIG_ENDIAN"
- "rshrn2\\t%0.<V2ntype>, %2.<Vtype>, %3"
+ (truncate:<VNARROWQ>
+ (lshiftrt:VQN
+ (plus:VQN (match_operand:VQN 2 "register_operand" "w")
+ (match_operand:VQN 3 "aarch64_simd_rshrn_imm_vec"))
+ (match_operand:VQN 4 "aarch64_simd_shift_imm_vec_<vn_mode>")))))]
+ "TARGET_SIMD && !BYTES_BIG_ENDIAN
+ && INTVAL (CONST_VECTOR_ELT (operands[3], 0))
+ == (HOST_WIDE_INT_1 << (INTVAL (CONST_VECTOR_ELT (operands[4], 0)) - 1))"
+ "rshrn2\\t%0.<V2ntype>, %2.<Vtype>, %4"
[(set_attr "type" "neon_shift_imm_narrow_q")]
)
(define_insn "aarch64_rshrn2<mode>_insn_be"
[(set (match_operand:<VNARROWQ2> 0 "register_operand" "=w")
(vec_concat:<VNARROWQ2>
- (unspec:<VNARROWQ> [(match_operand:VQN 2 "register_operand" "w")
- (match_operand:VQN 3 "aarch64_simd_shift_imm_vec_<vn_mode>")]
- UNSPEC_RSHRN)
+ (truncate:<VNARROWQ>
+ (lshiftrt:VQN
+ (plus:VQN (match_operand:VQN 2 "register_operand" "w")
+ (match_operand:VQN 3 "aarch64_simd_rshrn_imm_vec"))
+ (match_operand:VQN 4 "aarch64_simd_shift_imm_vec_<vn_mode>")))
(match_operand:<VNARROWQ> 1 "register_operand" "0")))]
- "TARGET_SIMD && BYTES_BIG_ENDIAN"
- "rshrn2\\t%0.<V2ntype>, %2.<Vtype>, %3"
+ "TARGET_SIMD && BYTES_BIG_ENDIAN
+ && INTVAL (CONST_VECTOR_ELT (operands[3], 0))
+ == (HOST_WIDE_INT_1 << (INTVAL (CONST_VECTOR_ELT (operands[4], 0)) - 1))"
+ "rshrn2\\t%0.<V2ntype>, %2.<Vtype>, %4"
[(set_attr "type" "neon_shift_imm_narrow_q")]
)
@@ -2142,17 +2150,24 @@
}
else
{
+ rtx shft
+ = aarch64_simd_gen_const_vector_dup (<MODE>mode,
+ HOST_WIDE_INT_1U
+ << (INTVAL (operands[3]) - 1));
+
operands[3] = aarch64_simd_gen_const_vector_dup (<MODE>mode,
INTVAL (operands[3]));
if (BYTES_BIG_ENDIAN)
emit_insn (gen_aarch64_rshrn2<mode>_insn_be (operands[0],
operands[1],
operands[2],
+ shft,
operands[3]));
else
emit_insn (gen_aarch64_rshrn2<mode>_insn_le (operands[0],
operands[1],
operands[2],
+ shft,
operands[3]));
}
DONE;
diff --git a/gcc/config/aarch64/aarch64.md b/gcc/config/aarch64/aarch64.md
index 3e18f04..e1a2b26 100644
--- a/gcc/config/aarch64/aarch64.md
+++ b/gcc/config/aarch64/aarch64.md
@@ -231,7 +231,6 @@
UNSPEC_SSP_SYSREG
UNSPEC_SP_SET
UNSPEC_SP_TEST
- UNSPEC_RSHRN
UNSPEC_RSQRT
UNSPEC_RSQRTE
UNSPEC_RSQRTS