https://gcc.gnu.org/g:f702b593e7268ab161053bafd097f1b09933b783

commit r16-2731-gf702b593e7268ab161053bafd097f1b09933b783
Author: Richard Sandiford <richard.sandif...@arm.com>
Date:   Mon Aug 4 11:45:28 2025 +0100

    aarch64: Use VNx16BI for more SVE WHILE* results [PR121118]
    
    PR121118 is about a case where we try to construct a predicate
    constant using a permutation of a PFALSE and a WHILELO.  The WHILELO
    is a .H operation and its result has mode VNx8BI.  However, the
    permute instruction expects both inputs to be VNx16BI, leading to
    an unrecognisable insn ICE.
    
    VNx8BI is effectively a form of VNx16BI in which every odd-indexed
    bit is insignificant.  In the PR's testcase that's OK, since those
    bits will be dropped by the permutation.  But if the WHILELO had been a
    VNx4BI, so that only every fourth bit is significant, the input to the
    permutation would have had undefined bits.  The testcase in the patch
    has an example of this.
    
    This feeds into a related ACLE problem that I'd been meaning to
    fix for a long time: every bit of an svbool_t result is significant,
    and so every ACLE intrinsic that returns an svbool_t should return a
    VNx16BI.  That doesn't currently happen for ACLE svwhile* intrinsics.
    
    This patch fixes both issues together.
    
    We still need to keep the current WHILE* patterns for autovectorisation,
    where the result mode should match the element width.  The patch
    therefore adds a new set of patterns that are defined to return
    VNx16BI instead.  For want of a better scheme, it uses an "_acle"
    suffix to distinguish these new patterns from the "normal" ones.
    
    The formulation used is:
    
      (and:VNx16BI (subreg:VNx16BI normal-pattern 0) C)
    
    where C has mode VNx16BI and is a canonical ptrue for normal-pattern's
    element width (so that the low bit of each element is set and the upper
    bits are clear).
    
    This is a bit clunky, and leads to some repetition.  But it has two
    advantages:
    
    * After g:965564eafb721f8000013a3112f1bba8d8fae32b, converting the
      above expression back to normal-pattern's mode will reduce to
      normal-pattern, so that the pattern for testing the result using a
      PTEST doesn't change.
    
    * It gives RTL optimisers a bit more information, as the new tests
      demonstrate.
    
    In the expression above, C is matched using a new "special" predicate
    aarch64_ptrue_all_operand, where "special" means that the mode on the
    predicate is not necessarily the mode of the expression.  In this case,
    C always has mode VNx16BI, but the mode on the predicate indicates which
    kind of canonical PTRUE is needed.
    
    gcc/
            PR testsuite/121118
            * config/aarch64/iterators.md (VNx16BI_ONLY): New mode iterator.
            * config/aarch64/predicates.md (aarch64_ptrue_all_operand): New
            predicate.
            * config/aarch64/aarch64-sve.md
            
(@aarch64_sve_while_<while_optab_cmp><GPI:mode><VNx16BI_ONLY:mode>_acle)
            (@aarch64_sve_while_<while_optab_cmp><GPI:mode><PRED_HSD:mode>_acle)
            (*aarch64_sve_while_<while_optab_cmp><GPI:mode><PRED_HSD:mode>_acle)
            (*while_<while_optab_cmp><GPI:mode><PRED_HSD:mode>_acle_cc): New
            patterns.
            * config/aarch64/aarch64-sve-builtins-functions.h
            (while_comparison::expand): Use the new _acle patterns that
            always return a VNx16BI.
            * config/aarch64/aarch64-sve-builtins-sve2.cc
            (svwhilerw_svwhilewr_impl::expand): Likewise.
            * config/aarch64/aarch64.cc
            (aarch64_sve_move_pred_via_while): Likewise.
    
    gcc/testsuite/
            PR testsuite/121118
            * gcc.target/aarch64/sve/acle/general/pr121118_1.c: New test.
            * gcc.target/aarch64/sve/acle/general/whilele_13.c: Likewise.
            * gcc.target/aarch64/sve/acle/general/whilelt_6.c: Likewise.
            * gcc.target/aarch64/sve2/acle/general/whilege_1.c: Likewise.
            * gcc.target/aarch64/sve2/acle/general/whilegt_1.c: Likewise.
            * gcc.target/aarch64/sve2/acle/general/whilerw_5.c: Likewise.
            * gcc.target/aarch64/sve2/acle/general/whilewr_5.c: Likewise.

Diff:
---
 .../aarch64/aarch64-sve-builtins-functions.h       |   3 +-
 gcc/config/aarch64/aarch64-sve-builtins-sve2.cc    |   4 +-
 gcc/config/aarch64/aarch64-sve.md                  |  84 +++++++++++++
 gcc/config/aarch64/aarch64.cc                      |   6 +-
 gcc/config/aarch64/iterators.md                    |   1 +
 gcc/config/aarch64/predicates.md                   |   6 +
 .../aarch64/sve/acle/general/pr121118_1.c          |  16 +++
 .../aarch64/sve/acle/general/whilele_13.c          | 130 +++++++++++++++++++++
 .../aarch64/sve/acle/general/whilelt_6.c           | 130 +++++++++++++++++++++
 .../aarch64/sve2/acle/general/whilege_1.c          | 130 +++++++++++++++++++++
 .../aarch64/sve2/acle/general/whilegt_1.c          | 130 +++++++++++++++++++++
 .../aarch64/sve2/acle/general/whilerw_5.c          | 130 +++++++++++++++++++++
 .../aarch64/sve2/acle/general/whilewr_5.c          | 130 +++++++++++++++++++++
 13 files changed, 895 insertions(+), 5 deletions(-)

diff --git a/gcc/config/aarch64/aarch64-sve-builtins-functions.h 
b/gcc/config/aarch64/aarch64-sve-builtins-functions.h
index 6f1c6948df29..b0cfa703dc48 100644
--- a/gcc/config/aarch64/aarch64-sve-builtins-functions.h
+++ b/gcc/config/aarch64/aarch64-sve-builtins-functions.h
@@ -838,7 +838,8 @@ public:
 
     machine_mode pred_mode = e.vector_mode (0);
     scalar_mode reg_mode = GET_MODE_INNER (e.vector_mode (1));
-    return e.use_exact_insn (code_for_while (unspec, reg_mode, pred_mode));
+    auto icode = code_for_aarch64_sve_while_acle (unspec, reg_mode, pred_mode);
+    return e.use_exact_insn (icode);
   }
 
   /* The unspec codes associated with signed and unsigned operations
diff --git a/gcc/config/aarch64/aarch64-sve-builtins-sve2.cc 
b/gcc/config/aarch64/aarch64-sve-builtins-sve2.cc
index 73004a8fd5c5..95c5ed81d610 100644
--- a/gcc/config/aarch64/aarch64-sve-builtins-sve2.cc
+++ b/gcc/config/aarch64/aarch64-sve-builtins-sve2.cc
@@ -881,7 +881,9 @@ public:
   {
     for (unsigned int i = 0; i < 2; ++i)
       e.args[i] = e.convert_to_pmode (e.args[i]);
-    return e.use_exact_insn (code_for_while (m_unspec, Pmode, e.gp_mode (0)));
+    auto icode = code_for_aarch64_sve_while_acle (m_unspec, Pmode,
+                                                 e.gp_mode (0));
+    return e.use_exact_insn (icode);
   }
 
   int m_unspec;
diff --git a/gcc/config/aarch64/aarch64-sve.md 
b/gcc/config/aarch64/aarch64-sve.md
index 80a32889f8cf..e8c9b67a077d 100644
--- a/gcc/config/aarch64/aarch64-sve.md
+++ b/gcc/config/aarch64/aarch64-sve.md
@@ -8584,6 +8584,58 @@
   "while<cmp_op>\t%0.<PRED_ALL:Vetype>, %<w>1, %<w>2"
 )
 
+;; Likewise, but yield a VNx16BI result regardless of the element width.
+;; The .b case is equivalent to the above.
+(define_expand 
"@aarch64_sve_while_<while_optab_cmp><GPI:mode><VNx16BI_ONLY:mode>_acle"
+  [(parallel
+     [(set (match_operand:VNx16BI_ONLY 0 "register_operand")
+          (unspec:VNx16BI_ONLY
+            [(const_int SVE_WHILE_B)
+             (match_operand:GPI 1 "aarch64_reg_or_zero")
+             (match_operand:GPI 2 "aarch64_reg_or_zero")]
+            SVE_WHILE))
+      (clobber (reg:CC_NZC CC_REGNUM))])]
+  "TARGET_SVE"
+)
+
+;; For wider elements, bitcast the predicate result to a VNx16BI and use
+;; an (and ...) to indicate that only every second, fourth, or eighth bit
+;; is set.
+(define_expand 
"@aarch64_sve_while_<while_optab_cmp><GPI:mode><PRED_HSD:mode>_acle"
+  [(parallel
+     [(set (match_operand:VNx16BI 0 "register_operand")
+          (and:VNx16BI
+            (subreg:VNx16BI
+              (unspec:PRED_HSD
+                [(const_int SVE_WHILE_B)
+                 (match_operand:GPI 1 "aarch64_reg_or_zero")
+                 (match_operand:GPI 2 "aarch64_reg_or_zero")]
+                SVE_WHILE)
+              0)
+            (match_dup 3)))
+      (clobber (reg:CC_NZC CC_REGNUM))])]
+  "TARGET_SVE"
+  {
+    operands[3] = aarch64_ptrue_all (<data_bytes>);
+  }
+)
+
+(define_insn 
"*aarch64_sve_while_<while_optab_cmp><GPI:mode><PRED_HSD:mode>_acle"
+  [(set (match_operand:VNx16BI 0 "register_operand" "=Upa")
+       (and:VNx16BI
+         (subreg:VNx16BI
+           (unspec:PRED_HSD
+             [(const_int SVE_WHILE_B)
+              (match_operand:GPI 1 "aarch64_reg_or_zero" "rZ")
+              (match_operand:GPI 2 "aarch64_reg_or_zero" "rZ")]
+             SVE_WHILE)
+           0)
+         (match_operand:PRED_HSD 3 "aarch64_ptrue_all_operand")))
+   (clobber (reg:CC_NZC CC_REGNUM))]
+  "TARGET_SVE"
+  "while<cmp_op>\t%0.<PRED_HSD:Vetype>, %<w>1, %<w>2"
+)
+
 ;; The WHILE instructions set the flags in the same way as a PTEST with
 ;; a PTRUE GP.  Handle the case in which both results are useful.  The GP
 ;; operands to the PTEST aren't needed, so we allow them to be anything.
@@ -8615,6 +8667,38 @@
   }
 )
 
+(define_insn_and_rewrite 
"*while_<while_optab_cmp><GPI:mode><PRED_HSD:mode>_acle_cc"
+  [(set (reg:CC_NZC CC_REGNUM)
+       (unspec:CC_NZC
+         [(match_operand 3)
+          (match_operand 4)
+          (const_int SVE_KNOWN_PTRUE)
+          (unspec:PRED_HSD
+            [(const_int SVE_WHILE_B)
+             (match_operand:GPI 1 "aarch64_reg_or_zero" "rZ")
+             (match_operand:GPI 2 "aarch64_reg_or_zero" "rZ")]
+            SVE_WHILE)]
+         UNSPEC_PTEST))
+   (set (match_operand:VNx16BI 0 "register_operand" "=Upa")
+       (and:VNx16BI
+         (subreg:VNx16BI
+           (unspec:PRED_HSD [(const_int SVE_WHILE_B)
+                             (match_dup 1)
+                             (match_dup 2)]
+                            SVE_WHILE)
+           0)
+         (match_operand:PRED_HSD 5 "aarch64_ptrue_all_operand")))]
+  "TARGET_SVE"
+  "while<cmp_op>\t%0.<PRED_HSD:Vetype>, %<w>1, %<w>2"
+  ;; Force the compiler to drop the unused predicate operand, so that we
+  ;; don't have an unnecessary PTRUE.
+  "&& (!CONSTANT_P (operands[3]) || !CONSTANT_P (operands[4]))"
+  {
+    operands[3] = CONSTM1_RTX (VNx16BImode);
+    operands[4] = CONSTM1_RTX (<PRED_HSD:MODE>mode);
+  }
+)
+
 ;; Same, but handle the case in which only the flags result is useful.
 (define_insn_and_rewrite 
"@while_<while_optab_cmp><GPI:mode><PRED_ALL:mode>_ptest"
   [(set (reg:CC_NZC CC_REGNUM)
diff --git a/gcc/config/aarch64/aarch64.cc b/gcc/config/aarch64/aarch64.cc
index f4a2062b042a..39171cf171a3 100644
--- a/gcc/config/aarch64/aarch64.cc
+++ b/gcc/config/aarch64/aarch64.cc
@@ -6069,9 +6069,9 @@ aarch64_sve_move_pred_via_while (rtx target, machine_mode 
mode,
                                 unsigned int vl)
 {
   rtx limit = force_reg (DImode, gen_int_mode (vl, DImode));
-  target = aarch64_target_reg (target, mode);
-  emit_insn (gen_while (UNSPEC_WHILELO, DImode, mode,
-                       target, const0_rtx, limit));
+  target = aarch64_target_reg (target, VNx16BImode);
+  emit_insn (gen_aarch64_sve_while_acle (UNSPEC_WHILELO, DImode, mode,
+                                        target, const0_rtx, limit));
   return target;
 }
 
diff --git a/gcc/config/aarch64/iterators.md b/gcc/config/aarch64/iterators.md
index 8533912e5937..175a55336c56 100644
--- a/gcc/config/aarch64/iterators.md
+++ b/gcc/config/aarch64/iterators.md
@@ -455,6 +455,7 @@
 (define_mode_iterator VCVTFPM [V4HF V8HF V4SF])
 
 ;; Iterators for single modes, for "@" patterns.
+(define_mode_iterator VNx16BI_ONLY [VNx16BI])
 (define_mode_iterator VNx16QI_ONLY [VNx16QI])
 (define_mode_iterator VNx16SI_ONLY [VNx16SI])
 (define_mode_iterator VNx8HI_ONLY [VNx8HI])
diff --git a/gcc/config/aarch64/predicates.md b/gcc/config/aarch64/predicates.md
index 32056daf3298..4d5d57f1e5d6 100644
--- a/gcc/config/aarch64/predicates.md
+++ b/gcc/config/aarch64/predicates.md
@@ -1078,3 +1078,9 @@
 (define_predicate "aarch64_maskload_else_operand"
   (and (match_code "const_vector")
        (match_test "op == CONST0_RTX (GET_MODE (op))")))
+
+;; Check for a VNx16BI predicate that is a canonical PTRUE for the given
+;; predicate mode.
+(define_special_predicate "aarch64_ptrue_all_operand"
+  (and (match_code "const_vector")
+       (match_test "aarch64_ptrue_all_mode (op) == mode")))
diff --git a/gcc/testsuite/gcc.target/aarch64/sve/acle/general/pr121118_1.c 
b/gcc/testsuite/gcc.target/aarch64/sve/acle/general/pr121118_1.c
new file mode 100644
index 000000000000..b59a972c0c44
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/sve/acle/general/pr121118_1.c
@@ -0,0 +1,16 @@
+/* { dg-options "-O2 -msve-vector-bits=512" } */
+
+typedef __SVBool_t fixed_bool __attribute__((arm_sve_vector_bits(512)));
+
+#define TEST_CONST(NAME, CONST)                                                
\
+  fixed_bool                                                           \
+  NAME ()                                                              \
+  {                                                                    \
+    union { unsigned long long i; fixed_bool pg; } u = { CONST };      \
+    return u.pg;                                                       \
+  }
+
+TEST_CONST (test1, 0x02aaaaaaaa)
+TEST_CONST (test2, 0x0155555557)
+TEST_CONST (test3, 0x0013333333333333ULL)
+TEST_CONST (test4, 0x0011111111111113ULL)
diff --git a/gcc/testsuite/gcc.target/aarch64/sve/acle/general/whilele_13.c 
b/gcc/testsuite/gcc.target/aarch64/sve/acle/general/whilele_13.c
new file mode 100644
index 000000000000..cf50dc17082d
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/sve/acle/general/whilele_13.c
@@ -0,0 +1,130 @@
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+/* { dg-final { check-function-bodies "**" "" } } */
+
+#include <arm_sve.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+** test1:
+**     whilele p0\.h, w0, w1
+**     ret
+*/
+svbool_t
+test1 (int32_t x, int32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilele_b16 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test2:
+**     whilele p0\.h, x0, x1
+**     ret
+*/
+svbool_t
+test2 (int64_t x, int64_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilele_b16 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test3:
+**     whilels p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test3 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilele_b32 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test4:
+**     whilels p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test4 (uint64_t x, uint64_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilele_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test5:
+**     whilele p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test5 (int32_t x, int32_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilele_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test6:
+**     whilels p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test6 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b32 (),
+                 svwhilele_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test7:
+**     whilels p0\.d, w0, w1
+**     ret
+*/
+svbool_t
+test7 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilele_b64 (x, y),
+                 svptrue_b64 ());
+}
+
+/*
+** test8:
+**     whilele p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test8 (int64_t x, int64_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilele_b64 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test9:
+**     whilels p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test9 (uint64_t x, uint64_t y)
+{
+  return svand_z (svptrue_b64 (),
+                 svwhilele_b64 (x, y),
+                 svptrue_b64 ());
+}
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/gcc/testsuite/gcc.target/aarch64/sve/acle/general/whilelt_6.c 
b/gcc/testsuite/gcc.target/aarch64/sve/acle/general/whilelt_6.c
new file mode 100644
index 000000000000..27bf0c28d54f
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/sve/acle/general/whilelt_6.c
@@ -0,0 +1,130 @@
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+/* { dg-final { check-function-bodies "**" "" } } */
+
+#include <arm_sve.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+** test1:
+**     whilelt p0\.h, w0, w1
+**     ret
+*/
+svbool_t
+test1 (int32_t x, int32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilelt_b16 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test2:
+**     whilelt p0\.h, x0, x1
+**     ret
+*/
+svbool_t
+test2 (int64_t x, int64_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilelt_b16 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test3:
+**     whilelo p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test3 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilelt_b32 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test4:
+**     whilelo p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test4 (uint64_t x, uint64_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilelt_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test5:
+**     whilelt p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test5 (int32_t x, int32_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilelt_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test6:
+**     whilelo p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test6 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b32 (),
+                 svwhilelt_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test7:
+**     whilelo p0\.d, w0, w1
+**     ret
+*/
+svbool_t
+test7 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilelt_b64 (x, y),
+                 svptrue_b64 ());
+}
+
+/*
+** test8:
+**     whilelt p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test8 (int64_t x, int64_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilelt_b64 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test9:
+**     whilelo p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test9 (uint64_t x, uint64_t y)
+{
+  return svand_z (svptrue_b64 (),
+                 svwhilelt_b64 (x, y),
+                 svptrue_b64 ());
+}
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilege_1.c 
b/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilege_1.c
new file mode 100644
index 000000000000..07b56a8138a2
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilege_1.c
@@ -0,0 +1,130 @@
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+/* { dg-final { check-function-bodies "**" "" } } */
+
+#include <arm_sve.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+** test1:
+**     whilege p0\.h, w0, w1
+**     ret
+*/
+svbool_t
+test1 (int32_t x, int32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilege_b16 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test2:
+**     whilege p0\.h, x0, x1
+**     ret
+*/
+svbool_t
+test2 (int64_t x, int64_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilege_b16 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test3:
+**     whilehs p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test3 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilege_b32 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test4:
+**     whilehs p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test4 (uint64_t x, uint64_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilege_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test5:
+**     whilege p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test5 (int32_t x, int32_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilege_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test6:
+**     whilehs p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test6 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b32 (),
+                 svwhilege_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test7:
+**     whilehs p0\.d, w0, w1
+**     ret
+*/
+svbool_t
+test7 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilege_b64 (x, y),
+                 svptrue_b64 ());
+}
+
+/*
+** test8:
+**     whilege p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test8 (int64_t x, int64_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilege_b64 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test9:
+**     whilehs p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test9 (uint64_t x, uint64_t y)
+{
+  return svand_z (svptrue_b64 (),
+                 svwhilege_b64 (x, y),
+                 svptrue_b64 ());
+}
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilegt_1.c 
b/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilegt_1.c
new file mode 100644
index 000000000000..df707c39571c
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilegt_1.c
@@ -0,0 +1,130 @@
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+/* { dg-final { check-function-bodies "**" "" } } */
+
+#include <arm_sve.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+** test1:
+**     whilegt p0\.h, w0, w1
+**     ret
+*/
+svbool_t
+test1 (int32_t x, int32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilegt_b16 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test2:
+**     whilegt p0\.h, x0, x1
+**     ret
+*/
+svbool_t
+test2 (int64_t x, int64_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilegt_b16 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test3:
+**     whilehi p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test3 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilegt_b32 (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test4:
+**     whilehi p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test4 (uint64_t x, uint64_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilegt_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test5:
+**     whilegt p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test5 (int32_t x, int32_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilegt_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test6:
+**     whilehi p0\.s, w0, w1
+**     ret
+*/
+svbool_t
+test6 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b32 (),
+                 svwhilegt_b32 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test7:
+**     whilehi p0\.d, w0, w1
+**     ret
+*/
+svbool_t
+test7 (uint32_t x, uint32_t y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilegt_b64 (x, y),
+                 svptrue_b64 ());
+}
+
+/*
+** test8:
+**     whilegt p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test8 (int64_t x, int64_t y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilegt_b64 (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test9:
+**     whilehi p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test9 (uint64_t x, uint64_t y)
+{
+  return svand_z (svptrue_b64 (),
+                 svwhilegt_b64 (x, y),
+                 svptrue_b64 ());
+}
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilerw_5.c 
b/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilerw_5.c
new file mode 100644
index 000000000000..0c24199e0788
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilerw_5.c
@@ -0,0 +1,130 @@
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+/* { dg-final { check-function-bodies "**" "" } } */
+
+#include <arm_sve.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+** test1:
+**     whilerw p0\.h, x0, x1
+**     ret
+*/
+svbool_t
+test1 (int16_t *x, int16_t *y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilerw (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test2:
+**     whilerw p0\.h, x0, x1
+**     ret
+*/
+svbool_t
+test2 (uint16_t *x, uint16_t *y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilerw (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test3:
+**     whilerw p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test3 (int32_t *x, int32_t *y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilerw (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test4:
+**     whilerw p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test4 (uint32_t *x, uint32_t *y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilerw (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test5:
+**     whilerw p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test5 (float32_t *x, float32_t *y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilerw (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test6:
+**     whilerw p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test6 (int32_t *x, int32_t *y)
+{
+  return svand_z (svptrue_b32 (),
+                 svwhilerw (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test7:
+**     whilerw p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test7 (int64_t *x, int64_t *y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilerw (x, y),
+                 svptrue_b64 ());
+}
+
+/*
+** test8:
+**     whilerw p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test8 (uint64_t *x, uint64_t *y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilerw (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test9:
+**     whilerw p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test9 (float64_t *x, float64_t *y)
+{
+  return svand_z (svptrue_b64 (),
+                 svwhilerw (x, y),
+                 svptrue_b64 ());
+}
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilewr_5.c 
b/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilewr_5.c
new file mode 100644
index 000000000000..38db9af47cf9
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/sve2/acle/general/whilewr_5.c
@@ -0,0 +1,130 @@
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+/* { dg-final { check-function-bodies "**" "" } } */
+
+#include <arm_sve.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*
+** test1:
+**     whilewr p0\.h, x0, x1
+**     ret
+*/
+svbool_t
+test1 (int16_t *x, int16_t *y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilewr (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test2:
+**     whilewr p0\.h, x0, x1
+**     ret
+*/
+svbool_t
+test2 (uint16_t *x, uint16_t *y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilewr (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test3:
+**     whilewr p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test3 (int32_t *x, int32_t *y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilewr (x, y),
+                 svptrue_b16 ());
+}
+
+/*
+** test4:
+**     whilewr p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test4 (uint32_t *x, uint32_t *y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilewr (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test5:
+**     whilewr p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test5 (float32_t *x, float32_t *y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilewr (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test6:
+**     whilewr p0\.s, x0, x1
+**     ret
+*/
+svbool_t
+test6 (int32_t *x, int32_t *y)
+{
+  return svand_z (svptrue_b32 (),
+                 svwhilewr (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test7:
+**     whilewr p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test7 (int64_t *x, int64_t *y)
+{
+  return svand_z (svptrue_b8 (),
+                 svwhilewr (x, y),
+                 svptrue_b64 ());
+}
+
+/*
+** test8:
+**     whilewr p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test8 (uint64_t *x, uint64_t *y)
+{
+  return svand_z (svptrue_b16 (),
+                 svwhilewr (x, y),
+                 svptrue_b32 ());
+}
+
+/*
+** test9:
+**     whilewr p0\.d, x0, x1
+**     ret
+*/
+svbool_t
+test9 (float64_t *x, float64_t *y)
+{
+  return svand_z (svptrue_b64 (),
+                 svwhilewr (x, y),
+                 svptrue_b64 ());
+}
+
+#ifdef __cplusplus
+}
+#endif

Reply via email to