Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

ext4: fix lockdep warning when enabling MMP

When we enable MMP in ext4_multi_mount_protect() during mount or
remount, we end up calling sb_start_write() from write_mmp_block(). This
triggers lockdep warning because freeze protection ranks above s_umount
semaphore we are holding during mount / remount. The problem is harmless
because we are guaranteed the filesystem is not frozen during mount /
remount but still let's fix the warning by not grabbing freeze
protection from ext4_multi_mount_protect().

Cc: stable@kernel.org
Reported-by: syzbot+6b7df7d5506b32467149@syzkaller.appspotmail.com
Link: https://syzkaller.appspot.com/bug?id=ab7e5b6f400b7778d46f01841422e5718fb81843
Signed-off-by: Jan Kara <jack@suse.cz>
Reviewed-by: Christian Brauner <brauner@kernel.org>
Link: https://lore.kernel.org/r/20230411121019.21940-1-jack@suse.cz
Signed-off-by: Theodore Ts'o <tytso@mit.edu>

authored by

Jan Kara and committed by
Theodore Ts'o
949f95ff fa08a7b6

+21 -9
+21 -9
fs/ext4/mmp.c
··· 39 39 * Write the MMP block using REQ_SYNC to try to get the block on-disk 40 40 * faster. 41 41 */ 42 - static int write_mmp_block(struct super_block *sb, struct buffer_head *bh) 42 + static int write_mmp_block_thawed(struct super_block *sb, 43 + struct buffer_head *bh) 43 44 { 44 45 struct mmp_struct *mmp = (struct mmp_struct *)(bh->b_data); 45 46 46 - /* 47 - * We protect against freezing so that we don't create dirty buffers 48 - * on frozen filesystem. 49 - */ 50 - sb_start_write(sb); 51 47 ext4_mmp_csum_set(sb, mmp); 52 48 lock_buffer(bh); 53 49 bh->b_end_io = end_buffer_write_sync; 54 50 get_bh(bh); 55 51 submit_bh(REQ_OP_WRITE | REQ_SYNC | REQ_META | REQ_PRIO, bh); 56 52 wait_on_buffer(bh); 57 - sb_end_write(sb); 58 53 if (unlikely(!buffer_uptodate(bh))) 59 54 return -EIO; 60 - 61 55 return 0; 56 + } 57 + 58 + static int write_mmp_block(struct super_block *sb, struct buffer_head *bh) 59 + { 60 + int err; 61 + 62 + /* 63 + * We protect against freezing so that we don't create dirty buffers 64 + * on frozen filesystem. 65 + */ 66 + sb_start_write(sb); 67 + err = write_mmp_block_thawed(sb, bh); 68 + sb_end_write(sb); 69 + return err; 62 70 } 63 71 64 72 /* ··· 352 344 seq = mmp_new_seq(); 353 345 mmp->mmp_seq = cpu_to_le32(seq); 354 346 355 - retval = write_mmp_block(sb, bh); 347 + /* 348 + * On mount / remount we are protected against fs freezing (by s_umount 349 + * semaphore) and grabbing freeze protection upsets lockdep 350 + */ 351 + retval = write_mmp_block_thawed(sb, bh); 356 352 if (retval) 357 353 goto failed; 358 354