Files
linux-apfs/fs
Aneesh Kumar K.V 393418676a ext4: Fix the race between read_inode_bitmap() and ext4_new_inode()
We need to make sure we update the inode bitmap and clear
EXT4_BG_INODE_UNINIT flag with sb_bgl_lock held, since
ext4_read_inode_bitmap() looks at EXT4_BG_INODE_UNINIT to decide
whether to initialize the inode bitmap each time it is called.
(introduced by commit c806e68f.)

ext4_read_inode_bitmap does:

spin_lock(sb_bgl_lock(EXT4_SB(sb), block_group));
if (desc->bg_flags & cpu_to_le16(EXT4_BG_INODE_UNINIT)) {
	ext4_init_inode_bitmap(sb, bh, block_group, desc);

and ext4_new_inode does
if (!ext4_set_bit_atomic(sb_bgl_lock(sbi, group),
                   ino, inode_bitmap_bh->b_data))
		   ......
		   ...
spin_lock(sb_bgl_lock(sbi, group));

gdp->bg_flags &= cpu_to_le16(~EXT4_BG_INODE_UNINIT);
i.e., on allocation we update the bitmap then we take the sb_bgl_lock
and clear the EXT4_BG_INODE_UNINIT flag. What can happen is a
parallel ext4_read_inode_bitmap can zero out the bitmap in between
the above ext4_set_bit_atomic and spin_lock(sb_bg_lock..)

The race results in below user visible errors
EXT4-fs error (device sdb1): ext4_free_inode: bit already cleared for inode 168449
EXT4-fs warning (device sdb1): ext4_unlink: Deleting nonexistent file ...
EXT4-fs warning (device sdb1): ext4_rmdir: empty directory has too many links ...
# ls -al /mnt/tmp/f/p369/d3/d6/d39/db2/dee/d10f/d3f/l71
ls: /mnt/tmp/f/p369/d3/d6/d39/db2/dee/d10f/d3f/l71: Stale NFS file handle

Signed-off-by: Aneesh Kumar K.V <aneesh.kumar@linux.vnet.ibm.com>
Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
Cc: stable@kernel.org
2009-01-05 21:38:14 -05:00
..
2008-12-25 11:40:09 +11:00
2008-11-14 11:29:12 +11:00
2008-11-20 08:11:52 +11:00
2008-08-20 15:40:32 -07:00
2008-10-13 09:47:43 +11:00
2008-11-25 16:51:45 -08:00
2008-12-31 18:07:43 -05:00
2008-11-14 10:39:25 +11:00
2008-12-31 18:07:44 -05:00
2008-12-30 16:51:43 -05:00
2008-12-30 16:51:43 -05:00
2008-10-17 02:38:36 +11:00
2008-12-01 19:55:25 -08:00
2008-11-18 15:08:56 +01:00
2008-12-04 17:16:36 +11:00
2008-12-29 16:47:18 +11:00
2008-12-29 08:29:50 +01:00
2008-12-31 18:07:43 -05:00
2009-01-03 11:45:54 -08:00
2008-12-29 08:29:53 +01:00
2008-10-23 05:12:59 -04:00
2008-12-31 18:07:38 -05:00
2008-12-25 11:40:09 +11:00
2008-12-31 18:07:43 -05:00
2008-12-31 18:07:41 -05:00
2009-01-04 15:14:41 -05:00
2008-10-30 11:38:45 -07:00