summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAl Viro <viro@zeniv.linux.org.uk>2016-09-05 22:20:03 -0400
committerAl Viro <viro@zeniv.linux.org.uk>2016-12-10 14:24:45 -0500
commitb9de313cf05fe08fa59efaf19756ec5283af672a (patch)
treec57749e0221aff9d8fb07786d7821f2ce80fcdfa
parentc0cf3ef5e0f47e385920450b245d22bead93e7ad (diff)
fix ceph_write_end()
don't zero on short copies; if the page was uptodate it's just plain wrong, and if it wasn't we'll be better off just returning 0 and buggering off. Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
-rw-r--r--fs/ceph/addr.c14
1 files changed, 8 insertions, 6 deletions
diff --git a/fs/ceph/addr.c b/fs/ceph/addr.c
index ef3ebd780aff..834be0943a26 100644
--- a/fs/ceph/addr.c
+++ b/fs/ceph/addr.c
@@ -1276,25 +1276,27 @@ static int ceph_write_end(struct file *file, struct address_space *mapping,
struct page *page, void *fsdata)
{
struct inode *inode = file_inode(file);
- unsigned from = pos & (PAGE_SIZE - 1);
int check_cap = 0;
dout("write_end file %p inode %p page %p %d~%d (%d)\n", file,
inode, page, (int)pos, (int)copied, (int)len);
/* zero the stale part of the page if we did a short copy */
- if (copied < len)
- zero_user_segment(page, from+copied, len);
+ if (!PageUptodate(page)) {
+ if (copied < len) {
+ copied = 0;
+ goto out;
+ }
+ SetPageUptodate(page);
+ }
/* did file size increase? */
if (pos+copied > i_size_read(inode))
check_cap = ceph_inode_set_size(inode, pos+copied);
- if (!PageUptodate(page))
- SetPageUptodate(page);
-
set_page_dirty(page);
+out:
unlock_page(page);
put_page(page);