aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/infiniband/core/uverbs_uapi.c
diff options
context:
space:
mode:
authorJason Gunthorpe <jgg@mellanox.com>2018-11-12 22:59:58 +0200
committerJason Gunthorpe <jgg@mellanox.com>2018-11-22 11:57:33 -0700
commita140692a52d2e12ba6a76dd042d556348e8bb55a (patch)
treed168281ba7eca4abde7746f7398d4d2187437a09 /drivers/infiniband/core/uverbs_uapi.c
parentRDMA/uverbs: Make all the method functions in uverbs_cmd static (diff)
downloadlinux-dev-a140692a52d2e12ba6a76dd042d556348e8bb55a.tar.xz
linux-dev-a140692a52d2e12ba6a76dd042d556348e8bb55a.zip
RDMA/uverbs: Check for NULL driver methods for every write call
Add annotations to the uverbs_api structure indicating which driver methods are called by the implementation. If the required method is NULL the write API will be not be callable. This effectively duplicates the cmd_mask system, however it does it by expressing invariants required by the core code, not by delegating decision making to the driver. This is another step toward eliminating cmd_mask. Signed-off-by: Jason Gunthorpe <jgg@mellanox.com> Signed-off-by: Leon Romanovsky <leonro@mellanox.com>
Diffstat (limited to 'drivers/infiniband/core/uverbs_uapi.c')
-rw-r--r--drivers/infiniband/core/uverbs_uapi.c47
1 files changed, 41 insertions, 6 deletions
diff --git a/drivers/infiniband/core/uverbs_uapi.c b/drivers/infiniband/core/uverbs_uapi.c
index 1e880f1d9d62..a92adbe2b034 100644
--- a/drivers/infiniband/core/uverbs_uapi.c
+++ b/drivers/infiniband/core/uverbs_uapi.c
@@ -60,8 +60,11 @@ static void *uapi_add_get_elm(struct uverbs_api *uapi, u32 key,
return elm;
}
-static int uapi_create_write(struct uverbs_api *uapi, struct ib_device *ibdev,
- const struct uapi_definition *def, u32 obj_key)
+static int uapi_create_write(struct uverbs_api *uapi,
+ struct ib_device *ibdev,
+ const struct uapi_definition *def,
+ u32 obj_key,
+ u32 *cur_method_key)
{
struct uverbs_api_write_method *method_elm;
u32 method_key = obj_key;
@@ -93,6 +96,8 @@ static int uapi_create_write(struct uverbs_api *uapi, struct ib_device *ibdev,
method_elm->disabled = !(ibdev->uverbs_cmd_mask &
BIT_ULL(def->write.command_num));
}
+
+ *cur_method_key = method_key;
return 0;
}
@@ -218,7 +223,8 @@ static int uapi_merge_obj_tree(struct uverbs_api *uapi,
static int uapi_disable_elm(struct uverbs_api *uapi,
const struct uapi_definition *def,
- u32 obj_key)
+ u32 obj_key,
+ u32 method_key)
{
bool exists;
@@ -233,6 +239,31 @@ static int uapi_disable_elm(struct uverbs_api *uapi,
return 0;
}
+ if (def->scope == UAPI_SCOPE_METHOD &&
+ uapi_key_is_ioctl_method(method_key)) {
+ struct uverbs_api_ioctl_method *method_elm;
+
+ method_elm = uapi_add_get_elm(uapi, method_key,
+ sizeof(*method_elm), &exists);
+ if (IS_ERR(method_elm))
+ return PTR_ERR(method_elm);
+ method_elm->disabled = 1;
+ return 0;
+ }
+
+ if (def->scope == UAPI_SCOPE_METHOD &&
+ (uapi_key_is_write_method(method_key) ||
+ uapi_key_is_write_ex_method(method_key))) {
+ struct uverbs_api_write_method *write_elm;
+
+ write_elm = uapi_add_get_elm(uapi, method_key,
+ sizeof(*write_elm), &exists);
+ if (IS_ERR(write_elm))
+ return PTR_ERR(write_elm);
+ write_elm->disabled = 1;
+ return 0;
+ }
+
WARN_ON(true);
return -EINVAL;
}
@@ -243,6 +274,7 @@ static int uapi_merge_def(struct uverbs_api *uapi, struct ib_device *ibdev,
{
const struct uapi_definition *def = def_list;
u32 cur_obj_key = UVERBS_API_KEY_ERR;
+ u32 cur_method_key = UVERBS_API_KEY_ERR;
bool exists;
int rc;
@@ -277,7 +309,8 @@ static int uapi_merge_def(struct uverbs_api *uapi, struct ib_device *ibdev,
if (*ibdev_fn)
continue;
- rc = uapi_disable_elm(uapi, def, cur_obj_key);
+ rc = uapi_disable_elm(
+ uapi, def, cur_obj_key, cur_method_key);
if (rc)
return rc;
continue;
@@ -286,7 +319,8 @@ static int uapi_merge_def(struct uverbs_api *uapi, struct ib_device *ibdev,
case UAPI_DEF_IS_SUPPORTED_FUNC:
if (def->func_is_supported(ibdev))
continue;
- rc = uapi_disable_elm(uapi, def, cur_obj_key);
+ rc = uapi_disable_elm(
+ uapi, def, cur_obj_key, cur_method_key);
if (rc)
return rc;
continue;
@@ -303,7 +337,8 @@ static int uapi_merge_def(struct uverbs_api *uapi, struct ib_device *ibdev,
}
case UAPI_DEF_WRITE:
- rc = uapi_create_write(uapi, ibdev, def, cur_obj_key);
+ rc = uapi_create_write(
+ uapi, ibdev, def, cur_obj_key, &cur_method_key);
if (rc)
return rc;
continue;