This pattern enables the combine pass to merge a vec_duplicate into a plus-mult
or minus-mult RTL instruction.
Before this patch, we have two instructions, e.g.:
vfmv.v.f v6,fa0
vfmadd.vv v9,v6,v7
After, we get only one:
vfmadd.vf v9,fa0,v7
On SPEC2017's 503.bwaves_r, depending on the workload, the reduction in dynamic
instruction count varies from -4.66% to -4.75%.
gcc/ChangeLog:
PR target/119100
* config/riscv/vector.md (*pred_<madd_msub><mode>_scalar): Define.
---
gcc/config/riscv/vector.md | 23 +++++++++++++++++++++++
1 file changed, 23 insertions(+)
diff --git gcc/config/riscv/vector.md gcc/config/riscv/vector.md
index 8ee43cf0ce1..6f538eeefda 100644
--- gcc/config/riscv/vector.md
+++ gcc/config/riscv/vector.md
@@ -6633,6 +6633,29 @@
(set (attr "frm_mode")
(symbol_ref "riscv_vector::get_frm_mode (operands[9])"))])
+(define_insn_and_split "*pred_<madd_msub><mode>_scalar"
+ [(set (match_operand:V_VLSF 0 "register_operand" "=vd, vr")
+ (plus_minus:V_VLSF
+ (mult:V_VLSF
+ (vec_duplicate:V_VLSF
+ (match_operand:<VEL> 1 "register_operand" " f, f"))
+ (match_operand:V_VLSF 2 "register_operand" " 0, 0"))
+ (match_operand:V_VLSF 3 "register_operand" " vr, vr")))]
+ "TARGET_VECTOR"
+ "#"
+ "!reload_completed"
+ [(const_int 0)]
+ {
+ rtx ops[] = {operands[0], operands[1], operands[2], operands[3],
+ operands[2]};
+ riscv_vector::emit_vlmax_insn (code_for_pred_mul_scalar (<CODE>,
<MODE>mode),
+ riscv_vector::TERNARY_OP_FRM_DYN, ops);
+ DONE;
+ }
+ [(set_attr "type" "vfmuladd")
+ (set_attr "mode" "<MODE>")]
+)
+
(define_insn "*pred_<macc_msac><mode>_scalar"
[(set (match_operand:V_VLSF 0 "register_operand" "=vd, vr")
(if_then_else:V_VLSF
--
2.34.1