Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 272365
b: refs/heads/master
c: 8541f8d
h: refs/heads/master
i:
  272363: 3e8ae34
v: v3
  • Loading branch information
Sean Hefty authored and Roland Dreier committed Oct 13, 2011
1 parent 656ba33 commit fe48904
Show file tree
Hide file tree
Showing 5 changed files with 157 additions and 43 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: 53d0bd1e7ff2fc626321f337c609fb76ae5d12c9
refs/heads/master: 8541f8de0583f562c652008a4e7a65e537842a7e
6 changes: 6 additions & 0 deletions trunk/drivers/infiniband/core/uverbs.h
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,11 @@ struct ib_uxrcd_object {
atomic_t refcnt;
};

struct ib_usrq_object {
struct ib_uevent_object uevent;
struct ib_uxrcd_object *uxrcd;
};

struct ib_uqp_object {
struct ib_uevent_object uevent;
struct list_head mcast_list;
Expand Down Expand Up @@ -204,6 +209,7 @@ IB_UVERBS_DECLARE_CMD(create_srq);
IB_UVERBS_DECLARE_CMD(modify_srq);
IB_UVERBS_DECLARE_CMD(query_srq);
IB_UVERBS_DECLARE_CMD(destroy_srq);
IB_UVERBS_DECLARE_CMD(create_xsrq);
IB_UVERBS_DECLARE_CMD(open_xrcd);
IB_UVERBS_DECLARE_CMD(close_xrcd);

Expand Down
172 changes: 132 additions & 40 deletions trunk/drivers/infiniband/core/uverbs_cmd.c
Original file line number Diff line number Diff line change
Expand Up @@ -1400,7 +1400,8 @@ ssize_t ib_uverbs_create_qp(struct ib_uverbs_file *file,
rcq = cmd.recv_cq_handle == cmd.send_cq_handle ?
scq : idr_read_cq(cmd.recv_cq_handle, file->ucontext, 1);

if (!pd || !scq || !rcq || (cmd.is_srq && !srq)) {
if (!pd || !scq || !rcq ||
(cmd.is_srq && (!srq || srq->srq_type != IB_SRQT_BASIC))) {
ret = -EINVAL;
goto err_put;
}
Expand Down Expand Up @@ -2293,108 +2294,199 @@ ssize_t ib_uverbs_detach_mcast(struct ib_uverbs_file *file,
return ret ? ret : in_len;
}

ssize_t ib_uverbs_create_srq(struct ib_uverbs_file *file,
const char __user *buf, int in_len,
int out_len)
int __uverbs_create_xsrq(struct ib_uverbs_file *file,
struct ib_uverbs_create_xsrq *cmd,
struct ib_udata *udata)
{
struct ib_uverbs_create_srq cmd;
struct ib_uverbs_create_srq_resp resp;
struct ib_udata udata;
struct ib_uevent_object *obj;
struct ib_usrq_object *obj;
struct ib_pd *pd;
struct ib_srq *srq;
struct ib_uobject *uninitialized_var(xrcd_uobj);
struct ib_srq_init_attr attr;
int ret;

if (out_len < sizeof resp)
return -ENOSPC;

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

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

obj = kmalloc(sizeof *obj, GFP_KERNEL);
if (!obj)
return -ENOMEM;

init_uobj(&obj->uobject, cmd.user_handle, file->ucontext, &srq_lock_key);
down_write(&obj->uobject.mutex);
init_uobj(&obj->uevent.uobject, cmd->user_handle, file->ucontext, &srq_lock_key);
down_write(&obj->uevent.uobject.mutex);

pd = idr_read_pd(cmd.pd_handle, file->ucontext);
pd = idr_read_pd(cmd->pd_handle, file->ucontext);
if (!pd) {
ret = -EINVAL;
goto err;
}

if (cmd->srq_type == IB_SRQT_XRC) {
attr.ext.xrc.cq = idr_read_cq(cmd->cq_handle, file->ucontext, 0);
if (!attr.ext.xrc.cq) {
ret = -EINVAL;
goto err_put_pd;
}

attr.ext.xrc.xrcd = idr_read_xrcd(cmd->xrcd_handle, file->ucontext, &xrcd_uobj);
if (!attr.ext.xrc.xrcd) {
ret = -EINVAL;
goto err_put_cq;
}

obj->uxrcd = container_of(xrcd_uobj, struct ib_uxrcd_object, uobject);
atomic_inc(&obj->uxrcd->refcnt);
}

attr.event_handler = ib_uverbs_srq_event_handler;
attr.srq_context = file;
attr.srq_type = IB_SRQT_BASIC;
attr.attr.max_wr = cmd.max_wr;
attr.attr.max_sge = cmd.max_sge;
attr.attr.srq_limit = cmd.srq_limit;
attr.srq_type = cmd->srq_type;
attr.attr.max_wr = cmd->max_wr;
attr.attr.max_sge = cmd->max_sge;
attr.attr.srq_limit = cmd->srq_limit;

obj->events_reported = 0;
INIT_LIST_HEAD(&obj->event_list);
obj->uevent.events_reported = 0;
INIT_LIST_HEAD(&obj->uevent.event_list);

srq = pd->device->create_srq(pd, &attr, &udata);
srq = pd->device->create_srq(pd, &attr, udata);
if (IS_ERR(srq)) {
ret = PTR_ERR(srq);
goto err_put;
}

srq->device = pd->device;
srq->pd = pd;
srq->uobject = &obj->uobject;
srq->device = pd->device;
srq->pd = pd;
srq->srq_type = cmd->srq_type;
srq->uobject = &obj->uevent.uobject;
srq->event_handler = attr.event_handler;
srq->srq_context = attr.srq_context;

if (cmd->srq_type == IB_SRQT_XRC) {
srq->ext.xrc.cq = attr.ext.xrc.cq;
srq->ext.xrc.xrcd = attr.ext.xrc.xrcd;
atomic_inc(&attr.ext.xrc.cq->usecnt);
atomic_inc(&attr.ext.xrc.xrcd->usecnt);
}

atomic_inc(&pd->usecnt);
atomic_set(&srq->usecnt, 0);

obj->uobject.object = srq;
ret = idr_add_uobj(&ib_uverbs_srq_idr, &obj->uobject);
obj->uevent.uobject.object = srq;
ret = idr_add_uobj(&ib_uverbs_srq_idr, &obj->uevent.uobject);
if (ret)
goto err_destroy;

memset(&resp, 0, sizeof resp);
resp.srq_handle = obj->uobject.id;
resp.srq_handle = obj->uevent.uobject.id;
resp.max_wr = attr.attr.max_wr;
resp.max_sge = attr.attr.max_sge;
if (cmd->srq_type == IB_SRQT_XRC)
resp.srqn = srq->ext.xrc.srq_num;

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

if (cmd->srq_type == IB_SRQT_XRC) {
put_uobj_read(xrcd_uobj);
put_cq_read(attr.ext.xrc.cq);
}
put_pd_read(pd);

mutex_lock(&file->mutex);
list_add_tail(&obj->uobject.list, &file->ucontext->srq_list);
list_add_tail(&obj->uevent.uobject.list, &file->ucontext->srq_list);
mutex_unlock(&file->mutex);

obj->uobject.live = 1;
obj->uevent.uobject.live = 1;

up_write(&obj->uobject.mutex);
up_write(&obj->uevent.uobject.mutex);

return in_len;
return 0;

err_copy:
idr_remove_uobj(&ib_uverbs_srq_idr, &obj->uobject);
idr_remove_uobj(&ib_uverbs_srq_idr, &obj->uevent.uobject);

err_destroy:
ib_destroy_srq(srq);

err_put:
if (cmd->srq_type == IB_SRQT_XRC) {
atomic_dec(&obj->uxrcd->refcnt);
put_uobj_read(xrcd_uobj);
}

err_put_cq:
if (cmd->srq_type == IB_SRQT_XRC)
put_cq_read(attr.ext.xrc.cq);

err_put_pd:
put_pd_read(pd);

err:
put_uobj_write(&obj->uobject);
put_uobj_write(&obj->uevent.uobject);
return ret;
}

ssize_t ib_uverbs_create_srq(struct ib_uverbs_file *file,
const char __user *buf, int in_len,
int out_len)
{
struct ib_uverbs_create_srq cmd;
struct ib_uverbs_create_xsrq xcmd;
struct ib_uverbs_create_srq_resp resp;
struct ib_udata udata;
int ret;

if (out_len < sizeof resp)
return -ENOSPC;

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

xcmd.response = cmd.response;
xcmd.user_handle = cmd.user_handle;
xcmd.srq_type = IB_SRQT_BASIC;
xcmd.pd_handle = cmd.pd_handle;
xcmd.max_wr = cmd.max_wr;
xcmd.max_sge = cmd.max_sge;
xcmd.srq_limit = cmd.srq_limit;

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

ret = __uverbs_create_xsrq(file, &xcmd, &udata);
if (ret)
return ret;

return in_len;
}

ssize_t ib_uverbs_create_xsrq(struct ib_uverbs_file *file,
const char __user *buf, int in_len, int out_len)
{
struct ib_uverbs_create_xsrq cmd;
struct ib_uverbs_create_srq_resp resp;
struct ib_udata udata;
int ret;

if (out_len < sizeof resp)
return -ENOSPC;

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

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

ret = __uverbs_create_xsrq(file, &cmd, &udata);
if (ret)
return ret;

return in_len;
}

ssize_t ib_uverbs_modify_srq(struct ib_uverbs_file *file,
const char __user *buf, int in_len,
int out_len)
Expand Down
1 change: 1 addition & 0 deletions trunk/drivers/infiniband/core/uverbs_main.c
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,7 @@ static ssize_t (*uverbs_cmd_table[])(struct ib_uverbs_file *file,
[IB_USER_VERBS_CMD_DESTROY_SRQ] = ib_uverbs_destroy_srq,
[IB_USER_VERBS_CMD_OPEN_XRCD] = ib_uverbs_open_xrcd,
[IB_USER_VERBS_CMD_CLOSE_XRCD] = ib_uverbs_close_xrcd,
[IB_USER_VERBS_CMD_CREATE_XSRQ] = ib_uverbs_create_xsrq
};

static void ib_uverbs_add_one(struct ib_device *device);
Expand Down
19 changes: 17 additions & 2 deletions trunk/include/rdma/ib_user_verbs.h
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,8 @@ enum {
IB_USER_VERBS_CMD_DESTROY_SRQ,
IB_USER_VERBS_CMD_POST_SRQ_RECV,
IB_USER_VERBS_CMD_OPEN_XRCD,
IB_USER_VERBS_CMD_CLOSE_XRCD
IB_USER_VERBS_CMD_CLOSE_XRCD,
IB_USER_VERBS_CMD_CREATE_XSRQ
};

/*
Expand Down Expand Up @@ -665,11 +666,25 @@ struct ib_uverbs_create_srq {
__u64 driver_data[0];
};

struct ib_uverbs_create_xsrq {
__u64 response;
__u64 user_handle;
__u32 srq_type;
__u32 pd_handle;
__u32 max_wr;
__u32 max_sge;
__u32 srq_limit;
__u32 reserved;
__u32 xrcd_handle;
__u32 cq_handle;
__u64 driver_data[0];
};

struct ib_uverbs_create_srq_resp {
__u32 srq_handle;
__u32 max_wr;
__u32 max_sge;
__u32 reserved;
__u32 srqn;
};

struct ib_uverbs_modify_srq {
Expand Down

0 comments on commit fe48904

Please sign in to comment.