Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 9403
b: refs/heads/master
c: 63c47c2
h: refs/heads/master
i:
  9401: ca6df85
  9399: 3be2928
v: v3
  • Loading branch information
Roland Dreier committed Sep 26, 2005
1 parent ec79949 commit 1204bf9
Show file tree
Hide file tree
Showing 5 changed files with 87 additions and 64 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 44dd823b00fa64bf01e53557d28555011f122a88
refs/heads/master: 63c47c286d062d93e0501d60797274c84a587e97
1 change: 1 addition & 0 deletions trunk/drivers/infiniband/core/uverbs.h
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@ struct ib_uverbs_event_file {

struct ib_uverbs_file {
struct kref ref;
struct semaphore mutex;
struct ib_uverbs_device *device;
struct ib_ucontext *ucontext;
struct ib_event_handler event_handler;
Expand Down
120 changes: 66 additions & 54 deletions trunk/drivers/infiniband/core/uverbs_cmd.c
Original file line number Diff line number Diff line change
Expand Up @@ -76,54 +76,66 @@ ssize_t ib_uverbs_get_context(struct ib_uverbs_file *file,
struct ib_uverbs_get_context_resp resp;
struct ib_udata udata;
struct ib_device *ibdev = file->device->ib_dev;
struct ib_ucontext *ucontext;
int i;
int ret = in_len;
int ret;

if (out_len < sizeof resp)
return -ENOSPC;

if (copy_from_user(&cmd, buf, sizeof cmd))
return -EFAULT;

down(&file->mutex);

if (file->ucontext) {
ret = -EINVAL;
goto err;
}

INIT_UDATA(&udata, buf + sizeof cmd,
(unsigned long) cmd.response + sizeof resp,
in_len - sizeof cmd, out_len - sizeof resp);

file->ucontext = ibdev->alloc_ucontext(ibdev, &udata);
if (IS_ERR(file->ucontext)) {
ret = PTR_ERR(file->ucontext);
file->ucontext = NULL;
return ret;
}
ucontext = ibdev->alloc_ucontext(ibdev, &udata);
if (IS_ERR(ucontext))
return PTR_ERR(file->ucontext);

file->ucontext->device = ibdev;
INIT_LIST_HEAD(&file->ucontext->pd_list);
INIT_LIST_HEAD(&file->ucontext->mr_list);
INIT_LIST_HEAD(&file->ucontext->mw_list);
INIT_LIST_HEAD(&file->ucontext->cq_list);
INIT_LIST_HEAD(&file->ucontext->qp_list);
INIT_LIST_HEAD(&file->ucontext->srq_list);
INIT_LIST_HEAD(&file->ucontext->ah_list);
spin_lock_init(&file->ucontext->lock);
ucontext->device = ibdev;
INIT_LIST_HEAD(&ucontext->pd_list);
INIT_LIST_HEAD(&ucontext->mr_list);
INIT_LIST_HEAD(&ucontext->mw_list);
INIT_LIST_HEAD(&ucontext->cq_list);
INIT_LIST_HEAD(&ucontext->qp_list);
INIT_LIST_HEAD(&ucontext->srq_list);
INIT_LIST_HEAD(&ucontext->ah_list);

resp.async_fd = file->async_file.fd;
for (i = 0; i < file->device->num_comp; ++i)
if (copy_to_user((void __user *) (unsigned long) cmd.cq_fd_tab +
i * sizeof (__u32),
&file->comp_file[i].fd, sizeof (__u32)))
goto err;
&file->comp_file[i].fd, sizeof (__u32))) {
ret = -EFAULT;
goto err_free;
}

if (copy_to_user((void __user *) (unsigned long) cmd.response,
&resp, sizeof resp))
goto err;
&resp, sizeof resp)) {
ret = -EFAULT;
goto err_free;
}

file->ucontext = ucontext;
up(&file->mutex);

return in_len;

err:
ibdev->dealloc_ucontext(file->ucontext);
file->ucontext = NULL;
err_free:
ibdev->dealloc_ucontext(ucontext);

return -EFAULT;
err:
up(&file->mutex);
return ret;
}

ssize_t ib_uverbs_query_device(struct ib_uverbs_file *file,
Expand Down Expand Up @@ -352,9 +364,9 @@ ssize_t ib_uverbs_alloc_pd(struct ib_uverbs_file *file,
if (ret)
goto err_pd;

spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_add_tail(&uobj->list, &file->ucontext->pd_list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

memset(&resp, 0, sizeof resp);
resp.pd_handle = uobj->id;
Expand All @@ -368,9 +380,9 @@ ssize_t ib_uverbs_alloc_pd(struct ib_uverbs_file *file,
return in_len;

err_list:
spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_del(&uobj->list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

down(&ib_uverbs_idr_mutex);
idr_remove(&ib_uverbs_pd_idr, uobj->id);
Expand Down Expand Up @@ -410,9 +422,9 @@ ssize_t ib_uverbs_dealloc_pd(struct ib_uverbs_file *file,

idr_remove(&ib_uverbs_pd_idr, cmd.pd_handle);

spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_del(&uobj->list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

kfree(uobj);

Expand Down Expand Up @@ -512,9 +524,9 @@ ssize_t ib_uverbs_reg_mr(struct ib_uverbs_file *file,

resp.mr_handle = obj->uobject.id;

spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_add_tail(&obj->uobject.list, &file->ucontext->mr_list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

if (copy_to_user((void __user *) (unsigned long) cmd.response,
&resp, sizeof resp)) {
Expand All @@ -527,9 +539,9 @@ ssize_t ib_uverbs_reg_mr(struct ib_uverbs_file *file,
return in_len;

err_list:
spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_del(&obj->uobject.list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

err_unreg:
ib_dereg_mr(mr);
Expand Down Expand Up @@ -570,9 +582,9 @@ ssize_t ib_uverbs_dereg_mr(struct ib_uverbs_file *file,

idr_remove(&ib_uverbs_mr_idr, cmd.mr_handle);

spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_del(&memobj->uobject.list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

ib_umem_release(file->device->ib_dev, &memobj->umem);
kfree(memobj);
Expand Down Expand Up @@ -647,9 +659,9 @@ ssize_t ib_uverbs_create_cq(struct ib_uverbs_file *file,
if (ret)
goto err_cq;

spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_add_tail(&uobj->uobject.list, &file->ucontext->cq_list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

memset(&resp, 0, sizeof resp);
resp.cq_handle = uobj->uobject.id;
Expand All @@ -664,9 +676,9 @@ ssize_t ib_uverbs_create_cq(struct ib_uverbs_file *file,
return in_len;

err_list:
spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_del(&uobj->uobject.list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

down(&ib_uverbs_idr_mutex);
idr_remove(&ib_uverbs_cq_idr, uobj->uobject.id);
Expand Down Expand Up @@ -712,9 +724,9 @@ ssize_t ib_uverbs_destroy_cq(struct ib_uverbs_file *file,

idr_remove(&ib_uverbs_cq_idr, cmd.cq_handle);

spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_del(&uobj->uobject.list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

spin_lock_irq(&file->comp_file[0].lock);
list_for_each_entry_safe(evt, tmp, &uobj->comp_list, obj_list) {
Expand Down Expand Up @@ -847,9 +859,9 @@ ssize_t ib_uverbs_create_qp(struct ib_uverbs_file *file,

resp.qp_handle = uobj->uobject.id;

spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_add_tail(&uobj->uobject.list, &file->ucontext->qp_list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

if (copy_to_user((void __user *) (unsigned long) cmd.response,
&resp, sizeof resp)) {
Expand All @@ -862,9 +874,9 @@ ssize_t ib_uverbs_create_qp(struct ib_uverbs_file *file,
return in_len;

err_list:
spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_del(&uobj->uobject.list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

err_destroy:
ib_destroy_qp(qp);
Expand Down Expand Up @@ -989,9 +1001,9 @@ ssize_t ib_uverbs_destroy_qp(struct ib_uverbs_file *file,

idr_remove(&ib_uverbs_qp_idr, cmd.qp_handle);

spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_del(&uobj->uobject.list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

spin_lock_irq(&file->async_file.lock);
list_for_each_entry_safe(evt, tmp, &uobj->event_list, obj_list) {
Expand Down Expand Up @@ -1136,9 +1148,9 @@ ssize_t ib_uverbs_create_srq(struct ib_uverbs_file *file,

resp.srq_handle = uobj->uobject.id;

spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_add_tail(&uobj->uobject.list, &file->ucontext->srq_list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

if (copy_to_user((void __user *) (unsigned long) cmd.response,
&resp, sizeof resp)) {
Expand All @@ -1151,9 +1163,9 @@ ssize_t ib_uverbs_create_srq(struct ib_uverbs_file *file,
return in_len;

err_list:
spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_del(&uobj->uobject.list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

err_destroy:
ib_destroy_srq(srq);
Expand Down Expand Up @@ -1227,9 +1239,9 @@ ssize_t ib_uverbs_destroy_srq(struct ib_uverbs_file *file,

idr_remove(&ib_uverbs_srq_idr, cmd.srq_handle);

spin_lock_irq(&file->ucontext->lock);
down(&file->mutex);
list_del(&uobj->uobject.list);
spin_unlock_irq(&file->ucontext->lock);
up(&file->mutex);

spin_lock_irq(&file->async_file.lock);
list_for_each_entry_safe(evt, tmp, &uobj->event_list, obj_list) {
Expand Down
27 changes: 19 additions & 8 deletions trunk/drivers/infiniband/core/uverbs_main.c
Original file line number Diff line number Diff line change
Expand Up @@ -448,7 +448,9 @@ static ssize_t ib_uverbs_write(struct file *filp, const char __user *buf,
if (hdr.in_words * 4 != count)
return -EINVAL;

if (hdr.command < 0 || hdr.command >= ARRAY_SIZE(uverbs_cmd_table))
if (hdr.command < 0 ||
hdr.command >= ARRAY_SIZE(uverbs_cmd_table) ||
!uverbs_cmd_table[hdr.command])
return -EINVAL;

if (!file->ucontext &&
Expand Down Expand Up @@ -484,27 +486,29 @@ static int ib_uverbs_open(struct inode *inode, struct file *filp)
file = kmalloc(sizeof *file +
(dev->num_comp - 1) * sizeof (struct ib_uverbs_event_file),
GFP_KERNEL);
if (!file)
return -ENOMEM;
if (!file) {
ret = -ENOMEM;
goto err;
}

file->device = dev;
kref_init(&file->ref);
init_MUTEX(&file->mutex);

file->ucontext = NULL;

kref_get(&file->ref);
ret = ib_uverbs_event_init(&file->async_file, file);
if (ret)
goto err;
goto err_kref;

file->async_file.is_async = 1;

kref_get(&file->ref);

for (i = 0; i < dev->num_comp; ++i) {
kref_get(&file->ref);
ret = ib_uverbs_event_init(&file->comp_file[i], file);
if (ret)
goto err_async;
kref_get(&file->ref);
file->comp_file[i].is_async = 0;
}

Expand All @@ -524,9 +528,16 @@ static int ib_uverbs_open(struct inode *inode, struct file *filp)

ib_uverbs_event_release(&file->async_file);

err:
err_kref:
/*
* One extra kref_put() because we took a reference before the
* event file creation that failed and got us here.
*/
kref_put(&file->ref, ib_uverbs_release_file);
kref_put(&file->ref, ib_uverbs_release_file);

err:
module_put(dev->ib_dev->owner);
return ret;
}

Expand Down
1 change: 0 additions & 1 deletion trunk/include/rdma/ib_verbs.h
Original file line number Diff line number Diff line change
Expand Up @@ -665,7 +665,6 @@ struct ib_ucontext {
struct list_head qp_list;
struct list_head srq_list;
struct list_head ah_list;
spinlock_t lock;
};

struct ib_uobject {
Expand Down

0 comments on commit 1204bf9

Please sign in to comment.