Skip to content

Commit e662e14

Browse files
yishaihjgunthorpe
authored andcommitted
IB/mlx5: Add DEVX support for modify and query commands
Add support in DEVX for modify and query commands, the required lock is taken (i.e. READ/WRITE) by the KABI infrastructure accordingly. Signed-off-by: Yishai Hadas <yishaih@mellanox.com> Signed-off-by: Leon Romanovsky <leonro@mellanox.com> Signed-off-by: Jason Gunthorpe <jgg@mellanox.com>
1 parent 7efce36 commit e662e14

File tree

4 files changed

+370
-2
lines changed

4 files changed

+370
-2
lines changed

drivers/infiniband/hw/mlx5/devx.c

Lines changed: 348 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,161 @@ void mlx5_ib_devx_destroy(struct mlx5_ib_dev *dev,
7373
mlx5_cmd_exec(dev->mdev, in, sizeof(in), out, sizeof(out));
7474
}
7575

76+
static int devx_is_valid_obj_id(struct devx_obj *obj, const void *in)
77+
{
78+
u16 opcode = MLX5_GET(general_obj_in_cmd_hdr, in, opcode);
79+
u32 obj_id;
80+
81+
switch (opcode) {
82+
case MLX5_CMD_OP_MODIFY_GENERAL_OBJECT:
83+
case MLX5_CMD_OP_QUERY_GENERAL_OBJECT:
84+
obj_id = MLX5_GET(general_obj_in_cmd_hdr, in, obj_id);
85+
break;
86+
case MLX5_CMD_OP_QUERY_MKEY:
87+
obj_id = MLX5_GET(query_mkey_in, in, mkey_index);
88+
break;
89+
case MLX5_CMD_OP_QUERY_CQ:
90+
obj_id = MLX5_GET(query_cq_in, in, cqn);
91+
break;
92+
case MLX5_CMD_OP_MODIFY_CQ:
93+
obj_id = MLX5_GET(modify_cq_in, in, cqn);
94+
break;
95+
case MLX5_CMD_OP_QUERY_SQ:
96+
obj_id = MLX5_GET(query_sq_in, in, sqn);
97+
break;
98+
case MLX5_CMD_OP_MODIFY_SQ:
99+
obj_id = MLX5_GET(modify_sq_in, in, sqn);
100+
break;
101+
case MLX5_CMD_OP_QUERY_RQ:
102+
obj_id = MLX5_GET(query_rq_in, in, rqn);
103+
break;
104+
case MLX5_CMD_OP_MODIFY_RQ:
105+
obj_id = MLX5_GET(modify_rq_in, in, rqn);
106+
break;
107+
case MLX5_CMD_OP_QUERY_RMP:
108+
obj_id = MLX5_GET(query_rmp_in, in, rmpn);
109+
break;
110+
case MLX5_CMD_OP_MODIFY_RMP:
111+
obj_id = MLX5_GET(modify_rmp_in, in, rmpn);
112+
break;
113+
case MLX5_CMD_OP_QUERY_RQT:
114+
obj_id = MLX5_GET(query_rqt_in, in, rqtn);
115+
break;
116+
case MLX5_CMD_OP_MODIFY_RQT:
117+
obj_id = MLX5_GET(modify_rqt_in, in, rqtn);
118+
break;
119+
case MLX5_CMD_OP_QUERY_TIR:
120+
obj_id = MLX5_GET(query_tir_in, in, tirn);
121+
break;
122+
case MLX5_CMD_OP_MODIFY_TIR:
123+
obj_id = MLX5_GET(modify_tir_in, in, tirn);
124+
break;
125+
case MLX5_CMD_OP_QUERY_TIS:
126+
obj_id = MLX5_GET(query_tis_in, in, tisn);
127+
break;
128+
case MLX5_CMD_OP_MODIFY_TIS:
129+
obj_id = MLX5_GET(modify_tis_in, in, tisn);
130+
break;
131+
case MLX5_CMD_OP_QUERY_FLOW_TABLE:
132+
obj_id = MLX5_GET(query_flow_table_in, in, table_id);
133+
break;
134+
case MLX5_CMD_OP_MODIFY_FLOW_TABLE:
135+
obj_id = MLX5_GET(modify_flow_table_in, in, table_id);
136+
break;
137+
case MLX5_CMD_OP_QUERY_FLOW_GROUP:
138+
obj_id = MLX5_GET(query_flow_group_in, in, group_id);
139+
break;
140+
case MLX5_CMD_OP_QUERY_FLOW_TABLE_ENTRY:
141+
obj_id = MLX5_GET(query_fte_in, in, flow_index);
142+
break;
143+
case MLX5_CMD_OP_SET_FLOW_TABLE_ENTRY:
144+
obj_id = MLX5_GET(set_fte_in, in, flow_index);
145+
break;
146+
case MLX5_CMD_OP_QUERY_Q_COUNTER:
147+
obj_id = MLX5_GET(query_q_counter_in, in, counter_set_id);
148+
break;
149+
case MLX5_CMD_OP_QUERY_FLOW_COUNTER:
150+
obj_id = MLX5_GET(query_flow_counter_in, in, flow_counter_id);
151+
break;
152+
case MLX5_CMD_OP_QUERY_MODIFY_HEADER_CONTEXT:
153+
obj_id = MLX5_GET(general_obj_in_cmd_hdr, in, obj_id);
154+
break;
155+
case MLX5_CMD_OP_QUERY_SCHEDULING_ELEMENT:
156+
obj_id = MLX5_GET(query_scheduling_element_in, in,
157+
scheduling_element_id);
158+
break;
159+
case MLX5_CMD_OP_MODIFY_SCHEDULING_ELEMENT:
160+
obj_id = MLX5_GET(modify_scheduling_element_in, in,
161+
scheduling_element_id);
162+
break;
163+
case MLX5_CMD_OP_ADD_VXLAN_UDP_DPORT:
164+
obj_id = MLX5_GET(add_vxlan_udp_dport_in, in, vxlan_udp_port);
165+
break;
166+
case MLX5_CMD_OP_QUERY_L2_TABLE_ENTRY:
167+
obj_id = MLX5_GET(query_l2_table_entry_in, in, table_index);
168+
break;
169+
case MLX5_CMD_OP_SET_L2_TABLE_ENTRY:
170+
obj_id = MLX5_GET(set_l2_table_entry_in, in, table_index);
171+
break;
172+
case MLX5_CMD_OP_QUERY_QP:
173+
obj_id = MLX5_GET(query_qp_in, in, qpn);
174+
break;
175+
case MLX5_CMD_OP_RST2INIT_QP:
176+
obj_id = MLX5_GET(rst2init_qp_in, in, qpn);
177+
break;
178+
case MLX5_CMD_OP_INIT2RTR_QP:
179+
obj_id = MLX5_GET(init2rtr_qp_in, in, qpn);
180+
break;
181+
case MLX5_CMD_OP_RTR2RTS_QP:
182+
obj_id = MLX5_GET(rtr2rts_qp_in, in, qpn);
183+
break;
184+
case MLX5_CMD_OP_RTS2RTS_QP:
185+
obj_id = MLX5_GET(rts2rts_qp_in, in, qpn);
186+
break;
187+
case MLX5_CMD_OP_SQERR2RTS_QP:
188+
obj_id = MLX5_GET(sqerr2rts_qp_in, in, qpn);
189+
break;
190+
case MLX5_CMD_OP_2ERR_QP:
191+
obj_id = MLX5_GET(qp_2err_in, in, qpn);
192+
break;
193+
case MLX5_CMD_OP_2RST_QP:
194+
obj_id = MLX5_GET(qp_2rst_in, in, qpn);
195+
break;
196+
case MLX5_CMD_OP_QUERY_DCT:
197+
obj_id = MLX5_GET(query_dct_in, in, dctn);
198+
break;
199+
case MLX5_CMD_OP_QUERY_XRQ:
200+
obj_id = MLX5_GET(query_xrq_in, in, xrqn);
201+
break;
202+
case MLX5_CMD_OP_QUERY_XRC_SRQ:
203+
obj_id = MLX5_GET(query_xrc_srq_in, in, xrc_srqn);
204+
break;
205+
case MLX5_CMD_OP_ARM_XRC_SRQ:
206+
obj_id = MLX5_GET(arm_xrc_srq_in, in, xrc_srqn);
207+
break;
208+
case MLX5_CMD_OP_QUERY_SRQ:
209+
obj_id = MLX5_GET(query_srq_in, in, srqn);
210+
break;
211+
case MLX5_CMD_OP_ARM_RQ:
212+
obj_id = MLX5_GET(arm_rq_in, in, srq_number);
213+
break;
214+
case MLX5_CMD_OP_DRAIN_DCT:
215+
case MLX5_CMD_OP_ARM_DCT_FOR_KEY_VIOLATION:
216+
obj_id = MLX5_GET(drain_dct_in, in, dctn);
217+
break;
218+
case MLX5_CMD_OP_ARM_XRQ:
219+
obj_id = MLX5_GET(arm_xrq_in, in, xrqn);
220+
break;
221+
default:
222+
return false;
223+
}
224+
225+
if (obj_id == obj->obj_id)
226+
return true;
227+
228+
return false;
229+
}
230+
76231
static bool devx_is_obj_create_cmd(const void *in)
77232
{
78233
u16 opcode = MLX5_GET(general_obj_in_cmd_hdr, in, opcode);
@@ -118,7 +273,83 @@ static bool devx_is_obj_create_cmd(const void *in)
118273
}
119274
}
120275

121-
static bool devx_is_general_cmd(const void *in)
276+
static bool devx_is_obj_modify_cmd(const void *in)
277+
{
278+
u16 opcode = MLX5_GET(general_obj_in_cmd_hdr, in, opcode);
279+
280+
switch (opcode) {
281+
case MLX5_CMD_OP_MODIFY_GENERAL_OBJECT:
282+
case MLX5_CMD_OP_MODIFY_CQ:
283+
case MLX5_CMD_OP_MODIFY_RMP:
284+
case MLX5_CMD_OP_MODIFY_SQ:
285+
case MLX5_CMD_OP_MODIFY_RQ:
286+
case MLX5_CMD_OP_MODIFY_RQT:
287+
case MLX5_CMD_OP_MODIFY_TIR:
288+
case MLX5_CMD_OP_MODIFY_TIS:
289+
case MLX5_CMD_OP_MODIFY_FLOW_TABLE:
290+
case MLX5_CMD_OP_MODIFY_SCHEDULING_ELEMENT:
291+
case MLX5_CMD_OP_ADD_VXLAN_UDP_DPORT:
292+
case MLX5_CMD_OP_SET_L2_TABLE_ENTRY:
293+
case MLX5_CMD_OP_RST2INIT_QP:
294+
case MLX5_CMD_OP_INIT2RTR_QP:
295+
case MLX5_CMD_OP_RTR2RTS_QP:
296+
case MLX5_CMD_OP_RTS2RTS_QP:
297+
case MLX5_CMD_OP_SQERR2RTS_QP:
298+
case MLX5_CMD_OP_2ERR_QP:
299+
case MLX5_CMD_OP_2RST_QP:
300+
case MLX5_CMD_OP_ARM_XRC_SRQ:
301+
case MLX5_CMD_OP_ARM_RQ:
302+
case MLX5_CMD_OP_DRAIN_DCT:
303+
case MLX5_CMD_OP_ARM_DCT_FOR_KEY_VIOLATION:
304+
case MLX5_CMD_OP_ARM_XRQ:
305+
return true;
306+
case MLX5_CMD_OP_SET_FLOW_TABLE_ENTRY:
307+
{
308+
u16 op_mod = MLX5_GET(set_fte_in, in, op_mod);
309+
310+
if (op_mod == 1)
311+
return true;
312+
return false;
313+
}
314+
default:
315+
return false;
316+
}
317+
}
318+
319+
static bool devx_is_obj_query_cmd(const void *in)
320+
{
321+
u16 opcode = MLX5_GET(general_obj_in_cmd_hdr, in, opcode);
322+
323+
switch (opcode) {
324+
case MLX5_CMD_OP_QUERY_GENERAL_OBJECT:
325+
case MLX5_CMD_OP_QUERY_MKEY:
326+
case MLX5_CMD_OP_QUERY_CQ:
327+
case MLX5_CMD_OP_QUERY_RMP:
328+
case MLX5_CMD_OP_QUERY_SQ:
329+
case MLX5_CMD_OP_QUERY_RQ:
330+
case MLX5_CMD_OP_QUERY_RQT:
331+
case MLX5_CMD_OP_QUERY_TIR:
332+
case MLX5_CMD_OP_QUERY_TIS:
333+
case MLX5_CMD_OP_QUERY_Q_COUNTER:
334+
case MLX5_CMD_OP_QUERY_FLOW_TABLE:
335+
case MLX5_CMD_OP_QUERY_FLOW_GROUP:
336+
case MLX5_CMD_OP_QUERY_FLOW_TABLE_ENTRY:
337+
case MLX5_CMD_OP_QUERY_FLOW_COUNTER:
338+
case MLX5_CMD_OP_QUERY_MODIFY_HEADER_CONTEXT:
339+
case MLX5_CMD_OP_QUERY_SCHEDULING_ELEMENT:
340+
case MLX5_CMD_OP_QUERY_L2_TABLE_ENTRY:
341+
case MLX5_CMD_OP_QUERY_QP:
342+
case MLX5_CMD_OP_QUERY_SRQ:
343+
case MLX5_CMD_OP_QUERY_XRC_SRQ:
344+
case MLX5_CMD_OP_QUERY_DCT:
345+
case MLX5_CMD_OP_QUERY_XRQ:
346+
return true;
347+
default:
348+
return false;
349+
}
350+
}
351+
352+
static bool devx_is_general_cmd(void *in)
122353
{
123354
u16 opcode = MLX5_GET(general_obj_in_cmd_hdr, in, opcode);
124355

@@ -430,6 +661,89 @@ static int UVERBS_HANDLER(MLX5_IB_METHOD_DEVX_OBJ_CREATE)(struct ib_device *ib_d
430661
return err;
431662
}
432663

664+
static int UVERBS_HANDLER(MLX5_IB_METHOD_DEVX_OBJ_MODIFY)(struct ib_device *ib_dev,
665+
struct ib_uverbs_file *file,
666+
struct uverbs_attr_bundle *attrs)
667+
{
668+
struct mlx5_ib_ucontext *c = devx_ufile2uctx(file);
669+
struct mlx5_ib_dev *dev = to_mdev(ib_dev);
670+
void *cmd_in = uverbs_attr_get_alloced_ptr(attrs, MLX5_IB_ATTR_DEVX_OBJ_MODIFY_CMD_IN);
671+
int cmd_out_len = uverbs_attr_get_len(attrs,
672+
MLX5_IB_ATTR_DEVX_OBJ_MODIFY_CMD_OUT);
673+
struct ib_uobject *uobj = uverbs_attr_get_uobject(attrs,
674+
MLX5_IB_ATTR_DEVX_OBJ_MODIFY_HANDLE);
675+
void *cmd_out;
676+
int err;
677+
678+
if (!c->devx_uid)
679+
return -EPERM;
680+
681+
if (!devx_is_obj_modify_cmd(cmd_in))
682+
return -EINVAL;
683+
684+
if (!devx_is_valid_obj_id(uobj->object, cmd_in))
685+
return -EINVAL;
686+
687+
cmd_out = kvzalloc(cmd_out_len, GFP_KERNEL);
688+
if (!cmd_out)
689+
return -ENOMEM;
690+
691+
MLX5_SET(general_obj_in_cmd_hdr, cmd_in, uid, c->devx_uid);
692+
err = mlx5_cmd_exec(dev->mdev, cmd_in,
693+
uverbs_attr_get_len(attrs, MLX5_IB_ATTR_DEVX_OBJ_MODIFY_CMD_IN),
694+
cmd_out, cmd_out_len);
695+
if (err)
696+
goto other_cmd_free;
697+
698+
err = uverbs_copy_to(attrs, MLX5_IB_ATTR_DEVX_OBJ_MODIFY_CMD_OUT,
699+
cmd_out, cmd_out_len);
700+
701+
other_cmd_free:
702+
kvfree(cmd_out);
703+
return err;
704+
}
705+
706+
static int UVERBS_HANDLER(MLX5_IB_METHOD_DEVX_OBJ_QUERY)(struct ib_device *ib_dev,
707+
struct ib_uverbs_file *file,
708+
struct uverbs_attr_bundle *attrs)
709+
{
710+
struct mlx5_ib_ucontext *c = devx_ufile2uctx(file);
711+
struct mlx5_ib_dev *dev = to_mdev(ib_dev);
712+
void *cmd_in = uverbs_attr_get_alloced_ptr(attrs, MLX5_IB_ATTR_DEVX_OBJ_QUERY_CMD_IN);
713+
int cmd_out_len = uverbs_attr_get_len(attrs,
714+
MLX5_IB_ATTR_DEVX_OBJ_QUERY_CMD_OUT);
715+
struct ib_uobject *uobj = uverbs_attr_get_uobject(attrs,
716+
MLX5_IB_ATTR_DEVX_OBJ_QUERY_HANDLE);
717+
void *cmd_out;
718+
int err;
719+
720+
if (!c->devx_uid)
721+
return -EPERM;
722+
723+
if (!devx_is_obj_query_cmd(cmd_in))
724+
return -EINVAL;
725+
726+
if (!devx_is_valid_obj_id(uobj->object, cmd_in))
727+
return -EINVAL;
728+
729+
cmd_out = kvzalloc(cmd_out_len, GFP_KERNEL);
730+
if (!cmd_out)
731+
return -ENOMEM;
732+
733+
MLX5_SET(general_obj_in_cmd_hdr, cmd_in, uid, c->devx_uid);
734+
err = mlx5_cmd_exec(dev->mdev, cmd_in,
735+
uverbs_attr_get_len(attrs, MLX5_IB_ATTR_DEVX_OBJ_QUERY_CMD_IN),
736+
cmd_out, cmd_out_len);
737+
if (err)
738+
goto other_cmd_free;
739+
740+
err = uverbs_copy_to(attrs, MLX5_IB_ATTR_DEVX_OBJ_QUERY_CMD_OUT, cmd_out, cmd_out_len);
741+
742+
other_cmd_free:
743+
kvfree(cmd_out);
744+
return err;
745+
}
746+
433747
static DECLARE_UVERBS_NAMED_METHOD(MLX5_IB_METHOD_DEVX_OTHER,
434748
&UVERBS_ATTR_PTR_IN_SZ(MLX5_IB_ATTR_DEVX_OTHER_CMD_IN,
435749
UVERBS_ATTR_MIN_SIZE(MLX5_ST_SZ_BYTES(general_obj_in_cmd_hdr)),
@@ -463,13 +777,45 @@ static DECLARE_UVERBS_NAMED_METHOD(MLX5_IB_METHOD_DEVX_OBJ_DESTROY,
463777
UVERBS_ACCESS_DESTROY,
464778
UA_FLAGS(UVERBS_ATTR_SPEC_F_MANDATORY)));
465779

780+
static DECLARE_UVERBS_NAMED_METHOD(MLX5_IB_METHOD_DEVX_OBJ_MODIFY,
781+
&UVERBS_ATTR_IDR(MLX5_IB_ATTR_DEVX_OBJ_MODIFY_HANDLE,
782+
MLX5_IB_OBJECT_DEVX_OBJ,
783+
UVERBS_ACCESS_WRITE,
784+
UA_FLAGS(UVERBS_ATTR_SPEC_F_MANDATORY)),
785+
&UVERBS_ATTR_PTR_IN_SZ(MLX5_IB_ATTR_DEVX_OBJ_MODIFY_CMD_IN,
786+
UVERBS_ATTR_MIN_SIZE(MLX5_ST_SZ_BYTES(general_obj_in_cmd_hdr)),
787+
UA_FLAGS(UVERBS_ATTR_SPEC_F_MANDATORY |
788+
UVERBS_ATTR_SPEC_F_MIN_SZ_OR_ZERO |
789+
UVERBS_ATTR_SPEC_F_ALLOC_AND_COPY)),
790+
&UVERBS_ATTR_PTR_OUT_SZ(MLX5_IB_ATTR_DEVX_OBJ_MODIFY_CMD_OUT,
791+
UVERBS_ATTR_MIN_SIZE(MLX5_ST_SZ_BYTES(general_obj_out_cmd_hdr)),
792+
UA_FLAGS(UVERBS_ATTR_SPEC_F_MANDATORY |
793+
UVERBS_ATTR_SPEC_F_MIN_SZ_OR_ZERO)));
794+
795+
static DECLARE_UVERBS_NAMED_METHOD(MLX5_IB_METHOD_DEVX_OBJ_QUERY,
796+
&UVERBS_ATTR_IDR(MLX5_IB_ATTR_DEVX_OBJ_QUERY_HANDLE,
797+
MLX5_IB_OBJECT_DEVX_OBJ,
798+
UVERBS_ACCESS_READ,
799+
UA_FLAGS(UVERBS_ATTR_SPEC_F_MANDATORY)),
800+
&UVERBS_ATTR_PTR_IN_SZ(MLX5_IB_ATTR_DEVX_OBJ_QUERY_CMD_IN,
801+
UVERBS_ATTR_MIN_SIZE(MLX5_ST_SZ_BYTES(general_obj_in_cmd_hdr)),
802+
UA_FLAGS(UVERBS_ATTR_SPEC_F_MANDATORY |
803+
UVERBS_ATTR_SPEC_F_MIN_SZ_OR_ZERO |
804+
UVERBS_ATTR_SPEC_F_ALLOC_AND_COPY)),
805+
&UVERBS_ATTR_PTR_OUT_SZ(MLX5_IB_ATTR_DEVX_OBJ_QUERY_CMD_OUT,
806+
UVERBS_ATTR_MIN_SIZE(MLX5_ST_SZ_BYTES(general_obj_out_cmd_hdr)),
807+
UA_FLAGS(UVERBS_ATTR_SPEC_F_MANDATORY |
808+
UVERBS_ATTR_SPEC_F_MIN_SZ_OR_ZERO)));
809+
466810
static DECLARE_UVERBS_GLOBAL_METHODS(MLX5_IB_OBJECT_DEVX,
467811
&UVERBS_METHOD(MLX5_IB_METHOD_DEVX_OTHER));
468812

469813
static DECLARE_UVERBS_NAMED_OBJECT(MLX5_IB_OBJECT_DEVX_OBJ,
470814
&UVERBS_TYPE_ALLOC_IDR(0, devx_obj_cleanup),
471815
&UVERBS_METHOD(MLX5_IB_METHOD_DEVX_OBJ_CREATE),
472-
&UVERBS_METHOD(MLX5_IB_METHOD_DEVX_OBJ_DESTROY));
816+
&UVERBS_METHOD(MLX5_IB_METHOD_DEVX_OBJ_DESTROY),
817+
&UVERBS_METHOD(MLX5_IB_METHOD_DEVX_OBJ_MODIFY),
818+
&UVERBS_METHOD(MLX5_IB_METHOD_DEVX_OBJ_QUERY));
473819

474820
static DECLARE_UVERBS_OBJECT_TREE(devx_objects,
475821
&UVERBS_OBJECT(MLX5_IB_OBJECT_DEVX),

0 commit comments

Comments
 (0)