summaryrefslogtreecommitdiffstats
path: root/fs/mpage.c
diff options
context:
space:
mode:
authorJan Kara <jack@suse.cz>2023-01-03 11:44:30 +0100
committerAndrew Morton <akpm@linux-foundation.org>2023-01-18 17:12:56 -0800
commit4b89a37d54a0b5ed6b2e5a9afc44a15a22e563f5 (patch)
tree8bdbc93c57930559198ec064b2900ce46eccb392 /fs/mpage.c
parent6c364edc194e104566f4de72f7a2af5b8fc17110 (diff)
downloadlinux-4b89a37d54a0b5ed6b2e5a9afc44a15a22e563f5.tar.gz
linux-4b89a37d54a0b5ed6b2e5a9afc44a15a22e563f5.tar.bz2
linux-4b89a37d54a0b5ed6b2e5a9afc44a15a22e563f5.zip
fs: don't allocate blocks beyond EOF from __mpage_writepage
When __mpage_writepage() is called for a page beyond EOF, it will go and allocate all blocks underlying the page. This is not only unnecessary but this way blocks can get leaked (e.g. if a page beyond EOF is marked dirty but in the end write fails and i_size is not extended). Link: https://lkml.kernel.org/r/20230103104430.27749-1-jack@suse.cz Signed-off-by: Jan Kara <jack@suse.cz> Reviewed-by: Christoph Hellwig <hch@lst.de> Cc: Matthew Wilcox <willy@infradead.org> Cc: Al Viro <viro@zeniv.linux.org.uk> Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Diffstat (limited to 'fs/mpage.c')
-rw-r--r--fs/mpage.c6
1 files changed, 6 insertions, 0 deletions
diff --git a/fs/mpage.c b/fs/mpage.c
index d36a95473f77..b8e7975159bc 100644
--- a/fs/mpage.c
+++ b/fs/mpage.c
@@ -524,6 +524,12 @@ static int __mpage_writepage(struct page *page, struct writeback_control *wbc,
*/
BUG_ON(!PageUptodate(page));
block_in_file = (sector_t)page->index << (PAGE_SHIFT - blkbits);
+ /*
+ * Whole page beyond EOF? Skip allocating blocks to avoid leaking
+ * space.
+ */
+ if (block_in_file >= (i_size + (1 << blkbits) - 1) >> blkbits)
+ goto page_is_mapped;
last_block = (i_size - 1) >> blkbits;
map_bh.b_page = page;
for (page_block = 0; page_block < blocks_per_page; ) {