summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLi Chen <me@linux.beauty>2026-03-06 11:56:40 +0300
committerTheodore Ts'o <tytso@mit.edu>2026-04-09 17:51:05 +0300
commit660d23669982202c99798658e2a15ccdd001f82b (patch)
tree30ecab95d36bcd0d1460b7f29fa28bb67d458a55
parent5267f6ef49cb5fba426f2d286817b1355fde31da (diff)
downloadlinux-660d23669982202c99798658e2a15ccdd001f82b.tar.xz
ext4: use jbd2 jinode dirty range accessor
ext4 journal commit callbacks access jbd2_inode dirty range fields without holding journal->j_list_lock. Use jbd2_jinode_get_dirty_range() to get the range in bytes, and read i_transaction with READ_ONCE() in the redirty check. Suggested-by: Jan Kara <jack@suse.cz> Reviewed-by: Jan Kara <jack@suse.cz> Signed-off-by: Li Chen <me@linux.beauty> Link: https://patch.msgid.link/20260306085643.465275-3-me@linux.beauty Signed-off-by: Theodore Ts'o <tytso@mit.edu>
-rw-r--r--fs/ext4/inode.c10
-rw-r--r--fs/ext4/super.c16
2 files changed, 19 insertions, 7 deletions
diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c
index 025ea8f0c41b..13cd564f89e1 100644
--- a/fs/ext4/inode.c
+++ b/fs/ext4/inode.c
@@ -3055,17 +3055,23 @@ static int ext4_writepages(struct address_space *mapping,
int ext4_normal_submit_inode_data_buffers(struct jbd2_inode *jinode)
{
+ loff_t range_start, range_end;
struct writeback_control wbc = {
.sync_mode = WB_SYNC_ALL,
.nr_to_write = LONG_MAX,
- .range_start = jinode->i_dirty_start,
- .range_end = jinode->i_dirty_end,
};
struct mpage_da_data mpd = {
.inode = jinode->i_vfs_inode,
.wbc = &wbc,
.can_map = 0,
};
+
+ if (!jbd2_jinode_get_dirty_range(jinode, &range_start, &range_end))
+ return 0;
+
+ wbc.range_start = range_start;
+ wbc.range_end = range_end;
+
return ext4_do_writepages(&mpd);
}
diff --git a/fs/ext4/super.c b/fs/ext4/super.c
index a34efb44e73d..638d859f4fca 100644
--- a/fs/ext4/super.c
+++ b/fs/ext4/super.c
@@ -521,6 +521,7 @@ static bool ext4_journalled_writepage_needs_redirty(struct jbd2_inode *jinode,
{
struct buffer_head *bh, *head;
struct journal_head *jh;
+ transaction_t *trans = READ_ONCE(jinode->i_transaction);
bh = head = folio_buffers(folio);
do {
@@ -539,7 +540,7 @@ static bool ext4_journalled_writepage_needs_redirty(struct jbd2_inode *jinode,
*/
jh = bh2jh(bh);
if (buffer_dirty(bh) ||
- (jh && (jh->b_transaction != jinode->i_transaction ||
+ (jh && (jh->b_transaction != trans ||
jh->b_next_transaction)))
return true;
} while ((bh = bh->b_this_page) != head);
@@ -550,15 +551,20 @@ static bool ext4_journalled_writepage_needs_redirty(struct jbd2_inode *jinode,
static int ext4_journalled_submit_inode_data_buffers(struct jbd2_inode *jinode)
{
struct address_space *mapping = jinode->i_vfs_inode->i_mapping;
+ loff_t range_start, range_end;
struct writeback_control wbc = {
- .sync_mode = WB_SYNC_ALL,
+ .sync_mode = WB_SYNC_ALL,
.nr_to_write = LONG_MAX,
- .range_start = jinode->i_dirty_start,
- .range_end = jinode->i_dirty_end,
- };
+ };
struct folio *folio = NULL;
int error;
+ if (!jbd2_jinode_get_dirty_range(jinode, &range_start, &range_end))
+ return 0;
+
+ wbc.range_start = range_start;
+ wbc.range_end = range_end;
+
/*
* writeback_iter() already checks for dirty pages and calls
* folio_clear_dirty_for_io(), which we want to write protect the