(and (match_code "const_vector")
(match_test "riscv_vector::const_vec_all_same_in_range_p (op, 0, 31)"))))
+;; pmode_reg_or_uimm5_operand can be used by vsll.vx/vsrl.vx/vsra.vx instructions.
+;; Since it has the same predicate with vector_length_operand which allows register
+;; or immediate (0 ~ 31), we define this predicate same as vector_length_operand here.
+;; We don't use vector_length_operand directly to predicate vsll.vx/vsrl.vx/vsra.vx
+;; since it may be confusing.
+(define_special_predicate "pmode_reg_or_uimm5_operand"
+ (match_operand 0 "vector_length_operand"))
+
(define_special_predicate "pmode_reg_or_0_operand"
(ior (match_operand 0 "const_0_operand")
(match_operand 0 "pmode_register_operand")))
public:
rtx expand (function_expander &e) const override
{
- return e.use_exact_insn (code_for_pred (CODE, e.vector_mode ()));
+ switch (e.op_info->op)
+ {
+ case OP_TYPE_vx:
+ return e.use_exact_insn (code_for_pred_scalar (CODE, e.vector_mode ()));
+ case OP_TYPE_vv:
+ return e.use_exact_insn (code_for_pred (CODE, e.vector_mode ()));
+ default:
+ gcc_unreachable ();
+ }
}
};
DEF_RVV_FUNCTION (vrem, binop, full_preds, iu_vvv_ops)
DEF_RVV_FUNCTION (vdivu, binop, full_preds, iu_vvv_ops)
DEF_RVV_FUNCTION (vremu, binop, full_preds, iu_vvv_ops)
+DEF_RVV_FUNCTION (vsll, binop, full_preds, iu_shift_vvx_ops)
+DEF_RVV_FUNCTION (vsra, binop, full_preds, iu_shift_vvx_ops)
+DEF_RVV_FUNCTION (vsrl, binop, full_preds, iu_shift_vvx_ops)
#undef DEF_RVV_FUNCTION
= {rvv_arg_type_info (RVV_BASE_vector),
rvv_arg_type_info (RVV_BASE_shift_vector), rvv_arg_type_info_end};
+/* A list of args for vector_type func (vector_type, size) function. */
+static CONSTEXPR const rvv_arg_type_info vector_size_args[]
+ = {rvv_arg_type_info (RVV_BASE_vector), rvv_arg_type_info (RVV_BASE_size),
+ rvv_arg_type_info_end};
+
/* A list of none preds that will be registered for intrinsic functions. */
static CONSTEXPR const predication_type_index none_preds[]
= {PRED_TYPE_none, NUM_PRED_TYPES};
rvv_arg_type_info (RVV_BASE_vector), /* Return type */
shift_vv_args /* Args */};
+/* A static operand information for vector_type func (vector_type, size_t)
+ * function registration. */
+static CONSTEXPR const rvv_op_info iu_shift_vvx_ops
+ = {iu_ops, /* Types */
+ OP_TYPE_vx, /* Suffix */
+ rvv_arg_type_info (RVV_BASE_vector), /* Return type */
+ vector_size_args /* Args */};
+
/* A list of all RVV intrinsic functions. */
static function_group_info function_groups[] = {
#define DEF_RVV_FUNCTION(NAME, SHAPE, PREDS, OPS_INFO) \
v<binop_alt2_insn>\t%0,<binop_alt2_op>%p1"
[(set_attr "type" "<int_binop_insn_type>")
(set_attr "mode" "<MODE>")])
+
+;; vx instructions patterns.
+;; Note: Unlike vv patterns, we should split them since they are variant.
+;; For vsll.vx/vsra.vx/vsrl.vx the scalar mode should be Pmode wheras the
+;; scalar mode is inner mode of the RVV mode for other vx patterns.
+(define_insn "@pred_<optab><mode>_scalar"
+ [(set (match_operand:VI 0 "register_operand" "=vr, vr")
+ (if_then_else:VI
+ (unspec:<VM>
+ [(match_operand:<VM> 1 "vector_mask_operand" "vmWc1,vmWc1")
+ (match_operand 5 "vector_length_operand" " rK, rK")
+ (match_operand 6 "const_int_operand" " i, i")
+ (match_operand 7 "const_int_operand" " i, i")
+ (match_operand 8 "const_int_operand" " i, i")
+ (reg:SI VL_REGNUM)
+ (reg:SI VTYPE_REGNUM)] UNSPEC_VPREDICATE)
+ (any_shift:VI
+ (match_operand:VI 3 "register_operand" " vr, vr")
+ (match_operand 4 "pmode_reg_or_uimm5_operand" " r, K"))
+ (match_operand:VI 2 "vector_merge_operand" "0vu, 0vu")))]
+ "TARGET_VECTOR"
+ "@
+ v<insn>.vx\t%0,%3,%4%p1
+ v<insn>.vi\t%0,%3,%4%p1"
+ [(set_attr "type" "vshift")
+ (set_attr "mode" "<MODE>")])