diff options
-rw-r--r-- | drivers/infiniband/core/uverbs_cmd.c | 34 |
1 files changed, 19 insertions, 15 deletions
diff --git a/drivers/infiniband/core/uverbs_cmd.c b/drivers/infiniband/core/uverbs_cmd.c index b81307b625a6..8b6df7cec0bf 100644 --- a/drivers/infiniband/core/uverbs_cmd.c +++ b/drivers/infiniband/core/uverbs_cmd.c | |||
@@ -155,7 +155,7 @@ static struct ib_uobject *__idr_get_uobj(struct idr *idr, int id, | |||
155 | } | 155 | } |
156 | 156 | ||
157 | static struct ib_uobject *idr_read_uobj(struct idr *idr, int id, | 157 | static struct ib_uobject *idr_read_uobj(struct idr *idr, int id, |
158 | struct ib_ucontext *context) | 158 | struct ib_ucontext *context, int nested) |
159 | { | 159 | { |
160 | struct ib_uobject *uobj; | 160 | struct ib_uobject *uobj; |
161 | 161 | ||
@@ -163,7 +163,10 @@ static struct ib_uobject *idr_read_uobj(struct idr *idr, int id, | |||
163 | if (!uobj) | 163 | if (!uobj) |
164 | return NULL; | 164 | return NULL; |
165 | 165 | ||
166 | down_read(&uobj->mutex); | 166 | if (nested) |
167 | down_read_nested(&uobj->mutex, SINGLE_DEPTH_NESTING); | ||
168 | else | ||
169 | down_read(&uobj->mutex); | ||
167 | if (!uobj->live) { | 170 | if (!uobj->live) { |
168 | put_uobj_read(uobj); | 171 | put_uobj_read(uobj); |
169 | return NULL; | 172 | return NULL; |
@@ -190,17 +193,18 @@ static struct ib_uobject *idr_write_uobj(struct idr *idr, int id, | |||
190 | return uobj; | 193 | return uobj; |
191 | } | 194 | } |
192 | 195 | ||
193 | static void *idr_read_obj(struct idr *idr, int id, struct ib_ucontext *context) | 196 | static void *idr_read_obj(struct idr *idr, int id, struct ib_ucontext *context, |
197 | int nested) | ||
194 | { | 198 | { |
195 | struct ib_uobject *uobj; | 199 | struct ib_uobject *uobj; |
196 | 200 | ||
197 | uobj = idr_read_uobj(idr, id, context); | 201 | uobj = idr_read_uobj(idr, id, context, nested); |
198 | return uobj ? uobj->object : NULL; | 202 | return uobj ? uobj->object : NULL; |
199 | } | 203 | } |
200 | 204 | ||
201 | static struct ib_pd *idr_read_pd(int pd_handle, struct ib_ucontext *context) | 205 | static struct ib_pd *idr_read_pd(int pd_handle, struct ib_ucontext *context) |
202 | { | 206 | { |
203 | return idr_read_obj(&ib_uverbs_pd_idr, pd_handle, context); | 207 | return idr_read_obj(&ib_uverbs_pd_idr, pd_handle, context, 0); |
204 | } | 208 | } |
205 | 209 | ||
206 | static void put_pd_read(struct ib_pd *pd) | 210 | static void put_pd_read(struct ib_pd *pd) |
@@ -208,9 +212,9 @@ static void put_pd_read(struct ib_pd *pd) | |||
208 | put_uobj_read(pd->uobject); | 212 | put_uobj_read(pd->uobject); |
209 | } | 213 | } |
210 | 214 | ||
211 | static struct ib_cq *idr_read_cq(int cq_handle, struct ib_ucontext *context) | 215 | static struct ib_cq *idr_read_cq(int cq_handle, struct ib_ucontext *context, int nested) |
212 | { | 216 | { |
213 | return idr_read_obj(&ib_uverbs_cq_idr, cq_handle, context); | 217 | return idr_read_obj(&ib_uverbs_cq_idr, cq_handle, context, nested); |
214 | } | 218 | } |
215 | 219 | ||
216 | static void put_cq_read(struct ib_cq *cq) | 220 | static void put_cq_read(struct ib_cq *cq) |
@@ -220,7 +224,7 @@ static void put_cq_read(struct ib_cq *cq) | |||
220 | 224 | ||
221 | static struct ib_ah *idr_read_ah(int ah_handle, struct ib_ucontext *context) | 225 | static struct ib_ah *idr_read_ah(int ah_handle, struct ib_ucontext *context) |
222 | { | 226 | { |
223 | return idr_read_obj(&ib_uverbs_ah_idr, ah_handle, context); | 227 | return idr_read_obj(&ib_uverbs_ah_idr, ah_handle, context, 0); |
224 | } | 228 | } |
225 | 229 | ||
226 | static void put_ah_read(struct ib_ah *ah) | 230 | static void put_ah_read(struct ib_ah *ah) |
@@ -230,7 +234,7 @@ static void put_ah_read(struct ib_ah *ah) | |||
230 | 234 | ||
231 | static struct ib_qp *idr_read_qp(int qp_handle, struct ib_ucontext *context) | 235 | static struct ib_qp *idr_read_qp(int qp_handle, struct ib_ucontext *context) |
232 | { | 236 | { |
233 | return idr_read_obj(&ib_uverbs_qp_idr, qp_handle, context); | 237 | return idr_read_obj(&ib_uverbs_qp_idr, qp_handle, context, 0); |
234 | } | 238 | } |
235 | 239 | ||
236 | static void put_qp_read(struct ib_qp *qp) | 240 | static void put_qp_read(struct ib_qp *qp) |
@@ -240,7 +244,7 @@ static void put_qp_read(struct ib_qp *qp) | |||
240 | 244 | ||
241 | static struct ib_srq *idr_read_srq(int srq_handle, struct ib_ucontext *context) | 245 | static struct ib_srq *idr_read_srq(int srq_handle, struct ib_ucontext *context) |
242 | { | 246 | { |
243 | return idr_read_obj(&ib_uverbs_srq_idr, srq_handle, context); | 247 | return idr_read_obj(&ib_uverbs_srq_idr, srq_handle, context, 0); |
244 | } | 248 | } |
245 | 249 | ||
246 | static void put_srq_read(struct ib_srq *srq) | 250 | static void put_srq_read(struct ib_srq *srq) |
@@ -867,7 +871,7 @@ ssize_t ib_uverbs_resize_cq(struct ib_uverbs_file *file, | |||
867 | (unsigned long) cmd.response + sizeof resp, | 871 | (unsigned long) cmd.response + sizeof resp, |
868 | in_len - sizeof cmd, out_len - sizeof resp); | 872 | in_len - sizeof cmd, out_len - sizeof resp); |
869 | 873 | ||
870 | cq = idr_read_cq(cmd.cq_handle, file->ucontext); | 874 | cq = idr_read_cq(cmd.cq_handle, file->ucontext, 0); |
871 | if (!cq) | 875 | if (!cq) |
872 | return -EINVAL; | 876 | return -EINVAL; |
873 | 877 | ||
@@ -914,7 +918,7 @@ ssize_t ib_uverbs_poll_cq(struct ib_uverbs_file *file, | |||
914 | goto out_wc; | 918 | goto out_wc; |
915 | } | 919 | } |
916 | 920 | ||
917 | cq = idr_read_cq(cmd.cq_handle, file->ucontext); | 921 | cq = idr_read_cq(cmd.cq_handle, file->ucontext, 0); |
918 | if (!cq) { | 922 | if (!cq) { |
919 | ret = -EINVAL; | 923 | ret = -EINVAL; |
920 | goto out; | 924 | goto out; |
@@ -962,7 +966,7 @@ ssize_t ib_uverbs_req_notify_cq(struct ib_uverbs_file *file, | |||
962 | if (copy_from_user(&cmd, buf, sizeof cmd)) | 966 | if (copy_from_user(&cmd, buf, sizeof cmd)) |
963 | return -EFAULT; | 967 | return -EFAULT; |
964 | 968 | ||
965 | cq = idr_read_cq(cmd.cq_handle, file->ucontext); | 969 | cq = idr_read_cq(cmd.cq_handle, file->ucontext, 0); |
966 | if (!cq) | 970 | if (!cq) |
967 | return -EINVAL; | 971 | return -EINVAL; |
968 | 972 | ||
@@ -1060,9 +1064,9 @@ ssize_t ib_uverbs_create_qp(struct ib_uverbs_file *file, | |||
1060 | 1064 | ||
1061 | srq = cmd.is_srq ? idr_read_srq(cmd.srq_handle, file->ucontext) : NULL; | 1065 | srq = cmd.is_srq ? idr_read_srq(cmd.srq_handle, file->ucontext) : NULL; |
1062 | pd = idr_read_pd(cmd.pd_handle, file->ucontext); | 1066 | pd = idr_read_pd(cmd.pd_handle, file->ucontext); |
1063 | scq = idr_read_cq(cmd.send_cq_handle, file->ucontext); | 1067 | scq = idr_read_cq(cmd.send_cq_handle, file->ucontext, 0); |
1064 | rcq = cmd.recv_cq_handle == cmd.send_cq_handle ? | 1068 | rcq = cmd.recv_cq_handle == cmd.send_cq_handle ? |
1065 | scq : idr_read_cq(cmd.recv_cq_handle, file->ucontext); | 1069 | scq : idr_read_cq(cmd.recv_cq_handle, file->ucontext, 1); |
1066 | 1070 | ||
1067 | if (!pd || !scq || !rcq || (cmd.is_srq && !srq)) { | 1071 | if (!pd || !scq || !rcq || (cmd.is_srq && !srq)) { |
1068 | ret = -EINVAL; | 1072 | ret = -EINVAL; |