1 // SPDX-License-Identifier: GPL-2.0 OR Linux-OpenIB
3 * Copyright (c) 2020, Mellanox Technologies inc. All rights reserved.
6 #include <rdma/uverbs_ioctl.h>
7 #include <rdma/mlx5_user_ioctl_cmds.h>
8 #include <rdma/mlx5_user_ioctl_verbs.h>
9 #include <linux/mlx5/driver.h>
12 #define UVERBS_MODULE_NAME mlx5_ib
13 #include <rdma/uverbs_named_ioctl.h>
15 static bool pp_is_supported(struct ib_device *device)
17 struct mlx5_ib_dev *dev = to_mdev(device);
19 return (MLX5_CAP_GEN(dev->mdev, qos) &&
20 MLX5_CAP_QOS(dev->mdev, packet_pacing) &&
21 MLX5_CAP_QOS(dev->mdev, packet_pacing_uid));
24 static int UVERBS_HANDLER(MLX5_IB_METHOD_PP_OBJ_ALLOC)(
25 struct uverbs_attr_bundle *attrs)
27 u8 rl_raw[MLX5_ST_SZ_BYTES(set_pp_rate_limit_context)] = {};
28 struct ib_uobject *uobj = uverbs_attr_get_uobject(attrs,
29 MLX5_IB_ATTR_PP_OBJ_ALLOC_HANDLE);
30 struct mlx5_ib_dev *dev;
31 struct mlx5_ib_ucontext *c;
32 struct mlx5_ib_pp *pp_entry;
39 c = to_mucontext(ib_uverbs_get_ucontext(attrs));
43 /* The allocated entry can be used only by a DEVX context */
47 dev = to_mdev(c->ibucontext.device);
48 pp_entry = kzalloc(sizeof(*pp_entry), GFP_KERNEL);
52 in_ctx = uverbs_attr_get_alloced_ptr(attrs,
53 MLX5_IB_ATTR_PP_OBJ_ALLOC_CTX);
54 inlen = uverbs_attr_get_len(attrs,
55 MLX5_IB_ATTR_PP_OBJ_ALLOC_CTX);
56 memcpy(rl_raw, in_ctx, inlen);
57 err = uverbs_get_flags32(&flags, attrs,
58 MLX5_IB_ATTR_PP_OBJ_ALLOC_FLAGS,
59 MLX5_IB_UAPI_PP_ALLOC_FLAGS_DEDICATED_INDEX);
63 uid = (flags & MLX5_IB_UAPI_PP_ALLOC_FLAGS_DEDICATED_INDEX) ?
64 c->devx_uid : MLX5_SHARED_RESOURCE_UID;
66 err = mlx5_rl_add_rate_raw(dev->mdev, rl_raw, uid,
67 (flags & MLX5_IB_UAPI_PP_ALLOC_FLAGS_DEDICATED_INDEX),
72 pp_entry->mdev = dev->mdev;
73 uobj->object = pp_entry;
74 uverbs_finalize_uobj_create(attrs, MLX5_IB_ATTR_PP_OBJ_ALLOC_HANDLE);
76 err = uverbs_copy_to(attrs, MLX5_IB_ATTR_PP_OBJ_ALLOC_INDEX,
77 &pp_entry->index, sizeof(pp_entry->index));
85 static int pp_obj_cleanup(struct ib_uobject *uobject,
86 enum rdma_remove_reason why,
87 struct uverbs_attr_bundle *attrs)
89 struct mlx5_ib_pp *pp_entry = uobject->object;
91 mlx5_rl_remove_rate_raw(pp_entry->mdev, pp_entry->index);
96 DECLARE_UVERBS_NAMED_METHOD(
97 MLX5_IB_METHOD_PP_OBJ_ALLOC,
98 UVERBS_ATTR_IDR(MLX5_IB_ATTR_PP_OBJ_ALLOC_HANDLE,
103 MLX5_IB_ATTR_PP_OBJ_ALLOC_CTX,
105 MLX5_ST_SZ_BYTES(set_pp_rate_limit_context)),
108 UVERBS_ATTR_FLAGS_IN(MLX5_IB_ATTR_PP_OBJ_ALLOC_FLAGS,
109 enum mlx5_ib_uapi_pp_alloc_flags,
111 UVERBS_ATTR_PTR_OUT(MLX5_IB_ATTR_PP_OBJ_ALLOC_INDEX,
112 UVERBS_ATTR_TYPE(u16),
115 DECLARE_UVERBS_NAMED_METHOD_DESTROY(
116 MLX5_IB_METHOD_PP_OBJ_DESTROY,
117 UVERBS_ATTR_IDR(MLX5_IB_ATTR_PP_OBJ_DESTROY_HANDLE,
119 UVERBS_ACCESS_DESTROY,
122 DECLARE_UVERBS_NAMED_OBJECT(MLX5_IB_OBJECT_PP,
123 UVERBS_TYPE_ALLOC_IDR(pp_obj_cleanup),
124 &UVERBS_METHOD(MLX5_IB_METHOD_PP_OBJ_ALLOC),
125 &UVERBS_METHOD(MLX5_IB_METHOD_PP_OBJ_DESTROY));
128 const struct uapi_definition mlx5_ib_qos_defs[] = {
129 UAPI_DEF_CHAIN_OBJ_TREE_NAMED(
131 UAPI_DEF_IS_OBJ_SUPPORTED(pp_is_supported)),