summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLukas Czerner <lczerner@redhat.com>2013-07-01 08:12:39 -0400
committerTheodore Ts'o <tytso@mit.edu>2013-07-01 08:12:39 -0400
commite1be3a928ee0b0b2a893695e6dd5c5dbe293af16 (patch)
treea03fcedb0198f00c02ace3814a3fe27772cf2dcf
parent42c832debbbf819f6c4ad8601baa559c44105ba4 (diff)
ext4: only zero partial blocks in ext4_zero_partial_blocks()
Currently if we pass range into ext4_zero_partial_blocks() which covers entire block we would attempt to zero it even though we should only zero unaligned part of the block. Fix this by checking whether the range covers the whole block skip zeroing if so. Signed-off-by: Lukas Czerner <lczerner@redhat.com> Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
-rw-r--r--fs/ext4/inode.c17
1 files changed, 10 insertions, 7 deletions
diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c
index 09942341dfae..502a9e1f5aa3 100644
--- a/fs/ext4/inode.c
+++ b/fs/ext4/inode.c
@@ -3424,33 +3424,36 @@ int ext4_zero_partial_blocks(handle_t *handle, struct inode *inode,
{
struct super_block *sb = inode->i_sb;
struct address_space *mapping = inode->i_mapping;
- unsigned partial = lstart & (sb->s_blocksize - 1);
+ unsigned partial_start, partial_end;
ext4_fsblk_t start, end;
loff_t byte_end = (lstart + length - 1);
int err = 0;
+ partial_start = lstart & (sb->s_blocksize - 1);
+ partial_end = byte_end & (sb->s_blocksize - 1);
+
start = lstart >> sb->s_blocksize_bits;
end = byte_end >> sb->s_blocksize_bits;
/* Handle partial zero within the single block */
- if (start == end) {
+ if (start == end &&
+ (partial_start || (partial_end != sb->s_blocksize - 1))) {
err = ext4_block_zero_page_range(handle, mapping,
lstart, length);
return err;
}
/* Handle partial zero out on the start of the range */
- if (partial) {
+ if (partial_start) {
err = ext4_block_zero_page_range(handle, mapping,
lstart, sb->s_blocksize);
if (err)
return err;
}
/* Handle partial zero out on the end of the range */
- partial = byte_end & (sb->s_blocksize - 1);
- if (partial != sb->s_blocksize - 1)
+ if (partial_end != sb->s_blocksize - 1)
err = ext4_block_zero_page_range(handle, mapping,
- byte_end - partial,
- partial + 1);
+ byte_end - partial_end,
+ partial_end + 1);
return err;
}