aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
Diffstat (limited to 'gcc')
-rw-r--r--gcc/config/riscv/autovec-opt.md22
-rw-r--r--gcc/config/riscv/autovec.md51
-rw-r--r--gcc/config/riscv/riscv-protos.h9
-rw-r--r--gcc/config/riscv/riscv-v.cc60
4 files changed, 79 insertions, 63 deletions
diff --git a/gcc/config/riscv/autovec-opt.md b/gcc/config/riscv/autovec-opt.md
index df51684..b47bae1 100644
--- a/gcc/config/riscv/autovec-opt.md
+++ b/gcc/config/riscv/autovec-opt.md
@@ -1208,7 +1208,8 @@
"&& 1"
[(const_int 0)]
{
- riscv_vector::expand_reduction (<WREDUC_UNSPEC>, operands,
+ riscv_vector::expand_reduction (<WREDUC_UNSPEC>, riscv_vector::REDUCE_OP,
+ operands,
CONST0_RTX (<V_DOUBLE_EXTEND_VEL>mode));
DONE;
}
@@ -1226,7 +1227,9 @@
"&& 1"
[(const_int 0)]
{
- riscv_vector::expand_reduction (UNSPEC_WREDUC_SUM_UNORDERED, operands,
+ riscv_vector::expand_reduction (UNSPEC_WREDUC_SUM_UNORDERED,
+ riscv_vector::REDUCE_OP_FRM_DYN,
+ operands,
CONST0_RTX (<V_DOUBLE_EXTEND_VEL>mode));
DONE;
}
@@ -1245,9 +1248,9 @@
"&& 1"
[(const_int 0)]
{
- riscv_vector::expand_reduction (UNSPEC_WREDUC_SUM_ORDERED, operands,
- operands[1],
- riscv_vector::reduction_type::FOLD_LEFT);
+ riscv_vector::expand_reduction (UNSPEC_WREDUC_SUM_ORDERED,
+ riscv_vector::REDUCE_OP_FRM_DYN,
+ operands, operands[1]);
DONE;
}
[(set_attr "type" "vector")])
@@ -1271,9 +1274,12 @@
if (rtx_equal_p (operands[4], const0_rtx))
emit_move_insn (operands[0], operands[1]);
else
- riscv_vector::expand_reduction (UNSPEC_WREDUC_SUM_ORDERED, operands,
- operands[1],
- riscv_vector::reduction_type::MASK_LEN_FOLD_LEFT);
+ {
+ rtx ops[] = {operands[0], operands[2], operands[3], operands[4]};
+ riscv_vector::expand_reduction (UNSPEC_WREDUC_SUM_ORDERED,
+ riscv_vector::REDUCE_OP_M_FRM_DYN,
+ ops, operands[1]);
+ }
DONE;
}
[(set_attr "type" "vector")])
diff --git a/gcc/config/riscv/autovec.md b/gcc/config/riscv/autovec.md
index 8537b9d..c6175a3 100644
--- a/gcc/config/riscv/autovec.md
+++ b/gcc/config/riscv/autovec.md
@@ -2096,7 +2096,8 @@
"&& 1"
[(const_int 0)]
{
- riscv_vector::expand_reduction (UNSPEC_REDUC_SUM, operands, CONST0_RTX (<VEL>mode));
+ riscv_vector::expand_reduction (UNSPEC_REDUC_SUM, riscv_vector::REDUCE_OP,
+ operands, CONST0_RTX (<VEL>mode));
DONE;
}
[(set_attr "type" "vector")])
@@ -2108,7 +2109,8 @@
{
int prec = GET_MODE_PRECISION (<VEL>mode);
rtx min = immed_wide_int_const (wi::min_value (prec, SIGNED), <VEL>mode);
- riscv_vector::expand_reduction (UNSPEC_REDUC_MAX, operands, min);
+ riscv_vector::expand_reduction (UNSPEC_REDUC_MAX, riscv_vector::REDUCE_OP,
+ operands, min);
DONE;
})
@@ -2117,7 +2119,8 @@
(match_operand:VI 1 "register_operand")]
"TARGET_VECTOR"
{
- riscv_vector::expand_reduction (UNSPEC_REDUC_MAXU, operands, CONST0_RTX (<VEL>mode));
+ riscv_vector::expand_reduction (UNSPEC_REDUC_MAXU, riscv_vector::REDUCE_OP,
+ operands, CONST0_RTX (<VEL>mode));
DONE;
})
@@ -2128,7 +2131,8 @@
{
int prec = GET_MODE_PRECISION (<VEL>mode);
rtx max = immed_wide_int_const (wi::max_value (prec, SIGNED), <VEL>mode);
- riscv_vector::expand_reduction (UNSPEC_REDUC_MIN, operands, max);
+ riscv_vector::expand_reduction (UNSPEC_REDUC_MIN, riscv_vector::REDUCE_OP,
+ operands, max);
DONE;
})
@@ -2139,7 +2143,8 @@
{
int prec = GET_MODE_PRECISION (<VEL>mode);
rtx max = immed_wide_int_const (wi::max_value (prec, UNSIGNED), <VEL>mode);
- riscv_vector::expand_reduction (UNSPEC_REDUC_MINU, operands, max);
+ riscv_vector::expand_reduction (UNSPEC_REDUC_MINU, riscv_vector::REDUCE_OP,
+ operands, max);
DONE;
})
@@ -2148,7 +2153,8 @@
(match_operand:VI 1 "register_operand")]
"TARGET_VECTOR"
{
- riscv_vector::expand_reduction (UNSPEC_REDUC_AND, operands, CONSTM1_RTX (<VEL>mode));
+ riscv_vector::expand_reduction (UNSPEC_REDUC_AND, riscv_vector::REDUCE_OP,
+ operands, CONSTM1_RTX (<VEL>mode));
DONE;
})
@@ -2157,7 +2163,8 @@
(match_operand:VI 1 "register_operand")]
"TARGET_VECTOR"
{
- riscv_vector::expand_reduction (UNSPEC_REDUC_OR, operands, CONST0_RTX (<VEL>mode));
+ riscv_vector::expand_reduction (UNSPEC_REDUC_OR, riscv_vector::REDUCE_OP,
+ operands, CONST0_RTX (<VEL>mode));
DONE;
})
@@ -2166,7 +2173,8 @@
(match_operand:VI 1 "register_operand")]
"TARGET_VECTOR"
{
- riscv_vector::expand_reduction (UNSPEC_REDUC_XOR, operands, CONST0_RTX (<VEL>mode));
+ riscv_vector::expand_reduction (UNSPEC_REDUC_XOR, riscv_vector::REDUCE_OP,
+ operands, CONST0_RTX (<VEL>mode));
DONE;
})
@@ -2189,8 +2197,9 @@
"&& 1"
[(const_int 0)]
{
- riscv_vector::expand_reduction (UNSPEC_REDUC_SUM_UNORDERED, operands,
- CONST0_RTX (<VEL>mode));
+ riscv_vector::expand_reduction (UNSPEC_REDUC_SUM_UNORDERED,
+ riscv_vector::REDUCE_OP_FRM_DYN,
+ operands, CONST0_RTX (<VEL>mode));
DONE;
}
[(set_attr "type" "vector")])
@@ -2203,7 +2212,8 @@
REAL_VALUE_TYPE rv;
real_inf (&rv, true);
rtx f = const_double_from_real_value (rv, <VEL>mode);
- riscv_vector::expand_reduction (UNSPEC_REDUC_MAX, operands, f);
+ riscv_vector::expand_reduction (UNSPEC_REDUC_MAX, riscv_vector::REDUCE_OP,
+ operands, f);
DONE;
})
@@ -2215,7 +2225,8 @@
REAL_VALUE_TYPE rv;
real_inf (&rv, false);
rtx f = const_double_from_real_value (rv, <VEL>mode);
- riscv_vector::expand_reduction (UNSPEC_REDUC_MIN, operands, f);
+ riscv_vector::expand_reduction (UNSPEC_REDUC_MIN, riscv_vector::REDUCE_OP,
+ operands, f);
DONE;
})
@@ -2238,9 +2249,10 @@
"&& 1"
[(const_int 0)]
{
- riscv_vector::expand_reduction (UNSPEC_REDUC_SUM_ORDERED, operands,
- operands[1],
- riscv_vector::reduction_type::FOLD_LEFT);
+ rtx ops[] = {operands[0], operands[2]};
+ riscv_vector::expand_reduction (UNSPEC_REDUC_SUM_ORDERED,
+ riscv_vector::REDUCE_OP_FRM_DYN,
+ ops, operands[1]);
DONE;
}
[(set_attr "type" "vector")])
@@ -2263,9 +2275,12 @@
if (rtx_equal_p (operands[4], const0_rtx))
emit_move_insn (operands[0], operands[1]);
else
- riscv_vector::expand_reduction (UNSPEC_REDUC_SUM_ORDERED, operands,
- operands[1],
- riscv_vector::reduction_type::MASK_LEN_FOLD_LEFT);
+ {
+ rtx ops[] = {operands[0], operands[2], operands[3], operands[4]};
+ riscv_vector::expand_reduction (UNSPEC_REDUC_SUM_ORDERED,
+ riscv_vector::REDUCE_OP_M_FRM_DYN,
+ ops, operands[1]);
+ }
DONE;
}
[(set_attr "type" "vector")])
diff --git a/gcc/config/riscv/riscv-protos.h b/gcc/config/riscv/riscv-protos.h
index 44fa36c..bb94a7e 100644
--- a/gcc/config/riscv/riscv-protos.h
+++ b/gcc/config/riscv/riscv-protos.h
@@ -414,12 +414,6 @@ enum mask_policy
/* Return true if VALUE is agnostic or any policy. */
#define IS_AGNOSTIC(VALUE) (bool) (VALUE & 0x1 || (VALUE >> 1 & 0x1))
-enum class reduction_type
-{
- UNORDERED,
- FOLD_LEFT,
- MASK_LEN_FOLD_LEFT,
-};
enum tail_policy get_prefer_tail_policy ();
enum mask_policy get_prefer_mask_policy ();
rtx get_avl_type_rtx (enum avl_type);
@@ -433,8 +427,7 @@ void expand_vec_cmp (rtx, rtx_code, rtx, rtx);
bool expand_vec_cmp_float (rtx, rtx_code, rtx, rtx, bool);
void expand_cond_len_unop (unsigned, rtx *);
void expand_cond_len_binop (unsigned, rtx *);
-void expand_reduction (unsigned, rtx *, rtx,
- reduction_type = reduction_type::UNORDERED);
+void expand_reduction (unsigned, unsigned, rtx *, rtx);
#endif
bool sew64_scalar_helper (rtx *, rtx *, rtx, machine_mode,
bool, void (*)(rtx *, rtx));
diff --git a/gcc/config/riscv/riscv-v.cc b/gcc/config/riscv/riscv-v.cc
index 668594b..7e9fd9e 100644
--- a/gcc/config/riscv/riscv-v.cc
+++ b/gcc/config/riscv/riscv-v.cc
@@ -67,6 +67,18 @@ const_vlmax_p (machine_mode mode)
: false;
}
+/* Helper functions for insn_flags && insn_types */
+
+/* Return true if caller need pass mask operand for insn pattern with
+ INSN_FLAGS. */
+
+static bool
+need_mask_operand_p (unsigned insn_flags)
+{
+ return (insn_flags & HAS_MASK_P)
+ && !(insn_flags & (USE_ONE_TRUE_MASK_P | USE_ALL_TRUES_MASK_P));
+}
+
template <int MAX_OPERANDS> class insn_expander
{
public:
@@ -3206,48 +3218,38 @@ expand_cond_len_ternop (unsigned icode, rtx *ops)
expand_cond_len_op (icode, TERNARY_OP_P, cond_ops, len);
}
-/* Expand reduction operations. */
+/* Expand reduction operations.
+ Case 1: ops = {scalar_dest, vector_src}
+ Case 2: ops = {scalar_dest, vector_src, mask, vl}
+*/
void
-expand_reduction (unsigned unspec, rtx *ops, rtx init, reduction_type type)
+expand_reduction (unsigned unspec, unsigned insn_flags, rtx *ops, rtx init)
{
- rtx vector = type == reduction_type::UNORDERED ? ops[1] : ops[2];
- machine_mode vmode = GET_MODE (vector);
- machine_mode vel_mode = GET_MODE (ops[0]);
+ rtx scalar_dest = ops[0];
+ rtx vector_src = ops[1];
+ machine_mode vmode = GET_MODE (vector_src);
+ machine_mode vel_mode = GET_MODE (scalar_dest);
machine_mode m1_mode = get_m1_mode (vel_mode).require ();
rtx m1_tmp = gen_reg_rtx (m1_mode);
rtx scalar_move_ops[] = {m1_tmp, init};
emit_nonvlmax_insn (code_for_pred_broadcast (m1_mode), SCALAR_MOVE_OP,
- scalar_move_ops,
- type == reduction_type::MASK_LEN_FOLD_LEFT
- ? ops[4]
- : CONST1_RTX (Pmode));
+ scalar_move_ops,
+ need_mask_operand_p (insn_flags) ? ops[3]
+ : CONST1_RTX (Pmode));
rtx m1_tmp2 = gen_reg_rtx (m1_mode);
- rtx reduc_ops[] = {m1_tmp2, vector, m1_tmp};
+ rtx reduc_ops[] = {m1_tmp2, vector_src, m1_tmp};
+ insn_code icode = code_for_pred (unspec, vmode);
- if (unspec == UNSPEC_REDUC_SUM_ORDERED
- || unspec == UNSPEC_WREDUC_SUM_ORDERED
- || unspec == UNSPEC_REDUC_SUM_UNORDERED
- || unspec == UNSPEC_WREDUC_SUM_UNORDERED)
+ if (need_mask_operand_p (insn_flags))
{
- insn_code icode = code_for_pred (unspec, vmode);
- if (type == reduction_type::MASK_LEN_FOLD_LEFT)
- {
- rtx mask = ops[3];
- rtx mask_len_reduc_ops[] = {m1_tmp2, mask, vector, m1_tmp};
- emit_nonvlmax_insn (icode, REDUCE_OP_M_FRM_DYN, mask_len_reduc_ops,
- ops[4]);
- }
- else
- emit_vlmax_insn (icode, REDUCE_OP_FRM_DYN, reduc_ops);
+ rtx mask_len_reduc_ops[] = {m1_tmp2, ops[2], vector_src, m1_tmp};
+ emit_nonvlmax_insn (icode, insn_flags, mask_len_reduc_ops, ops[3]);
}
else
- {
- insn_code icode = code_for_pred (unspec, vmode);
- emit_vlmax_insn (icode, REDUCE_OP, reduc_ops);
- }
+ emit_vlmax_insn (icode, insn_flags, reduc_ops);
- emit_insn (gen_pred_extract_first (m1_mode, ops[0], m1_tmp2));
+ emit_insn (gen_pred_extract_first (m1_mode, scalar_dest, m1_tmp2));
}
/* Prepare ops for ternary operations.