]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
ext4: reserved credits for one extent during the folio writeback
authorZhang Yi <yi.zhang@huawei.com>
Mon, 7 Jul 2025 14:08:11 +0000 (22:08 +0800)
committerTheodore Ts'o <tytso@mit.edu>
Mon, 14 Jul 2025 03:41:52 +0000 (23:41 -0400)
After ext4 supports large folios, reserving journal credits for one
maximum-ordered folio based on the worst case cenario during the
writeback process can easily exceed the maximum transaction credits.
Additionally, reserving journal credits for one page is also no
longer appropriate.

Currently, the folio writeback process can either extend the journal
credits or initiate a new transaction if the currently reserved journal
credits are insufficient. Therefore, it can be modified to reserve
credits for only one extent at the outset. In most cases involving
continuous mapping, these credits are generally adequate, and we may
only need to perform some basic credit expansion. However, in extreme
cases where the block size and folio size differ significantly, or when
the folios are sufficiently discontinuous, it may be necessary to
restart a new transaction and resubmit the folios.

Suggested-by: Jan Kara <jack@suse.cz>
Signed-off-by: Zhang Yi <yi.zhang@huawei.com>
Reviewed-by: Jan Kara <jack@suse.cz>
Link: https://patch.msgid.link/20250707140814.542883-9-yi.zhang@huaweicloud.com
Signed-off-by: Theodore Ts'o <tytso@mit.edu>
fs/ext4/inode.c

index 1d158e1de3a15d8f3323d719bd7a52aedee7ab4f..5230af8798143984ff03786a01a3bdbab1c378b9 100644 (file)
@@ -2545,21 +2545,6 @@ update_disksize:
        return err;
 }
 
-/*
- * Calculate the total number of credits to reserve for one writepages
- * iteration. This is called from ext4_writepages(). We map an extent of
- * up to MAX_WRITEPAGES_EXTENT_LEN blocks and then we go on and finish mapping
- * the last partial page. So in total we can map MAX_WRITEPAGES_EXTENT_LEN +
- * bpp - 1 blocks in bpp different extents.
- */
-static int ext4_da_writepages_trans_blocks(struct inode *inode)
-{
-       int bpp = ext4_journal_blocks_per_folio(inode);
-
-       return ext4_meta_trans_blocks(inode,
-                               MAX_WRITEPAGES_EXTENT_LEN + bpp - 1, bpp);
-}
-
 static int ext4_journal_folio_buffers(handle_t *handle, struct folio *folio,
                                     size_t len)
 {
@@ -2916,8 +2901,14 @@ retry:
                 * not supported by delalloc.
                 */
                BUG_ON(ext4_should_journal_data(inode));
-               needed_blocks = ext4_da_writepages_trans_blocks(inode);
-
+               /*
+                * Calculate the number of credits needed to reserve for one
+                * extent of up to MAX_WRITEPAGES_EXTENT_LEN blocks. It will
+                * attempt to extend the transaction or start a new iteration
+                * if the reserved credits are insufficient.
+                */
+               needed_blocks = ext4_chunk_trans_blocks(inode,
+                                               MAX_WRITEPAGES_EXTENT_LEN);
                /* start a new transaction */
                handle = ext4_journal_start_with_reserve(inode,
                                EXT4_HT_WRITE_PAGE, needed_blocks, rsv_blocks);