Commit 710214e3 authored by Ilya Dryomov's avatar Ilya Dryomov

rbd: rework rbd_img_obj_exists_submit() error paths

- don't put obj_request before rbd_obj_request_get() if
  rbd_obj_request_create() fails
- don't leak pages if rbd_obj_request_create() fails
- don't leak stat_request if rbd_osd_req_create() fails
Reported-by: default avatarDavid Disseldorp <ddiss@suse.de>
Signed-off-by: default avatarIlya Dryomov <idryomov@gmail.com>
Reviewed-by: default avatarAlex Elder <elder@linaro.org>
Reviewed-by: default avatarDavid Disseldorp <ddiss@suse.de>
parent fa355112
...@@ -2894,11 +2894,23 @@ static int rbd_img_obj_exists_submit(struct rbd_obj_request *obj_request) ...@@ -2894,11 +2894,23 @@ static int rbd_img_obj_exists_submit(struct rbd_obj_request *obj_request)
{ {
struct rbd_device *rbd_dev = obj_request->img_request->rbd_dev; struct rbd_device *rbd_dev = obj_request->img_request->rbd_dev;
struct rbd_obj_request *stat_request; struct rbd_obj_request *stat_request;
struct page **pages = NULL; struct page **pages;
u32 page_count; u32 page_count;
size_t size; size_t size;
int ret; int ret;
stat_request = rbd_obj_request_create(obj_request->object_name, 0, 0,
OBJ_REQUEST_PAGES);
if (!stat_request)
return -ENOMEM;
stat_request->osd_req = rbd_osd_req_create(rbd_dev, OBJ_OP_READ, 1,
stat_request);
if (!stat_request->osd_req) {
ret = -ENOMEM;
goto fail_stat_request;
}
/* /*
* The response data for a STAT call consists of: * The response data for a STAT call consists of:
* le64 length; * le64 length;
...@@ -2910,38 +2922,28 @@ static int rbd_img_obj_exists_submit(struct rbd_obj_request *obj_request) ...@@ -2910,38 +2922,28 @@ static int rbd_img_obj_exists_submit(struct rbd_obj_request *obj_request)
size = sizeof (__le64) + sizeof (__le32) + sizeof (__le32); size = sizeof (__le64) + sizeof (__le32) + sizeof (__le32);
page_count = (u32)calc_pages_for(0, size); page_count = (u32)calc_pages_for(0, size);
pages = ceph_alloc_page_vector(page_count, GFP_KERNEL); pages = ceph_alloc_page_vector(page_count, GFP_KERNEL);
if (IS_ERR(pages)) if (IS_ERR(pages)) {
return PTR_ERR(pages); ret = PTR_ERR(pages);
goto fail_stat_request;
}
ret = -ENOMEM; osd_req_op_init(stat_request->osd_req, 0, CEPH_OSD_OP_STAT, 0);
stat_request = rbd_obj_request_create(obj_request->object_name, 0, 0, osd_req_op_raw_data_in_pages(stat_request->osd_req, 0, pages, size, 0,
OBJ_REQUEST_PAGES); false, false);
if (!stat_request)
goto out;
rbd_obj_request_get(obj_request); rbd_obj_request_get(obj_request);
stat_request->obj_request = obj_request; stat_request->obj_request = obj_request;
stat_request->pages = pages; stat_request->pages = pages;
stat_request->page_count = page_count; stat_request->page_count = page_count;
stat_request->osd_req = rbd_osd_req_create(rbd_dev, OBJ_OP_READ, 1,
stat_request);
if (!stat_request->osd_req)
goto out;
stat_request->callback = rbd_img_obj_exists_callback; stat_request->callback = rbd_img_obj_exists_callback;
osd_req_op_init(stat_request->osd_req, 0, CEPH_OSD_OP_STAT, 0);
osd_req_op_raw_data_in_pages(stat_request->osd_req, 0, pages, size, 0,
false, false);
rbd_osd_req_format_read(stat_request); rbd_osd_req_format_read(stat_request);
rbd_obj_request_submit(stat_request); rbd_obj_request_submit(stat_request);
return 0; return 0;
out: fail_stat_request:
if (ret) rbd_obj_request_put(stat_request);
rbd_obj_request_put(obj_request);
return ret; return ret;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment