From 2c8a0041c1018a6945c7e08ae63324d5934ef954 Mon Sep 17 00:00:00 2001 From: ZhangXiaoxu Date: Wed, 13 Feb 2019 14:31:54 +0800 Subject: [PATCH] CIFS: Fix possible oops and memory leaks in async IO mainline inclusion from mainline-v5.0-rc4-4-g9bda872 commit 9bda8723da2d category: bugfix bugzilla: 7426 CVE: NA ------------------------------------------------- Allocation of a page array for non-cached IO was separated from allocation of rdata and wdata structures and this introduced memory leaks and a possible null pointer dereference. This patch fixes these problems. conflict: fs/cifs/file.c Cc: Signed-off-by: Pavel Shilovsky Signed-off-by: Steve French Signed-off-by: ZhangXiaoxu Reviewed-by: Miao Xie Signed-off-by: Yang Yingliang --- fs/cifs/file.c | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/fs/cifs/file.c b/fs/cifs/file.c index 7b637fc27990..e19e9b54f57d 100644 --- a/fs/cifs/file.c +++ b/fs/cifs/file.c @@ -2564,6 +2564,7 @@ cifs_write_from_iter(loff_t offset, size_t len, struct iov_iter *from, rc = cifs_write_allocate_pages(wdata->pages, nr_pages); if (rc) { + kvfree(wdata->pages); kfree(wdata); add_credits_and_wake_if(server, credits, 0); break; @@ -2574,6 +2575,7 @@ cifs_write_from_iter(loff_t offset, size_t len, struct iov_iter *from, if (rc) { for (i = 0; i < nr_pages; i++) put_page(wdata->pages[i]); + kvfree(wdata->pages); kfree(wdata); add_credits_and_wake_if(server, credits, 0); break; @@ -3130,8 +3132,12 @@ cifs_send_async_read(loff_t offset, size_t len, struct cifsFileInfo *open_file, } rc = cifs_read_allocate_pages(rdata, npages); - if (rc) - goto error; + if (rc) { + kvfree(rdata->pages); + kfree(rdata); + add_credits_and_wake_if(server, credits, 0); + break; + } rdata->cfile = cifsFileInfo_get(open_file); rdata->nr_pages = npages; @@ -3149,7 +3155,6 @@ cifs_send_async_read(loff_t offset, size_t len, struct cifsFileInfo *open_file, if (!rdata->cfile->invalidHandle || !(rc = cifs_reopen_file(rdata->cfile, true))) rc = server->ops->async_readv(rdata); -error: if (rc) { add_credits_and_wake_if(server, rdata->credits, 0); kref_put(&rdata->refcount, -- GitLab