summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorZhang Yi <yi.zhang@huawei.com>2026-08-25 21:17:53 -0400
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2026-09-02 14:32:35 +0200
commit3cc1c2d5fbd072901ed1601a82da9acf4a2507c6 (patch)
treee53a5864c92454c8ea769ca5aff5fa16d4e8dc4b
parent7e9ff031a5bc7c7ef76425b23edaf96064bd1642 (diff)
downloadlinux-stable-3cc1c2d5fbd072901ed1601a82da9acf4a2507c6.tar.gz
linux-stable-3cc1c2d5fbd072901ed1601a82da9acf4a2507c6.zip
ext4: move partial block zeroing earlier in ext4_zero_range()
[ Upstream commit b16e9d27a643a3cf8907c994d25ed52717f36418 ] In ext4_zero_range(), move the ext4_zero_partial_blocks() call, which handles unaligned edges, into the same branch where the unaligned range is preallocated, immediately after ext4_alloc_file_blocks(). This is safe because there is no dependency between partial block handling and the subsequent full block handling. This change will be used by later patches that handle unaligned FALLOC_FL_WRITE_ZEROES operations, which will need to check the partial zeroed result. Signed-off-by: Zhang Yi <yi.zhang@huawei.com> Reviewed-by: Jan Kara <jack@suse.cz> Link: https://patch.msgid.link/20260714080044.4038124-5-yi.zhang@huaweicloud.com Signed-off-by: Theodore Ts'o <tytso@mit.edu> Stable-dep-of: d19d239ada9b ("ext4: write back partial-zeroed edges in WRITE_ZEROES") Signed-off-by: Sasha Levin <sashal@kernel.org> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
-rw-r--r--fs/ext4/extents.c12
1 files changed, 7 insertions, 5 deletions
diff --git a/fs/ext4/extents.c b/fs/ext4/extents.c
index 951d9b394ccd..6ca4f94c4b2b 100644
--- a/fs/ext4/extents.c
+++ b/fs/ext4/extents.c
@@ -4796,10 +4796,16 @@ static long ext4_zero_range(struct file *file, loff_t offset,
}
flags = EXT4_GET_BLOCKS_CREATE_UNWRIT_EXT;
- /* Preallocate the range including the unaligned edges */
+ /*
+ * Preallocate the range including the unaligned edges, and zero
+ * out partial blocks if they already contain data.
+ */
if (!IS_ALIGNED(offset | end, blocksize)) {
ret = ext4_alloc_file_blocks(file, offset, len, new_size,
flags);
+ if (!ret)
+ ret = ext4_zero_partial_blocks(inode, offset, len,
+ &partial_zeroed);
if (ret)
return ret;
}
@@ -4832,10 +4838,6 @@ static long ext4_zero_range(struct file *file, loff_t offset,
if (IS_ALIGNED(offset | end, blocksize))
return ret;
- /* Zero out partial block at the edges of the range */
- ret = ext4_zero_partial_blocks(inode, offset, len, &partial_zeroed);
- if (ret)
- return ret;
if (((file->f_flags & O_SYNC) || IS_SYNC(inode)) && partial_zeroed) {
ret = filemap_write_and_wait_range(inode->i_mapping, offset,
end - 1);