summaryrefslogtreecommitdiffstats
path: root/fs/ntfs/aops.c
diff options
context:
space:
mode:
authorAnton Altaparmakov <aia21@cam.ac.uk>2007-11-03 07:38:59 +0000
committerLinus Torvalds <torvalds@woody.linux-foundation.org>2007-11-03 12:27:21 -0700
commitebab89909e0dc716282d5e7f6e73a3155fe66d4a (patch)
tree8cee9ff6f9e0a08c6f08853e38e563514e92a99e /fs/ntfs/aops.c
parent74521c28e550c4ec265cda14114bd9b908e9de34 (diff)
downloadlinux-stable-ebab89909e0dc716282d5e7f6e73a3155fe66d4a.tar.gz
linux-stable-ebab89909e0dc716282d5e7f6e73a3155fe66d4a.tar.bz2
linux-stable-ebab89909e0dc716282d5e7f6e73a3155fe66d4a.zip
NTFS: Fix read regression.
The regression was caused by: commit[a32ea1e1f925399e0d81ca3f7394a44a6dafa12c] Fix read/truncate race This causes ntfs_readpage() to be called for a zero i_size inode, which failed when the file was compressed and non-resident. Thanks a lot to Mike Galbraith for reporting the issue and tracking down the commit that caused the regression. Looking into it I found three bugs which the patch fixes. Signed-off-by: Anton Altaparmakov <aia21@cantab.net> Tested-by: Mike Galbraith <efault@gmx.de> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'fs/ntfs/aops.c')
-rw-r--r--fs/ntfs/aops.c10
1 files changed, 9 insertions, 1 deletions
diff --git a/fs/ntfs/aops.c b/fs/ntfs/aops.c
index cfdc7900d271..ad87cb01299b 100644
--- a/fs/ntfs/aops.c
+++ b/fs/ntfs/aops.c
@@ -405,6 +405,15 @@ static int ntfs_readpage(struct file *file, struct page *page)
retry_readpage:
BUG_ON(!PageLocked(page));
+ vi = page->mapping->host;
+ i_size = i_size_read(vi);
+ /* Is the page fully outside i_size? (truncate in progress) */
+ if (unlikely(page->index >= (i_size + PAGE_CACHE_SIZE - 1) >>
+ PAGE_CACHE_SHIFT)) {
+ zero_user_page(page, 0, PAGE_CACHE_SIZE, KM_USER0);
+ ntfs_debug("Read outside i_size - truncated?");
+ goto done;
+ }
/*
* This can potentially happen because we clear PageUptodate() during
* ntfs_writepage() of MstProtected() attributes.
@@ -413,7 +422,6 @@ retry_readpage:
unlock_page(page);
return 0;
}
- vi = page->mapping->host;
ni = NTFS_I(vi);
/*
* Only $DATA attributes can be encrypted and only unnamed $DATA