Skip to content

Commit bfc5d83

Browse files
mark-blochjgunthorpe
authored andcommitted
RDMA/mlx5: Attach a DEVX counter via raw flow creation
Allow a user to attach a DEVX counter via mlx5 raw flow creation. In order to attach a counter we introduce a new attribute: MLX5_IB_ATTR_CREATE_FLOW_ARR_COUNTERS_DEVX A counter can be attached to multiple flow steering rules. Signed-off-by: Mark Bloch <markb@mellanox.com> Reviewed-by: Yishai Hadas <yishaih@mellanox.com> Signed-off-by: Leon Romanovsky <leonro@mellanox.com> Signed-off-by: Jason Gunthorpe <jgg@mellanox.com>
1 parent 67810e8 commit bfc5d83

File tree

5 files changed

+56
-12
lines changed

5 files changed

+56
-12
lines changed

drivers/infiniband/hw/mlx5/devx.c

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -107,6 +107,21 @@ bool mlx5_ib_devx_is_flow_dest(void *obj, int *dest_id, int *dest_type)
107107
}
108108
}
109109

110+
bool mlx5_ib_devx_is_flow_counter(void *obj, u32 *counter_id)
111+
{
112+
struct devx_obj *devx_obj = obj;
113+
u16 opcode = MLX5_GET(general_obj_in_cmd_hdr, devx_obj->dinbox, opcode);
114+
115+
if (opcode == MLX5_CMD_OP_DEALLOC_FLOW_COUNTER) {
116+
*counter_id = MLX5_GET(dealloc_flow_counter_in,
117+
devx_obj->dinbox,
118+
flow_counter_id);
119+
return true;
120+
}
121+
122+
return false;
123+
}
124+
110125
/*
111126
* As the obj_id in the firmware is not globally unique the object type
112127
* must be considered upon checking for a valid object id.

drivers/infiniband/hw/mlx5/flow.c

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,7 @@ static int UVERBS_HANDLER(MLX5_IB_METHOD_CREATE_FLOW)(
7777
uverbs_attr_get_uobject(attrs, MLX5_IB_ATTR_CREATE_FLOW_HANDLE);
7878
struct mlx5_ib_dev *dev = to_mdev(uobj->context->device);
7979
int len, ret, i;
80+
u32 counter_id = 0;
8081

8182
if (!capable(CAP_NET_RAW))
8283
return -EPERM;
@@ -128,6 +129,15 @@ static int UVERBS_HANDLER(MLX5_IB_METHOD_CREATE_FLOW)(
128129
dest_type = MLX5_FLOW_DESTINATION_TYPE_PORT;
129130
}
130131

132+
len = uverbs_attr_get_uobjs_arr(attrs,
133+
MLX5_IB_ATTR_CREATE_FLOW_ARR_COUNTERS_DEVX, &arr_flow_actions);
134+
if (len) {
135+
devx_obj = arr_flow_actions[0]->object;
136+
137+
if (!mlx5_ib_devx_is_flow_counter(devx_obj, &counter_id))
138+
return -EINVAL;
139+
flow_act.action |= MLX5_FLOW_CONTEXT_ACTION_COUNT;
140+
}
131141
if (dev->rep)
132142
return -ENOTSUPP;
133143

@@ -164,6 +174,7 @@ static int UVERBS_HANDLER(MLX5_IB_METHOD_CREATE_FLOW)(
164174
}
165175

166176
flow_handler = mlx5_ib_raw_fs_rule_add(dev, fs_matcher, &flow_act,
177+
counter_id,
167178
cmd_in, inlen,
168179
dest_id, dest_type);
169180
if (IS_ERR(flow_handler)) {
@@ -524,7 +535,11 @@ DECLARE_UVERBS_NAMED_METHOD(
524535
UA_OPTIONAL),
525536
UVERBS_ATTR_PTR_IN(MLX5_IB_ATTR_CREATE_FLOW_TAG,
526537
UVERBS_ATTR_TYPE(u32),
527-
UA_OPTIONAL));
538+
UA_OPTIONAL),
539+
UVERBS_ATTR_IDRS_ARR(MLX5_IB_ATTR_CREATE_FLOW_ARR_COUNTERS_DEVX,
540+
MLX5_IB_OBJECT_DEVX_OBJ,
541+
UVERBS_ACCESS_READ, 1, 1,
542+
UA_OPTIONAL));
528543

529544
DECLARE_UVERBS_NAMED_METHOD_DESTROY(
530545
MLX5_IB_METHOD_DESTROY_FLOW,

drivers/infiniband/hw/mlx5/main.c

Lines changed: 20 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -3713,7 +3713,8 @@ _create_raw_flow_rule(struct mlx5_ib_dev *dev,
37133713
struct mlx5_flow_destination *dst,
37143714
struct mlx5_ib_flow_matcher *fs_matcher,
37153715
struct mlx5_flow_act *flow_act,
3716-
void *cmd_in, int inlen)
3716+
void *cmd_in, int inlen,
3717+
int dst_num)
37173718
{
37183719
struct mlx5_ib_flow_handler *handler;
37193720
struct mlx5_flow_spec *spec;
@@ -3735,7 +3736,7 @@ _create_raw_flow_rule(struct mlx5_ib_dev *dev,
37353736
spec->match_criteria_enable = fs_matcher->match_criteria_enable;
37363737

37373738
handler->rule = mlx5_add_flow_rules(ft, spec,
3738-
flow_act, dst, 1);
3739+
flow_act, dst, dst_num);
37393740

37403741
if (IS_ERR(handler->rule)) {
37413742
err = PTR_ERR(handler->rule);
@@ -3798,12 +3799,14 @@ struct mlx5_ib_flow_handler *
37983799
mlx5_ib_raw_fs_rule_add(struct mlx5_ib_dev *dev,
37993800
struct mlx5_ib_flow_matcher *fs_matcher,
38003801
struct mlx5_flow_act *flow_act,
3802+
u32 counter_id,
38013803
void *cmd_in, int inlen, int dest_id,
38023804
int dest_type)
38033805
{
38043806
struct mlx5_flow_destination *dst;
38053807
struct mlx5_ib_flow_prio *ft_prio;
38063808
struct mlx5_ib_flow_handler *handler;
3809+
int dst_num = 0;
38073810
bool mcast;
38083811
int err;
38093812

@@ -3813,7 +3816,7 @@ mlx5_ib_raw_fs_rule_add(struct mlx5_ib_dev *dev,
38133816
if (fs_matcher->priority > MLX5_IB_FLOW_LAST_PRIO)
38143817
return ERR_PTR(-ENOMEM);
38153818

3816-
dst = kzalloc(sizeof(*dst), GFP_KERNEL);
3819+
dst = kzalloc(sizeof(*dst) * 2, GFP_KERNEL);
38173820
if (!dst)
38183821
return ERR_PTR(-ENOMEM);
38193822

@@ -3827,20 +3830,28 @@ mlx5_ib_raw_fs_rule_add(struct mlx5_ib_dev *dev,
38273830
}
38283831

38293832
if (dest_type == MLX5_FLOW_DESTINATION_TYPE_TIR) {
3830-
dst->type = dest_type;
3831-
dst->tir_num = dest_id;
3833+
dst[dst_num].type = dest_type;
3834+
dst[dst_num].tir_num = dest_id;
38323835
flow_act->action |= MLX5_FLOW_CONTEXT_ACTION_FWD_DEST;
38333836
} else if (dest_type == MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE) {
3834-
dst->type = MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE_NUM;
3835-
dst->ft_num = dest_id;
3837+
dst[dst_num].type = MLX5_FLOW_DESTINATION_TYPE_FLOW_TABLE_NUM;
3838+
dst[dst_num].ft_num = dest_id;
38363839
flow_act->action |= MLX5_FLOW_CONTEXT_ACTION_FWD_DEST;
38373840
} else {
3838-
dst->type = MLX5_FLOW_DESTINATION_TYPE_PORT;
3841+
dst[dst_num].type = MLX5_FLOW_DESTINATION_TYPE_PORT;
38393842
flow_act->action |= MLX5_FLOW_CONTEXT_ACTION_ALLOW;
38403843
}
38413844

3845+
dst_num++;
3846+
3847+
if (flow_act->action & MLX5_FLOW_CONTEXT_ACTION_COUNT) {
3848+
dst[dst_num].type = MLX5_FLOW_DESTINATION_TYPE_COUNTER;
3849+
dst[dst_num].counter_id = counter_id;
3850+
dst_num++;
3851+
}
3852+
38423853
handler = _create_raw_flow_rule(dev, ft_prio, dst, fs_matcher, flow_act,
3843-
cmd_in, inlen);
3854+
cmd_in, inlen, dst_num);
38443855

38453856
if (IS_ERR(handler)) {
38463857
err = PTR_ERR(handler);

drivers/infiniband/hw/mlx5/mlx5_ib.h

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1266,9 +1266,11 @@ extern const struct uapi_definition mlx5_ib_devx_defs[];
12661266
extern const struct uapi_definition mlx5_ib_flow_defs[];
12671267
struct mlx5_ib_flow_handler *mlx5_ib_raw_fs_rule_add(
12681268
struct mlx5_ib_dev *dev, struct mlx5_ib_flow_matcher *fs_matcher,
1269-
struct mlx5_flow_act *flow_act, void *cmd_in, int inlen,
1270-
int dest_id, int dest_type);
1269+
struct mlx5_flow_act *flow_act, u32 counter_id,
1270+
void *cmd_in, int inlen, int dest_id, int dest_type);
12711271
bool mlx5_ib_devx_is_flow_dest(void *obj, int *dest_id, int *dest_type);
1272+
bool mlx5_ib_devx_is_flow_counter(void *obj, u32 *counter_id);
1273+
int mlx5_ib_get_flow_trees(const struct uverbs_object_tree_def **root);
12721274
void mlx5_ib_destroy_flow_action_raw(struct mlx5_ib_flow_action *maction);
12731275
#else
12741276
static inline int

include/uapi/rdma/mlx5_user_ioctl_cmds.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -158,6 +158,7 @@ enum mlx5_ib_create_flow_attrs {
158158
MLX5_IB_ATTR_CREATE_FLOW_MATCHER,
159159
MLX5_IB_ATTR_CREATE_FLOW_ARR_FLOW_ACTIONS,
160160
MLX5_IB_ATTR_CREATE_FLOW_TAG,
161+
MLX5_IB_ATTR_CREATE_FLOW_ARR_COUNTERS_DEVX,
161162
};
162163

163164
enum mlx5_ib_destoy_flow_attrs {

0 commit comments

Comments
 (0)