The Zvabd specification only defines vabd[u]/vwabda[u] for SEW 8 or 16.
We should not allow unsupported SEW instructions to be generated.

gcc/ChangeLog:

        * config/riscv/autovec-opt.md (*vwabda<su><mode>): Limit mode to
        VWEXTI_HS.
        (*vwabda_right<su><mode>): Ditto.
        * config/riscv/autovec.md (<su>abd<mode>3): Limit mode to VI_QH.
        * config/riscv/vector-iterators.md: New iterators.
        * config/riscv/vector.md: Limit modes in Zvabd patterns except
        vabs.

gcc/testsuite/ChangeLog:

        * gcc.target/riscv/rvv/autovec/zvabd-2.c: New test.
---
 gcc/config/riscv/autovec-opt.md               | 16 +++++-----
 gcc/config/riscv/autovec.md                   |  8 ++---
 gcc/config/riscv/vector-iterators.md          | 32 +++++++++++++++++++
 gcc/config/riscv/vector.md                    | 20 ++++++------
 .../gcc.target/riscv/rvv/autovec/zvabd-2.c    | 28 ++++++++++++++++
 5 files changed, 82 insertions(+), 22 deletions(-)
 create mode 100644 gcc/testsuite/gcc.target/riscv/rvv/autovec/zvabd-2.c

diff --git a/gcc/config/riscv/autovec-opt.md b/gcc/config/riscv/autovec-opt.md
index cc84f6336c5..d210b05a8a2 100644
--- a/gcc/config/riscv/autovec-opt.md
+++ b/gcc/config/riscv/autovec-opt.md
@@ -685,14 +685,14 @@ (define_insn_and_split 
"*single_widen_add<any_extend:su><mode>"
 [(set_attr "type" "viwalu")])
 
 (define_insn_and_split "*vwabda<su><mode>"
-  [(set (match_operand:VWEXTI 0 "register_operand" "+&vr")
-       (plus:VWEXTI
-         (zero_extend:VWEXTI
+  [(set (match_operand:VWEXTI_HS 0 "register_operand" "+&vr")
+       (plus:VWEXTI_HS
+         (zero_extend:VWEXTI_HS
            (unspec:<V_DOUBLE_TRUNC>
              [(match_operand:<V_DOUBLE_TRUNC> 1 "register_operand" "vr")
               (match_operand:<V_DOUBLE_TRUNC> 2 "register_operand" "vr")]
              UNSPEC_VABD))
-         (match_operand:VWEXTI 3 "register_operand" "0")))]
+         (match_operand:VWEXTI_HS 3 "register_operand" "0")))]
   "TARGET_ZVABD && can_create_pseudo_p ()"
   "#"
   "&& 1"
@@ -707,10 +707,10 @@ (define_insn_and_split "*vwabda<su><mode>"
 
 ;; have this since we don't canonicalize the plus in the presence of an unspec.
 (define_insn_and_split "*vwabda_right<su><mode>"
-  [(set (match_operand:VWEXTI 0 "register_operand" "+&vr")
-       (plus:VWEXTI
-         (match_operand:VWEXTI 1 "register_operand" "0")
-         (zero_extend:VWEXTI
+  [(set (match_operand:VWEXTI_HS 0 "register_operand" "+&vr")
+       (plus:VWEXTI_HS
+         (match_operand:VWEXTI_HS 1 "register_operand" "0")
+         (zero_extend:VWEXTI_HS
            (unspec:<V_DOUBLE_TRUNC>
              [(match_operand:<V_DOUBLE_TRUNC> 2 "register_operand" "vr")
               (match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" "vr")]
diff --git a/gcc/config/riscv/autovec.md b/gcc/config/riscv/autovec.md
index f6ec19d0025..964eed927c8 100644
--- a/gcc/config/riscv/autovec.md
+++ b/gcc/config/riscv/autovec.md
@@ -3080,10 +3080,10 @@ (define_expand "mask_len_strided_store_<mode>"
 ; == Absolute difference (not including sum)
 ; ========
 (define_insn_and_split "<su>abd<mode>3"
-  [(set (match_operand:V_VLSI 0 "register_operand" "=vr")
-       (unspec:V_VLSI
-        [(match_operand:V_VLSI 1 "register_operand" "vr")
-         (match_operand:V_VLSI 2 "register_operand" "vr")]
+  [(set (match_operand:VI_QH 0 "register_operand" "=vr")
+       (unspec:VI_QH
+        [(match_operand:VI_QH 1 "register_operand" "vr")
+         (match_operand:VI_QH 2 "register_operand" "vr")]
         UNSPEC_VABD))]
   "TARGET_ZVABD && can_create_pseudo_p ()"
   "#"
diff --git a/gcc/config/riscv/vector-iterators.md 
b/gcc/config/riscv/vector-iterators.md
index 3de38409342..e3ec8e519bb 100644
--- a/gcc/config/riscv/vector-iterators.md
+++ b/gcc/config/riscv/vector-iterators.md
@@ -1258,6 +1258,36 @@ (define_mode_iterator V_FRACT [
   (RVVMF2SF "TARGET_VECTOR_ELEN_FP_32 && TARGET_VECTOR_ELEN_64")
 ])
 
+(define_mode_iterator VWEXTI_HS [
+  RVVM8HI RVVM4HI RVVM2HI RVVM1HI RVVMF2HI (RVVMF4HI "TARGET_VECTOR_ELEN_64")
+
+  RVVM8SI RVVM4SI RVVM2SI RVVM1SI (RVVMF2SI "TARGET_VECTOR_ELEN_64")
+
+  (V1HI "riscv_vector::vls_mode_valid_p (V1HImode)")
+  (V2HI "riscv_vector::vls_mode_valid_p (V2HImode)")
+  (V4HI "riscv_vector::vls_mode_valid_p (V4HImode)")
+  (V8HI "riscv_vector::vls_mode_valid_p (V8HImode)")
+  (V16HI "riscv_vector::vls_mode_valid_p (V16HImode)")
+  (V32HI "riscv_vector::vls_mode_valid_p (V32HImode) && TARGET_MIN_VLEN >= 64")
+  (V64HI "riscv_vector::vls_mode_valid_p (V64HImode) && TARGET_MIN_VLEN >= 
128")
+  (V128HI "riscv_vector::vls_mode_valid_p (V128HImode) && TARGET_MIN_VLEN >= 
256")
+  (V256HI "riscv_vector::vls_mode_valid_p (V256HImode) && TARGET_MIN_VLEN >= 
512")
+  (V512HI "riscv_vector::vls_mode_valid_p (V512HImode) && TARGET_MIN_VLEN >= 
1024")
+  (V1024HI "riscv_vector::vls_mode_valid_p (V1024HImode) && TARGET_MIN_VLEN >= 
2048")
+  (V2048HI "riscv_vector::vls_mode_valid_p (V2048HImode) && TARGET_MIN_VLEN >= 
4096")
+  (V1SI "riscv_vector::vls_mode_valid_p (V1SImode)")
+  (V2SI "riscv_vector::vls_mode_valid_p (V2SImode)")
+  (V4SI "riscv_vector::vls_mode_valid_p (V4SImode)")
+  (V8SI "riscv_vector::vls_mode_valid_p (V8SImode)")
+  (V16SI "riscv_vector::vls_mode_valid_p (V16SImode) && TARGET_MIN_VLEN >= 64")
+  (V32SI "riscv_vector::vls_mode_valid_p (V32SImode) && TARGET_MIN_VLEN >= 
128")
+  (V64SI "riscv_vector::vls_mode_valid_p (V64SImode) && TARGET_MIN_VLEN >= 
256")
+  (V128SI "riscv_vector::vls_mode_valid_p (V128SImode) && TARGET_MIN_VLEN >= 
512")
+  (V256SI "riscv_vector::vls_mode_valid_p (V256SImode) && TARGET_MIN_VLEN >= 
1024")
+  (V512SI "riscv_vector::vls_mode_valid_p (V512SImode) && TARGET_MIN_VLEN >= 
2048")
+  (V1024SI "riscv_vector::vls_mode_valid_p (V1024SImode) && TARGET_MIN_VLEN >= 
4096")
+])
+
 (define_mode_iterator VWEXTI_D [
   (RVVM8DI "TARGET_VECTOR_ELEN_64") (RVVM4DI "TARGET_VECTOR_ELEN_64")
   (RVVM2DI "TARGET_VECTOR_ELEN_64") (RVVM1DI "TARGET_VECTOR_ELEN_64")
@@ -5898,6 +5928,8 @@ (define_mode_iterator V_VLSI_S [
   (V1024SI "riscv_vector::vls_mode_valid_p (V1024SImode) && TARGET_MIN_VLEN >= 
4096")
 ])
 
+(define_mode_iterator V_VLSI_SD [V_VLSI_S V_VLSI_D])
+
 (define_mode_iterator V_VLSI_S_LMULX2 [
   RVVM4SI RVVM2SI RVVM1SI (RVVMF2SI "TARGET_VECTOR_ELEN_64")
 
diff --git a/gcc/config/riscv/vector.md b/gcc/config/riscv/vector.md
index 32c0036ffa4..5225e85ed61 100644
--- a/gcc/config/riscv/vector.md
+++ b/gcc/config/riscv/vector.md
@@ -9264,8 +9264,8 @@ (define_insn "@pred_abs<mode>"
    (set (attr "avl_type_idx") (const_int 7))])
 
 (define_insn "@pred_vabd<su><mode>"
-  [(set (match_operand:V_VLSI 0 "register_operand"         "=vd, vd, vr, vr")
-       (if_then_else:V_VLSI
+  [(set (match_operand:VI_QH 0 "register_operand"          "=vd, vd, vr, vr")
+       (if_then_else:VI_QH
          (unspec:<VM>
            [(match_operand:<VM> 1 "vector_mask_operand" " vm, vm, Wc1, Wc1")
             (match_operand 5 "vector_length_operand"    " rK, rK, rK, rK")
@@ -9274,19 +9274,19 @@ (define_insn "@pred_vabd<su><mode>"
             (match_operand 8 "const_int_operand"        " i, i, i, i")
             (reg:SI VL_REGNUM)
             (reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
-         (unspec:V_VLSI
-           [(match_operand:V_VLSI 3 "register_operand" "vr,vr,vr,vr")
-            (match_operand:V_VLSI 4 "register_operand" "vr,vr,vr,vr")]
+         (unspec:VI_QH
+           [(match_operand:VI_QH 3 "register_operand" "vr,vr,vr,vr")
+            (match_operand:VI_QH 4 "register_operand" "vr,vr,vr,vr")]
            UNSPEC_VABD)
-         (match_operand:V_VLSI 2 "vector_merge_operand" "vu,0,vu,0")))]
+         (match_operand:VI_QH 2 "vector_merge_operand" "vu,0,vu,0")))]
   "TARGET_ZVABD"
   "vabd<u>.vv\t%0,%3,%4%p1"
   [(set_attr "type" "vialu")
    (set_attr "mode" "<MODE>")])
 
 (define_insn "@pred_widen_abd_plus<su><mode>"
-  [(set (match_operand:VWEXTI 0 "register_operand"      "+&vd,&vd,&vr,&vr")
-       (if_then_else:VWEXTI
+  [(set (match_operand:VWEXTI_HS 0 "register_operand"      "+&vd,&vd,&vr,&vr")
+       (if_then_else:VWEXTI_HS
          (unspec:<VM>
            [(match_operand:<VM> 1 "vector_mask_operand" "vm,vm,Wc1,Wc1")
             (match_operand 5 "vector_length_operand"    "rK,rK,rK,rK")
@@ -9295,12 +9295,12 @@ (define_insn "@pred_widen_abd_plus<su><mode>"
             (match_operand 8 "const_int_operand"      "i,i,i,i")
             (reg:SI VL_REGNUM)
             (reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
-         (unspec:VWEXTI
+         (unspec:VWEXTI_HS
            [(match_operand:<V_DOUBLE_TRUNC> 3 "register_operand" "vr,vr,vr,vr")
             (match_operand:<V_DOUBLE_TRUNC> 4 "register_operand" "vr,vr,vr,vr")
             (match_dup 0)]
            UNSPEC_VABDA)
-         (match_operand:VWEXTI 2 "vector_merge_operand" "vu,0,vu,0")))]
+         (match_operand:VWEXTI_HS 2 "vector_merge_operand" "vu,0,vu,0")))]
   "TARGET_ZVABD"
   "vwabda<u>.vv\t%0,%3,%4%p1"
   [(set_attr "type" "viwalu")
diff --git a/gcc/testsuite/gcc.target/riscv/rvv/autovec/zvabd-2.c 
b/gcc/testsuite/gcc.target/riscv/rvv/autovec/zvabd-2.c
new file mode 100644
index 00000000000..a3e624d8362
--- /dev/null
+++ b/gcc/testsuite/gcc.target/riscv/rvv/autovec/zvabd-2.c
@@ -0,0 +1,28 @@
+/* { dg-do compile } */
+/* { dg-additional-options "-march=rv64gcv_zvabd -mabi=lp64d 
-fno-vect-cost-model" } */
+
+static long
+abs64 (long i)
+{
+  return i < 0 ? -i : i;
+}
+
+__attribute__((noipa)) void
+test_abd_i32 (int *__restrict dst, int *__restrict a, int *__restrict b, int n)
+{
+  int i;
+  for (i = 0; i < n; i++)
+    dst[i] = abs64 (a[i] - b[i]);
+}
+
+__attribute__((noipa)) void
+test_wabda_i32 (long *__restrict dst, int *__restrict a, int *__restrict b,
+               int n)
+{
+  int i;
+  for (i = 0; i < n; i++)
+    dst[i] += abs64 (a[i] - b[i]);
+}
+
+/* { dg-final { scan-assembler-not {vabd\.vv} } } */
+/* { dg-final { scan-assembler-not {vwabda\.vv} } } */
-- 
2.46.0

Reply via email to