[PATCH 29/32] ext4: Track metadata bhs in fs-private inode part

Jan Kara <[email protected]> Tue, 3 Mar 2026 11:34:18 +0100
Newsgroups gmane.linux.kernel.aio.general,gmane.linux.file-systems,gmane.comp.file-systems.ext4,gmane.linux.kernel.mm
Message-ID <[email protected]>
Track metadata bhs for an inode in fs-private part of the inode. We need
the tracking only for nojournal mode so this is somewhat wasteful. We
can relatively easily make the mapping_metadata_bhs struct dynamically
allocated similarly to how we treat jbd2_inode but let's leave that for
ext4 specific series once the dust settles a bit.

Signed-off-by: Jan Kara <[email protected]>
---
 fs/ext4/ext4.h    | 4 +++-
 fs/ext4/file.c    | 1 +
 fs/ext4/inode.c   | 2 +-
 fs/ext4/namei.c   | 2 ++
 fs/ext4/super.c   | 6 ++++++
 fs/ext4/symlink.c | 3 +++
 6 files changed, 16 insertions(+), 2 deletions(-)

diff --git a/fs/ext4/ext4.h b/fs/ext4/ext4.h
index 293f698b7042..a829e5da67af 100644
--- a/fs/ext4/ext4.h
+++ b/fs/ext4/ext4.h
@@ -1121,6 +1121,7 @@ struct ext4_inode_info {
 	struct rw_semaphore i_data_sem;
 	struct inode vfs_inode;
 	struct jbd2_inode *jinode;
+	struct mapping_metadata_bhs i_metadata_bhs;
 
 	/*
 	 * File creation time. Its function is same as that of
@@ -3203,8 +3204,9 @@ extern void ext4_mark_group_bitmap_corrupted(struct super_block *sb,
 					     unsigned int flags);
 extern unsigned int ext4_num_base_meta_blocks(struct super_block *sb,
 					      ext4_group_t block_group);
-extern void print_daily_error_info(struct timer_list *t);
+struct mapping_metadata_bhs *ext4_get_metadata_bhs(struct inode *inode);
 
+extern void print_daily_error_info(struct timer_list *t);
 extern __printf(7, 8)
 void __ext4_error(struct super_block *, const char *, unsigned int, bool,
 		  int, __u64, const char *, ...);
diff --git a/fs/ext4/file.c b/fs/ext4/file.c
index f1dc5ce791a7..3d433f50524b 100644
--- a/fs/ext4/file.c
+++ b/fs/ext4/file.c
@@ -987,5 +987,6 @@ const struct inode_operations ext4_file_inode_operations = {
 	.fiemap		= ext4_fiemap,
 	.fileattr_get	= ext4_fileattr_get,
 	.fileattr_set	= ext4_fileattr_set,
+	.get_metadata_bhs = ext4_get_metadata_bhs,
 };
 
diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c
index 011cb2eb16a2..eead6c5c2366 100644
--- a/fs/ext4/inode.c
+++ b/fs/ext4/inode.c
@@ -3436,7 +3436,7 @@ static bool ext4_inode_datasync_dirty(struct inode *inode)
 	}
 
 	/* Any metadata buffers to write? */
-	if (mmb_has_buffers(&inode->i_mapping->i_metadata_bhs))
+	if (mmb_has_buffers(&EXT4_I(inode)->i_metadata_bhs))
 		return true;
 	return inode_state_read_once(inode) & I_DIRTY_DATASYNC;
 }
diff --git a/fs/ext4/namei.c b/fs/ext4/namei.c
index c4b5e252af0e..4d2cae140b71 100644
--- a/fs/ext4/namei.c
+++ b/fs/ext4/namei.c
@@ -4228,6 +4228,7 @@ const struct inode_operations ext4_dir_inode_operations = {
 	.fiemap         = ext4_fiemap,
 	.fileattr_get	= ext4_fileattr_get,
 	.fileattr_set	= ext4_fileattr_set,
+	.get_metadata_bhs = ext4_get_metadata_bhs,
 };
 
 const struct inode_operations ext4_special_inode_operations = {
@@ -4236,4 +4237,5 @@ const struct inode_operations ext4_special_inode_operations = {
 	.listxattr	= ext4_listxattr,
 	.get_inode_acl	= ext4_get_acl,
 	.set_acl	= ext4_set_acl,
+	.get_metadata_bhs = ext4_get_metadata_bhs,
 };
diff --git a/fs/ext4/super.c b/fs/ext4/super.c
index ea827b0ecc8d..4b9eb86b03e2 100644
--- a/fs/ext4/super.c
+++ b/fs/ext4/super.c
@@ -1428,6 +1428,7 @@ static struct inode *ext4_alloc_inode(struct super_block *sb)
 	INIT_WORK(&ei->i_rsv_conversion_work, ext4_end_io_rsv_work);
 	ext4_fc_init_inode(&ei->vfs_inode);
 	spin_lock_init(&ei->i_fc_lock);
+	mmb_init(&ei->i_metadata_bhs);
 	return &ei->vfs_inode;
 }
 
@@ -1521,6 +1522,11 @@ static void destroy_inodecache(void)
 	kmem_cache_destroy(ext4_inode_cachep);
 }
 
+struct mapping_metadata_bhs *ext4_get_metadata_bhs(struct inode *inode)
+{
+	return &EXT4_I(inode)->i_metadata_bhs;
+}
+
 void ext4_clear_inode(struct inode *inode)
 {
 	ext4_fc_del(inode);
diff --git a/fs/ext4/symlink.c b/fs/ext4/symlink.c
index 645240cc0229..53ec8daf4cae 100644
--- a/fs/ext4/symlink.c
+++ b/fs/ext4/symlink.c
@@ -119,6 +119,7 @@ const struct inode_operations ext4_encrypted_symlink_inode_operations = {
 	.setattr	= ext4_setattr,
 	.getattr	= ext4_encrypted_symlink_getattr,
 	.listxattr	= ext4_listxattr,
+	.get_metadata_bhs = ext4_get_metadata_bhs,
 };
 
 const struct inode_operations ext4_symlink_inode_operations = {
@@ -126,6 +127,7 @@ const struct inode_operations ext4_symlink_inode_operations = {
 	.setattr	= ext4_setattr,
 	.getattr	= ext4_getattr,
 	.listxattr	= ext4_listxattr,
+	.get_metadata_bhs = ext4_get_metadata_bhs,
 };
 
 const struct inode_operations ext4_fast_symlink_inode_operations = {
@@ -133,4 +135,5 @@ const struct inode_operations ext4_fast_symlink_inode_operations = {
 	.setattr	= ext4_setattr,
 	.getattr	= ext4_getattr,
 	.listxattr	= ext4_listxattr,
+	.get_metadata_bhs = ext4_get_metadata_bhs,
 };
-- 
2.51.0


--
To unsubscribe, send a message with 'unsubscribe linux-aio' in
the body to [email protected].  For more info on Linux AIO,
see: http://www.kvack.org/aio/
Don't email: <a href=mailto:"[email protected]">[email protected]</a>