From: Leon Romanovsky <leonro@xxxxxxxxxxxx> As a preparation to extension of rdma_restrack_root to provide software IDs, which will be per-type too. We convert the rdma_restrack_root from struct with arrays to array of structs. Signed-off-by: Leon Romanovsky <leonro@xxxxxxxxxxxx> --- drivers/infiniband/core/nldev.c | 18 ++++++------ drivers/infiniband/core/restrack.c | 46 ++++++++++++++++-------------- drivers/infiniband/core/restrack.h | 11 ++----- 3 files changed, 36 insertions(+), 39 deletions(-) diff --git a/drivers/infiniband/core/nldev.c b/drivers/infiniband/core/nldev.c index 91df7dfde11b..522db1f023bc 100644 --- a/drivers/infiniband/core/nldev.c +++ b/drivers/infiniband/core/nldev.c @@ -1018,6 +1018,7 @@ static int res_get_common_dumpit(struct sk_buff *skb, const struct nldev_fill_res_entry *fe = &fill_entries[res_type]; struct nlattr *tb[RDMA_NLDEV_ATTR_MAX]; struct rdma_restrack_entry *res; + struct rdma_restrack_root *rt; int err, ret = 0, idx = 0; struct nlattr *table_attr; struct nlattr *entry_attr; @@ -1028,7 +1029,6 @@ static int res_get_common_dumpit(struct sk_buff *skb, unsigned long id; u32 index, port = 0; bool filled = false; - struct xarray *xa; err = nlmsg_parse(cb->nlh, 0, tb, RDMA_NLDEV_ATTR_MAX - 1, nldev_policy, NULL); @@ -1076,9 +1076,9 @@ static int res_get_common_dumpit(struct sk_buff *skb, has_cap_net_admin = netlink_capable(cb->skb, CAP_NET_ADMIN); - xa = &device->res->xa[res_type]; - down_read(&device->res->rwsem); - xa_for_each(xa, id, res) { + rt = &device->res[res_type]; + down_read(&rt->rwsem); + xa_for_each(&rt->xa, id, res) { if (idx < start) goto next; @@ -1099,13 +1099,13 @@ static int res_get_common_dumpit(struct sk_buff *skb, if (!entry_attr) { ret = -EMSGSIZE; rdma_restrack_put(res); - up_read(&device->res->rwsem); + up_read(&rt->rwsem); break; } - up_read(&device->res->rwsem); + up_read(&rt->rwsem); ret = fe->fill_res_func(skb, has_cap_net_admin, res, port); - down_read(&device->res->rwsem); + down_read(&rt->rwsem); /* * Return resource back, but it won't be released till * the &device->res.rwsem will be released for write. @@ -1126,7 +1126,7 @@ static int res_get_common_dumpit(struct sk_buff *skb, nla_nest_end(skb, entry_attr); next: idx++; } - up_read(&device->res->rwsem); + up_read(&rt->rwsem); nla_nest_end(skb, table_attr); nlmsg_end(skb, nlh); @@ -1144,7 +1144,7 @@ next: idx++; res_err: nla_nest_cancel(skb, table_attr); - up_read(&device->res->rwsem); + up_read(&rt->rwsem); err: nlmsg_cancel(skb, nlh); diff --git a/drivers/infiniband/core/restrack.c b/drivers/infiniband/core/restrack.c index 6a4b76c66bcb..b73e6c693863 100644 --- a/drivers/infiniband/core/restrack.c +++ b/drivers/infiniband/core/restrack.c @@ -47,15 +47,16 @@ int rdma_restrack_init(struct ib_device *dev) struct rdma_restrack_root *rt; int i; - dev->res = kzalloc(sizeof(*rt), GFP_KERNEL); + dev->res = kcalloc(RDMA_RESTRACK_MAX, sizeof(*rt), GFP_KERNEL); if (!dev->res) return -ENOMEM; rt = dev->res; - for (i = 0 ; i < RDMA_RESTRACK_MAX; i++) - xa_init_flags(&rt->xa[i], XA_FLAGS_ALLOC); - init_rwsem(&rt->rwsem); + for (i = 0 ; i < RDMA_RESTRACK_MAX; i++) { + init_rwsem(&rt[i].rwsem); + xa_init_flags(&rt[i].xa, XA_FLAGS_ALLOC); + } return 0; } @@ -88,7 +89,7 @@ void rdma_restrack_clean(struct ib_device *dev) int i; for (i = 0 ; i < RDMA_RESTRACK_MAX; i++) { - struct xarray *xa = &dev->res->xa[i]; + struct xarray *xa = &dev->res[i].xa; if (!xa_empty(xa)) { unsigned long index; @@ -134,19 +135,20 @@ void rdma_restrack_clean(struct ib_device *dev) int rdma_restrack_count(struct ib_device *dev, enum rdma_restrack_type type, struct pid_namespace *ns) { - struct xarray *xa = &dev->res->xa[type]; struct rdma_restrack_entry *e; + struct rdma_restrack_root *rt; unsigned long index = 0; u32 cnt = 0; - down_read(&dev->res->rwsem); - xa_for_each(xa, index, e) { + rt = &dev->res[type]; + down_read(&rt->rwsem); + xa_for_each(&rt->xa, index, e) { if (ns == &init_pid_ns || (!rdma_is_kernel_res(e) && ns == task_active_pid_ns(e->task))) cnt++; } - up_read(&dev->res->rwsem); + up_read(&rt->rwsem); return cnt; } EXPORT_SYMBOL(rdma_restrack_count); @@ -218,18 +220,16 @@ static void rdma_restrack_add(struct rdma_restrack_entry *res) { struct ib_device *dev = res_to_dev(res); struct rdma_restrack_root *rt; - struct xarray *xa; int ret; if (!dev) return; - rt = dev->res; - xa = &dev->res->xa[res->type]; + rt = &dev->res[res->type]; kref_init(&res->kref); init_completion(&res->comp); - ret = rt_xa_alloc_cyclic(xa, &res->id, res, &rt->next_id[res->type]); + ret = rt_xa_alloc_cyclic(&rt->xa, &res->id, res, &rt->next_id); if (!ret) res->valid = true; } @@ -283,14 +283,15 @@ struct rdma_restrack_entry * rdma_restrack_get_byid(struct ib_device *dev, enum rdma_restrack_type type, u32 id) { - struct xarray *xa = &dev->res->xa[type]; struct rdma_restrack_entry *res; + struct rdma_restrack_root *rt; - down_read(&dev->res->rwsem); - res = xa_load(xa, id); + rt = &dev->res[type]; + down_read(&rt->rwsem); + res = xa_load(&rt->xa, id); if (!res || !rdma_restrack_get(res)) res = ERR_PTR(-ENOENT); - up_read(&dev->res->rwsem); + up_read(&rt->rwsem); return res; } @@ -313,7 +314,7 @@ EXPORT_SYMBOL(rdma_restrack_put); void rdma_restrack_del(struct rdma_restrack_entry *res) { struct ib_device *dev = res_to_dev(res); - struct xarray *xa; + struct rdma_restrack_root *rt; if (!res->valid) goto out; @@ -334,11 +335,12 @@ void rdma_restrack_del(struct rdma_restrack_entry *res) if (!dev) return; - xa = &dev->res->xa[res->type]; - down_write(&dev->res->rwsem); - xa_erase(xa, res->id); + rt = &dev->res[res->type]; + + down_write(&rt->rwsem); + xa_erase(&rt->xa, res->id); res->valid = false; - up_write(&dev->res->rwsem); + up_write(&rt->rwsem); rdma_restrack_put(res); wait_for_completion(&res->comp); diff --git a/drivers/infiniband/core/restrack.h b/drivers/infiniband/core/restrack.h index 34f7cf29dcc0..2ea6ec3a58c4 100644 --- a/drivers/infiniband/core/restrack.h +++ b/drivers/infiniband/core/restrack.h @@ -20,20 +20,15 @@ struct rdma_restrack_root { */ struct rw_semaphore rwsem; /** - * @xa: Array of XArray structures to hold restrack entries. - * We want to use array of XArrays because insertion is type - * dependent. For types with xisiting unique ID (like QPN), - * we will insert to that unique index. For other types, - * we insert based on pointers and auto-allocate unique index. + * @xa: Array of XArray structure to hold restrack entries. */ - struct xarray xa[RDMA_RESTRACK_MAX]; + struct xarray xa; /** * #next_id: Next ID to support cyclic allocation */ - u32 next_id[RDMA_RESTRACK_MAX]; + u32 next_id; }; - int rdma_restrack_init(struct ib_device *dev); void rdma_restrack_clean(struct ib_device *dev); #endif /* _RDMA_CORE_RESTRACK_H_ */ -- 2.19.1