diff --git a/gcc/config/aarch64/aarch64-sve.md b/gcc/config/aarch64/aarch64-sve.md index 90db51e51b9d2d8b730498983458e7bf215aa93f..06bd3e4bb2c0b31392f3483db240f92a549c441a 100644 --- a/gcc/config/aarch64/aarch64-sve.md +++ b/gcc/config/aarch64/aarch64-sve.md @@ -3088,6 +3088,23 @@ ;; - NOT ;; ------------------------------------------------------------------------- +(define_expand "ctz<mode>2" + [(set (match_operand:SVE_I 0 "register_operand") + (unspec:SVE_I + [(match_dup 2) + (ctz:SVE_I + (match_operand:SVE_I 1 "register_operand"))] + UNSPEC_PRED_X))] + "TARGET_SVE" + { + rtx pred = aarch64_ptrue_reg (<VPRED>mode); + rtx temp = gen_reg_rtx (<MODE>mode); + emit_insn (gen_aarch64_pred_rbit<mode> (temp, pred, operands[1])); + emit_insn (gen_aarch64_pred_clz<mode> (operands[0], pred, temp)); + DONE; + } +) + ;; Unpredicated integer unary arithmetic. (define_expand "<optab><mode>2" [(set (match_operand:SVE_I 0 "register_operand") diff --git a/gcc/testsuite/gcc.target/aarch64/sve/ctz.c b/gcc/testsuite/gcc.target/aarch64/sve/ctz.c new file mode 100644 index 0000000000000000000000000000000000000000..433a9174f487182098e8af05c53d71728649280e --- /dev/null +++ b/gcc/testsuite/gcc.target/aarch64/sve/ctz.c @@ -0,0 +1,49 @@ +/* { dg-final { check-function-bodies "**" "" } } */ +/* { dg-options "-O3 --param aarch64-autovec-preference=sve-only" } */ + +#include <stdint.h> + +#define FUNC(FUNCTION, NAME, DTYPE) \ +void \ +NAME (DTYPE *__restrict x, DTYPE *__restrict y, int n) { \ + for (int i = 0; i < n; i++) \ + x[i] = FUNCTION (y[i]); \ +} \ + + +/* +** ctz_uint8: +** ... +** rbit z[0-9]+\.b, p[0-7]/m, z[0-9]+\.b +** clz z[0-9]+\.b, p[0-7]/m, z[0-9]+\.b +** ... +*/ +FUNC (__builtin_ctzg, ctz_uint8, uint8_t) + +/* +** ctz_uint16: +** ... +** rbit z[0-9]+\.h, p[0-7]/m, z[0-9]+\.h +** clz z[0-9]+\.h, p[0-7]/m, z[0-9]+\.h +** ... +*/ +FUNC (__builtin_ctzg, ctz_uint16, uint16_t) + +/* +** ctz_uint32: +** ... +** rbit z[0-9]+\.s, p[0-7]/m, z[0-9]+\.s +** clz z[0-9]+\.s, p[0-7]/m, z[0-9]+\.s +** ... +*/ +FUNC (__builtin_ctz, ctz_uint32, uint32_t) + +/* +** ctz_uint64: +** ... +** rbit z[0-9]+\.d, p[0-7]/m, z[0-9]+\.d +** clz z[0-9]+\.d, p[0-7]/m, z[0-9]+\.d +** ... +*/ +FUNC (__builtin_ctzll, ctz_uint64, uint64_t) +