public inbox for gcc-cvs@sourceware.org
help / color / mirror / Atom feed
* [gcc r13-4447] RISC-V: Add duplicate vector support.
@ 2022-12-01 16:14 Kito Cheng
0 siblings, 0 replies; only message in thread
From: Kito Cheng @ 2022-12-01 16:14 UTC (permalink / raw)
To: gcc-cvs
https://gcc.gnu.org/g:fa144175c9ccaa10d7021d00f97aaa9eac59afec
commit r13-4447-gfa144175c9ccaa10d7021d00f97aaa9eac59afec
Author: Ju-Zhe Zhong <juzhe.zhong@rivai.ai>
Date: Sat Nov 26 00:06:39 2022 +0800
RISC-V: Add duplicate vector support.
gcc/ChangeLog:
* config/riscv/constraints.md (Wdm): New constraint.
* config/riscv/predicates.md (direct_broadcast_operand): New predicate.
* config/riscv/riscv-protos.h (RVV_VLMAX): New macro.
(emit_pred_op): Refine function.
* config/riscv/riscv-selftests.cc (run_const_vector_selftests): New function.
(run_broadcast_selftests): Ditto.
(BROADCAST_TEST): New tests.
(riscv_run_selftests): More tests.
* config/riscv/riscv-v.cc (emit_pred_move): Refine function.
(emit_vlmax_vsetvl): Ditto.
(emit_pred_op): Ditto.
(expand_const_vector): New function.
(legitimize_move): Add constant vector support.
* config/riscv/riscv.cc (riscv_print_operand): New asm print rule for const vector.
* config/riscv/riscv.h (X0_REGNUM): New macro.
* config/riscv/vector-iterators.md: New attribute.
* config/riscv/vector.md (vec_duplicate<mode>): New pattern.
(@pred_broadcast<mode>): New pattern.
gcc/testsuite/ChangeLog:
* gcc.target/riscv/rvv/base/dup-1.c: New test.
* gcc.target/riscv/rvv/base/dup-2.c: New test.
Diff:
---
gcc/config/riscv/constraints.md | 5 +
gcc/config/riscv/predicates.md | 5 +
gcc/config/riscv/riscv-protos.h | 2 +
gcc/config/riscv/riscv-selftests.cc | 127 ++++++
gcc/config/riscv/riscv-v.cc | 86 +++-
gcc/config/riscv/riscv.cc | 13 +
gcc/config/riscv/riscv.h | 3 +
gcc/config/riscv/vector-iterators.md | 9 +
gcc/config/riscv/vector.md | 53 ++-
gcc/testsuite/gcc.target/riscv/rvv/base/dup-1.c | 521 ++++++++++++++++++++++++
gcc/testsuite/gcc.target/riscv/rvv/base/dup-2.c | 75 ++++
11 files changed, 881 insertions(+), 18 deletions(-)
diff --git a/gcc/config/riscv/constraints.md b/gcc/config/riscv/constraints.md
index 4088c48150a..51cffb2bcb6 100644
--- a/gcc/config/riscv/constraints.md
+++ b/gcc/config/riscv/constraints.md
@@ -151,3 +151,8 @@
A constraint that matches a vector of immediate all ones."
(and (match_code "const_vector")
(match_test "op == CONSTM1_RTX (GET_MODE (op))")))
+
+(define_constraint "Wdm"
+ "Vector duplicate memory operand"
+ (and (match_operand 0 "memory_operand")
+ (match_code "reg" "0")))
diff --git a/gcc/config/riscv/predicates.md b/gcc/config/riscv/predicates.md
index dfd98761b8b..5a5a49bf7c0 100644
--- a/gcc/config/riscv/predicates.md
+++ b/gcc/config/riscv/predicates.md
@@ -286,6 +286,11 @@
(match_test "GET_CODE (op) == UNSPEC
&& (XINT (op, 1) == UNSPEC_VUNDEF)"))))
+;; The scalar operand can be directly broadcast by RVV instructions.
+(define_predicate "direct_broadcast_operand"
+ (ior (match_operand 0 "register_operand")
+ (match_test "satisfies_constraint_Wdm (op)")))
+
;; A CONST_INT operand that has exactly two bits cleared.
(define_predicate "const_nottwobits_operand"
(and (match_code "const_int")
diff --git a/gcc/config/riscv/riscv-protos.h b/gcc/config/riscv/riscv-protos.h
index 2ec3af05aa4..27692ffb210 100644
--- a/gcc/config/riscv/riscv-protos.h
+++ b/gcc/config/riscv/riscv-protos.h
@@ -119,6 +119,7 @@ extern void riscv_run_selftests (void);
#endif
namespace riscv_vector {
+#define RVV_VLMAX gen_rtx_REG (Pmode, X0_REGNUM)
/* Routines implemented in riscv-vector-builtins.cc. */
extern void init_builtins (void);
extern const char *mangle_builtin_type (const_tree);
@@ -130,6 +131,7 @@ extern tree builtin_decl (unsigned, bool);
extern rtx expand_builtin (unsigned int, tree, rtx);
extern bool const_vec_all_same_in_range_p (rtx, HOST_WIDE_INT, HOST_WIDE_INT);
extern bool legitimize_move (rtx, rtx, machine_mode);
+extern void emit_pred_op (unsigned, rtx, rtx, machine_mode);
enum tail_policy
{
TAIL_UNDISTURBED = 0,
diff --git a/gcc/config/riscv/riscv-selftests.cc b/gcc/config/riscv/riscv-selftests.cc
index 636874ebc0f..1bf1a648fa1 100644
--- a/gcc/config/riscv/riscv-selftests.cc
+++ b/gcc/config/riscv/riscv-selftests.cc
@@ -33,6 +33,9 @@ along with GCC; see the file COPYING3. If not see
#include "expr.h"
#include "selftest.h"
#include "selftest-rtl.h"
+#include "insn-attr.h"
+#include "target.h"
+#include "optabs.h"
#if CHECKING_P
using namespace selftest;
@@ -230,12 +233,136 @@ run_poly_int_selftests (void)
run_poly_int_selftest ("rv32imafd_zve32x1p0", ABI_ILP32D, POLY_TEST_DIMODE,
worklist);
}
+
+static void
+run_const_vector_selftests (void)
+{
+ /* We dont't need to do the redundant tests in different march && mabi.
+ Just pick up the march && mabi which fully support all RVV modes. */
+ riscv_selftest_arch_abi_setter rv ("rv64imafdcv", ABI_LP64D);
+ rtl_dump_test t (SELFTEST_LOCATION, locate_file ("riscv/empty-func.rtl"));
+ set_new_first_and_last_insn (NULL, NULL);
+
+ machine_mode mode;
+ std::vector<HOST_WIDE_INT> worklist = {-111, -17, -16, 7, 15, 16, 111};
+
+ FOR_EACH_MODE_IN_CLASS (mode, MODE_VECTOR_INT)
+ {
+ if (riscv_v_ext_vector_mode_p (mode))
+ {
+ for (const HOST_WIDE_INT &val : worklist)
+ {
+ start_sequence ();
+ rtx dest = gen_reg_rtx (mode);
+ rtx dup = gen_const_vec_duplicate (mode, GEN_INT (val));
+ emit_move_insn (dest, dup);
+ rtx_insn *insn = get_last_insn ();
+ rtx src = XEXP (SET_SRC (PATTERN (insn)), 1);
+ /* 1. Should be vmv.v.i for in rang of -16 ~ 15.
+ 2. Should be vmv.v.x for exceed -16 ~ 15. */
+ if (IN_RANGE (val, -16, 15))
+ ASSERT_TRUE (rtx_equal_p (src, dup));
+ else
+ ASSERT_TRUE (
+ rtx_equal_p (src,
+ gen_rtx_VEC_DUPLICATE (mode, XEXP (src, 0))));
+ end_sequence ();
+ }
+ }
+ }
+
+ FOR_EACH_MODE_IN_CLASS (mode, MODE_VECTOR_FLOAT)
+ {
+ if (riscv_v_ext_vector_mode_p (mode))
+ {
+ scalar_mode inner_mode = GET_MODE_INNER (mode);
+ REAL_VALUE_TYPE f = REAL_VALUE_ATOF ("0.2928932", inner_mode);
+ rtx ele = const_double_from_real_value (f, inner_mode);
+
+ start_sequence ();
+ rtx dest = gen_reg_rtx (mode);
+ rtx dup = gen_const_vec_duplicate (mode, ele);
+ emit_move_insn (dest, dup);
+ rtx_insn *insn = get_last_insn ();
+ rtx src = XEXP (SET_SRC (PATTERN (insn)), 1);
+ /* Should always be vfmv.v.f. */
+ ASSERT_TRUE (
+ rtx_equal_p (src, gen_rtx_VEC_DUPLICATE (mode, XEXP (src, 0))));
+ end_sequence ();
+ }
+ }
+
+ FOR_EACH_MODE_IN_CLASS (mode, MODE_VECTOR_BOOL)
+ {
+ /* Test vmset.m. */
+ if (riscv_v_ext_vector_mode_p (mode))
+ {
+ start_sequence ();
+ rtx dest = gen_reg_rtx (mode);
+ emit_move_insn (dest, CONSTM1_RTX (mode));
+ rtx_insn *insn = get_last_insn ();
+ rtx src = XEXP (SET_SRC (PATTERN (insn)), 1);
+ ASSERT_TRUE (rtx_equal_p (src, CONSTM1_RTX (mode)));
+ end_sequence ();
+ }
+ }
+}
+
+static void
+run_broadcast_selftests (void)
+{
+ /* We dont't need to do the redundant tests in different march && mabi.
+ Just pick up the march && mabi which fully support all RVV modes. */
+ riscv_selftest_arch_abi_setter rv ("rv64imafdcv", ABI_LP64D);
+ rtl_dump_test t (SELFTEST_LOCATION, locate_file ("riscv/empty-func.rtl"));
+ set_new_first_and_last_insn (NULL, NULL);
+
+ machine_mode mode;
+
+#define BROADCAST_TEST(MODE_CLASS) \
+ FOR_EACH_MODE_IN_CLASS (mode, MODE_VECTOR_INT) \
+ { \
+ if (riscv_v_ext_vector_mode_p (mode)) \
+ { \
+ rtx_insn *insn; \
+ rtx src; \
+ scalar_mode inner_mode = GET_MODE_INNER (mode); \
+ /* Test vlse.v with zero stride. */ \
+ start_sequence (); \
+ rtx addr = gen_reg_rtx (Pmode); \
+ rtx mem = gen_rtx_MEM (inner_mode, addr); \
+ expand_vector_broadcast (mode, mem); \
+ insn = get_last_insn (); \
+ src = XEXP (SET_SRC (PATTERN (insn)), 1); \
+ ASSERT_TRUE (MEM_P (XEXP (src, 0))); \
+ ASSERT_TRUE ( \
+ rtx_equal_p (src, gen_rtx_VEC_DUPLICATE (mode, XEXP (src, 0)))); \
+ end_sequence (); \
+ /* Test vmv.v.x or vfmv.v.f. */ \
+ start_sequence (); \
+ rtx reg = gen_reg_rtx (inner_mode); \
+ expand_vector_broadcast (mode, reg); \
+ insn = get_last_insn (); \
+ src = XEXP (SET_SRC (PATTERN (insn)), 1); \
+ ASSERT_TRUE (REG_P (XEXP (src, 0))); \
+ ASSERT_TRUE ( \
+ rtx_equal_p (src, gen_rtx_VEC_DUPLICATE (mode, XEXP (src, 0)))); \
+ end_sequence (); \
+ } \
+ }
+
+ BROADCAST_TEST (MODE_VECTOR_INT)
+ BROADCAST_TEST (MODE_VECTOR_FLOAT)
+}
+
namespace selftest {
/* Run all target-specific selftests. */
void
riscv_run_selftests (void)
{
run_poly_int_selftests ();
+ run_const_vector_selftests ();
+ run_broadcast_selftests ();
}
} // namespace selftest
#endif /* #if CHECKING_P */
diff --git a/gcc/config/riscv/riscv-v.cc b/gcc/config/riscv/riscv-v.cc
index e0459e3f610..fbd8bbfe254 100644
--- a/gcc/config/riscv/riscv-v.cc
+++ b/gcc/config/riscv/riscv-v.cc
@@ -40,6 +40,7 @@
#include "target.h"
#include "expr.h"
#include "optabs.h"
+#include "tm-constrs.h"
using namespace riscv_vector;
@@ -104,34 +105,80 @@ const_vec_all_same_in_range_p (rtx x, HOST_WIDE_INT minval,
&& IN_RANGE (INTVAL (elt), minval, maxval));
}
-/* Emit an RVV unmask && vl mov from SRC to DEST. */
-static void
-emit_pred_move (rtx dest, rtx src, machine_mode mask_mode)
+static rtx
+emit_vlmax_vsetvl (machine_mode vmode)
{
- insn_expander<7> e;
- machine_mode mode = GET_MODE (dest);
rtx vl = gen_reg_rtx (Pmode);
- unsigned int sew = GET_MODE_CLASS (mode) == MODE_VECTOR_BOOL
+ unsigned int sew = GET_MODE_CLASS (vmode) == MODE_VECTOR_BOOL
? 8
- : GET_MODE_BITSIZE (GET_MODE_INNER (mode));
+ : GET_MODE_BITSIZE (GET_MODE_INNER (vmode));
- emit_insn (gen_vsetvl_no_side_effects (
- Pmode, vl, gen_rtx_REG (Pmode, 0), gen_int_mode (sew, Pmode),
- gen_int_mode ((unsigned int) mode, Pmode), const1_rtx, const1_rtx));
+ emit_insn (
+ gen_vsetvl_no_side_effects (Pmode, vl, RVV_VLMAX, gen_int_mode (sew, Pmode),
+ gen_int_mode ((unsigned int) vmode, Pmode),
+ const1_rtx, const1_rtx));
+ return vl;
+}
+
+/* Emit an RVV unmask && vl mov from SRC to DEST. */
+void
+emit_pred_op (unsigned icode, rtx dest, rtx src, machine_mode mask_mode)
+{
+ insn_expander<7> e;
+ machine_mode mode = GET_MODE (dest);
e.add_output_operand (dest, mode);
e.add_all_one_mask_operand (mask_mode);
e.add_vundef_operand (mode);
- e.add_input_operand (src, mode);
+ e.add_input_operand (src, GET_MODE (src));
- e.add_input_operand (vl, Pmode);
+ rtx vlmax = emit_vlmax_vsetvl (mode);
+ e.add_input_operand (vlmax, Pmode);
e.add_policy_operand (TAIL_AGNOSTIC, MASK_AGNOSTIC);
- enum insn_code icode;
- icode = code_for_pred_mov (mode);
- e.expand (icode, true);
+ e.expand ((enum insn_code) icode, MEM_P (dest) || MEM_P (src));
+}
+
+static void
+expand_const_vector (rtx target, rtx src, machine_mode mask_mode)
+{
+ machine_mode mode = GET_MODE (target);
+ scalar_mode elt_mode = GET_MODE_INNER (mode);
+ if (GET_MODE_CLASS (mode) == MODE_VECTOR_BOOL)
+ {
+ rtx elt;
+ gcc_assert (
+ const_vec_duplicate_p (src, &elt)
+ && (rtx_equal_p (elt, const0_rtx) || rtx_equal_p (elt, const1_rtx)));
+ emit_pred_op (code_for_pred_mov (mode), target, src, mode);
+ return;
+ }
+
+ rtx elt;
+ if (const_vec_duplicate_p (src, &elt))
+ {
+ rtx tmp = register_operand (target, mode) ? target : gen_reg_rtx (mode);
+ /* Element in range -16 ~ 15 integer or 0.0 floating-point,
+ we use vmv.v.i instruction. */
+ if (satisfies_constraint_vi (src) || satisfies_constraint_Wc0 (src))
+ emit_pred_op (code_for_pred_mov (mode), tmp, src, mask_mode);
+ else
+ emit_pred_op (code_for_pred_broadcast (mode), tmp,
+ force_reg (elt_mode, elt), mask_mode);
+
+ if (tmp != target)
+ emit_move_insn (target, tmp);
+ return;
+ }
+
+ /* TODO: We only support const duplicate vector for now. More cases
+ will be supported when we support auto-vectorization:
+
+ 1. series vector.
+ 2. multiple elts duplicate vector.
+ 3. multiple patterns with multiple elts. */
}
/* Expand a pre-RA RVV data move from SRC to DEST.
@@ -140,6 +187,11 @@ bool
legitimize_move (rtx dest, rtx src, machine_mode mask_mode)
{
machine_mode mode = GET_MODE (dest);
+ if (CONST_VECTOR_P (src))
+ {
+ expand_const_vector (dest, src, mask_mode);
+ return true;
+ }
if (known_ge (GET_MODE_SIZE (mode), BYTES_PER_RISCV_VECTOR)
&& GET_MODE_CLASS (mode) != MODE_VECTOR_BOOL)
{
@@ -153,12 +205,12 @@ legitimize_move (rtx dest, rtx src, machine_mode mask_mode)
{
rtx tmp = gen_reg_rtx (mode);
if (MEM_P (src))
- emit_pred_move (tmp, src, mask_mode);
+ emit_pred_op (code_for_pred_mov (mode), tmp, src, mask_mode);
else
emit_move_insn (tmp, src);
src = tmp;
}
- emit_pred_move (dest, src, mask_mode);
+ emit_pred_op (code_for_pred_mov (mode), dest, src, mask_mode);
return true;
}
diff --git a/gcc/config/riscv/riscv.cc b/gcc/config/riscv/riscv.cc
index 05bdba5ab4d..bc0411ea862 100644
--- a/gcc/config/riscv/riscv.cc
+++ b/gcc/config/riscv/riscv.cc
@@ -4229,6 +4229,19 @@ riscv_print_operand (FILE *file, rtx op, int letter)
switch (letter)
{
+ case 'v': {
+ rtx elt;
+
+ if (!const_vec_duplicate_p (op, &elt))
+ output_operand_lossage ("invalid vector constant");
+ else if (satisfies_constraint_Wc0 (op))
+ asm_fprintf (file, "0");
+ else if (satisfies_constraint_vi (op))
+ asm_fprintf (file, "%wd", INTVAL (elt));
+ else
+ output_operand_lossage ("invalid vector constant");
+ break;
+ }
case 'm': {
if (riscv_v_ext_vector_mode_p (mode))
{
diff --git a/gcc/config/riscv/riscv.h b/gcc/config/riscv/riscv.h
index b05c3c1545c..defb475f948 100644
--- a/gcc/config/riscv/riscv.h
+++ b/gcc/config/riscv/riscv.h
@@ -651,6 +651,9 @@ enum reg_class
#define FP_ARG_FIRST (FP_REG_FIRST + 10)
#define FP_ARG_LAST (FP_ARG_FIRST + MAX_ARGS_IN_REGISTERS - 1)
+/* Helper macro for RVV vsetvl instruction generation. */
+#define X0_REGNUM GP_REG_FIRST
+
#define CALLEE_SAVED_REG_NUMBER(REGNO) \
((REGNO) >= 8 && (REGNO) <= 9 ? (REGNO) - 8 : \
(REGNO) >= 18 && (REGNO) <= 27 ? (REGNO) - 16 : -1)
diff --git a/gcc/config/riscv/vector-iterators.md b/gcc/config/riscv/vector-iterators.md
index 9d4a9dc8a0e..92c4bd0a6a3 100644
--- a/gcc/config/riscv/vector-iterators.md
+++ b/gcc/config/riscv/vector-iterators.md
@@ -71,6 +71,15 @@
(VNx1DF "VNx1BI") (VNx2DF "VNx2BI") (VNx4DF "VNx4BI") (VNx8DF "VNx8BI")
])
+(define_mode_attr VEL [
+ (VNx1QI "QI") (VNx2QI "QI") (VNx4QI "QI") (VNx8QI "QI") (VNx16QI "QI") (VNx32QI "QI") (VNx64QI "QI")
+ (VNx1HI "HI") (VNx2HI "HI") (VNx4HI "HI") (VNx8HI "HI") (VNx16HI "HI") (VNx32HI "HI")
+ (VNx1SI "SI") (VNx2SI "SI") (VNx4SI "SI") (VNx8SI "SI") (VNx16SI "SI")
+ (VNx1DI "DI") (VNx2DI "DI") (VNx4DI "DI") (VNx8DI "DI")
+ (VNx1SF "SF") (VNx2SF "SF") (VNx4SF "SF") (VNx8SF "SF") (VNx16SF "SF")
+ (VNx1DF "DF") (VNx2DF "DF") (VNx4DF "DF") (VNx8DF "DF")
+])
+
(define_mode_attr sew [
(VNx1QI "8") (VNx2QI "8") (VNx4QI "8") (VNx8QI "8") (VNx16QI "8") (VNx32QI "8") (VNx64QI "8")
(VNx1HI "16") (VNx2HI "16") (VNx4HI "16") (VNx8HI "16") (VNx16HI "16") (VNx32HI "16")
diff --git a/gcc/config/riscv/vector.md b/gcc/config/riscv/vector.md
index 01418ac5fcf..611cc862ca8 100644
--- a/gcc/config/riscv/vector.md
+++ b/gcc/config/riscv/vector.md
@@ -151,6 +151,26 @@
[(set_attr "type" "vmov")
(set_attr "mode" "<MODE>")])
+;; -----------------------------------------------------------------
+;; ---- Duplicate Operations
+;; -----------------------------------------------------------------
+
+;; According to GCC internal:
+;; This pattern only handles duplicates of non-constant inputs.
+;; Constant vectors go through the movm pattern instead.
+;; So "direct_broadcast_operand" can only be mem or reg, no CONSTANT.
+(define_expand "vec_duplicate<mode>"
+ [(set (match_operand:V 0 "register_operand")
+ (vec_duplicate:V
+ (match_operand:<VEL> 1 "direct_broadcast_operand")))]
+ "TARGET_VECTOR"
+ {
+ riscv_vector::emit_pred_op (
+ code_for_pred_broadcast (<MODE>mode), operands[0], operands[1], <VM>mode);
+ DONE;
+ }
+)
+
;; -----------------------------------------------------------------
;; ---- 6. Configuration-Setting Instructions
;; -----------------------------------------------------------------
@@ -368,7 +388,7 @@
vle<sew>.v\t%0,%3%p1
vse<sew>.v\t%3,%0%p1
vmv.v.v\t%0,%3
- vmv.v.i\t%0,v%3"
+ vmv.v.i\t%0,%v3"
"&& register_operand (operands[0], <MODE>mode)
&& register_operand (operands[3], <MODE>mode)
&& satisfies_constraint_vu (operands[2])"
@@ -407,3 +427,34 @@
""
[(set_attr "type" "vldm,vstm,vimov,vmalu,vmalu")
(set_attr "mode" "<MODE>")])
+
+;; -------------------------------------------------------------------------------
+;; ---- Predicated Broadcast
+;; -------------------------------------------------------------------------------
+;; Includes:
+;; - 7.5. Vector Strided Instructions (zero stride)
+;; - 11.16 Vector Integer Move Instructions (vmv.v.x)
+;; - 13.16 Vector Floating-Point Move Instruction (vfmv.v.f)
+;; -------------------------------------------------------------------------------
+
+(define_insn "@pred_broadcast<mode>"
+ [(set (match_operand:V 0 "register_operand" "=vr, vr, vr, vr")
+ (if_then_else:V
+ (unspec:<VM>
+ [(match_operand:<VM> 1 "vector_mask_operand" " Wc1, Wc1, vm, Wc1")
+ (match_operand 4 "vector_length_operand" " rK, rK, rK, rK")
+ (match_operand 5 "const_int_operand" " i, i, i, i")
+ (match_operand 6 "const_int_operand" " i, i, i, i")
+ (reg:SI VL_REGNUM)
+ (reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
+ (vec_duplicate:V
+ (match_operand:<VEL> 3 "direct_broadcast_operand" " r, f, Wdm, Wdm"))
+ (match_operand:V 2 "vector_merge_operand" "vu0, vu0, vu0, vu0")))]
+ "TARGET_VECTOR"
+ "@
+ vmv.v.x\t%0,%3
+ vfmv.v.f\t%0,%3
+ vlse<sew>.v\t%0,%3,zero,%1.t
+ vlse<sew>.v\t%0,%3,zero"
+ [(set_attr "type" "vimov,vfmov,vlds,vlds")
+ (set_attr "mode" "<MODE>")])
diff --git a/gcc/testsuite/gcc.target/riscv/rvv/base/dup-1.c b/gcc/testsuite/gcc.target/riscv/rvv/base/dup-1.c
new file mode 100644
index 00000000000..2a83afae056
--- /dev/null
+++ b/gcc/testsuite/gcc.target/riscv/rvv/base/dup-1.c
@@ -0,0 +1,521 @@
+/* { dg-do compile } */
+/* { dg-options "-march=rv32gcv -mabi=ilp32 -O3 -fgimple" } */
+
+#include "riscv_vector.h"
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f1 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint8mf8_t> ((vint8mf8_t *)out_2(D)) = _Literal (vint8mf8_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f2 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint8mf4_t> ((vint8mf4_t *)out_2(D)) = _Literal (vint8mf4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f3 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint8mf2_t> ((vint8mf2_t *)out_2(D)) = _Literal (vint8mf2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f4 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint8m1_t> ((vint8m1_t *)out_2(D)) = _Literal (vint8m1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f5 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint8m2_t> ((vint8m2_t *)out_2(D)) = _Literal (vint8m2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f6 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint8m4_t> ((vint8m4_t *)out_2(D)) = _Literal (vint8m4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f7 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint8m8_t> ((vint8m8_t *)out_2(D)) = _Literal (vint8m8_t) 0;
+ return;
+
+}
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f8 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint8mf8_t> ((vuint8mf8_t *)out_2(D)) = _Literal (vuint8mf8_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f9 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint8mf4_t> ((vuint8mf4_t *)out_2(D)) = _Literal (vuint8mf4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f10 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint8mf2_t> ((vuint8mf2_t *)out_2(D)) = _Literal (vuint8mf2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f11 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint8m1_t> ((vuint8m1_t *)out_2(D)) = _Literal (vuint8m1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f12 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint8m2_t> ((vuint8m2_t *)out_2(D)) = _Literal (vuint8m2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f13 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint8m4_t> ((vuint8m4_t *)out_2(D)) = _Literal (vuint8m4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f14 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint8m8_t> ((vuint8m8_t *)out_2(D)) = _Literal (vuint8m8_t) 0;
+ return;
+
+}
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f15 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint16mf4_t> ((vint16mf4_t *)out_2(D)) = _Literal (vint16mf4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f16 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint16mf2_t> ((vint16mf2_t *)out_2(D)) = _Literal (vint16mf2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f17 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint16m1_t> ((vint16m1_t *)out_2(D)) = _Literal (vint16m1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f18 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint16m2_t> ((vint16m2_t *)out_2(D)) = _Literal (vint16m2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f19 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint16m4_t> ((vint16m4_t *)out_2(D)) = _Literal (vint16m4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f20 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint16m8_t> ((vint16m8_t *)out_2(D)) = _Literal (vint16m8_t) 0;
+ return;
+
+}
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f21 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint16mf4_t> ((vuint16mf4_t *)out_2(D)) = _Literal (vuint16mf4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f22 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint16mf2_t> ((vuint16mf2_t *)out_2(D)) = _Literal (vuint16mf2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f23 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint16m1_t> ((vuint16m1_t *)out_2(D)) = _Literal (vuint16m1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f24 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint16m2_t> ((vuint16m2_t *)out_2(D)) = _Literal (vuint16m2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f25 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint16m4_t> ((vuint16m4_t *)out_2(D)) = _Literal (vuint16m4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f26 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint16m8_t> ((vuint16m8_t *)out_2(D)) = _Literal (vuint16m8_t) 0;
+ return;
+
+}
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f27 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint32mf2_t> ((vint32mf2_t *)out_2(D)) = _Literal (vint32mf2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f28 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint32m1_t> ((vint32m1_t *)out_2(D)) = _Literal (vint32m1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f29 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint32m2_t> ((vint32m2_t *)out_2(D)) = _Literal (vint32m2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f30 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint32m4_t> ((vint32m4_t *)out_2(D)) = _Literal (vint32m4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f31 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint32m8_t> ((vint32m8_t *)out_2(D)) = _Literal (vint32m8_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f32 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint32mf2_t> ((vuint32mf2_t *)out_2(D)) = _Literal (vuint32mf2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f33 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint32m1_t> ((vuint32m1_t *)out_2(D)) = _Literal (vuint32m1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f34 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint32m2_t> ((vuint32m2_t *)out_2(D)) = _Literal (vuint32m2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f35 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint32m4_t> ((vuint32m4_t *)out_2(D)) = _Literal (vuint32m4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f36 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint32m8_t> ((vuint32m8_t *)out_2(D)) = _Literal (vuint32m8_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f37 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint64m1_t> ((vint64m1_t *)out_2(D)) = _Literal (vint64m1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f38 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint64m2_t> ((vint64m2_t *)out_2(D)) = _Literal (vint64m2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f39 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint64m4_t> ((vint64m4_t *)out_2(D)) = _Literal (vint64m4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f40 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vint64m8_t> ((vint64m8_t *)out_2(D)) = _Literal (vint64m8_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f41 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint64m1_t> ((vuint64m1_t *)out_2(D)) = _Literal (vuint64m1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f42 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint64m2_t> ((vuint64m2_t *)out_2(D)) = _Literal (vuint64m2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f43 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint64m4_t> ((vuint64m4_t *)out_2(D)) = _Literal (vuint64m4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f44 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vuint64m8_t> ((vuint64m8_t *)out_2(D)) = _Literal (vuint64m8_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f45 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vfloat32m1_t> ((vfloat32m1_t *)out_2(D)) = _Literal (vfloat32m1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f46 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vfloat32m2_t> ((vfloat32m2_t *)out_2(D)) = _Literal (vfloat32m2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f47 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vfloat32m4_t> ((vfloat32m4_t *)out_2(D)) = _Literal (vfloat32m4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f48 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vfloat32m8_t> ((vfloat32m8_t *)out_2(D)) = _Literal (vfloat32m8_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f49 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vfloat64m1_t> ((vfloat64m1_t *)out_2(D)) = _Literal (vfloat64m1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f50 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vfloat64m2_t> ((vfloat64m2_t *)out_2(D)) = _Literal (vfloat64m2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f51 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vfloat64m4_t> ((vfloat64m4_t *)out_2(D)) = _Literal (vfloat64m4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f52 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vfloat64m8_t> ((vfloat64m8_t *)out_2(D)) = _Literal (vfloat64m8_t) 0;
+ return;
+
+}
+
+/* { dg-final { scan-assembler-times {vmv\.v\.i\s+(?:v[0-9]|v[1-2][0-9]|v3[0-1]),\s*0} 52 } } */
diff --git a/gcc/testsuite/gcc.target/riscv/rvv/base/dup-2.c b/gcc/testsuite/gcc.target/riscv/rvv/base/dup-2.c
new file mode 100644
index 00000000000..c6903039c2a
--- /dev/null
+++ b/gcc/testsuite/gcc.target/riscv/rvv/base/dup-2.c
@@ -0,0 +1,75 @@
+/* { dg-do compile } */
+/* { dg-options "-march=rv32gcv -mabi=ilp32 -O3 -fgimple" } */
+
+#include "riscv_vector.h"
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f1 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vbool1_t> ((vbool1_t *)out_2(D)) = _Literal (vbool1_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f2 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vbool2_t> ((vbool2_t *)out_2(D)) = _Literal (vbool2_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f3 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vbool4_t> ((vbool4_t *)out_2(D)) = _Literal (vbool4_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f4 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vbool8_t> ((vbool8_t *)out_2(D)) = _Literal (vbool8_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f5 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vbool16_t> ((vbool16_t *)out_2(D)) = _Literal (vbool16_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f6 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vbool32_t> ((vbool32_t *)out_2(D)) = _Literal (vbool32_t) 0;
+ return;
+
+}
+
+
+void __GIMPLE (ssa,guessed_local(1073741824))
+f7 (void * out)
+{
+ __BB(2,guessed_local(1073741824)):
+ __MEM <vbool64_t> ((vbool64_t *)out_2(D)) = _Literal (vbool64_t) 0;
+ return;
+
+}
+
+/* { dg-final { scan-assembler-times {vmclr\.m\s+(?:v[0-9]|v[1-2][0-9]|v3[0-1])} 7 } } */
^ permalink raw reply [flat|nested] only message in thread
only message in thread, other threads:[~2022-12-01 16:14 UTC | newest]
Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-12-01 16:14 [gcc r13-4447] RISC-V: Add duplicate vector support Kito Cheng
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).