linux/fs/ext4
Jiayuan Chen c8fe17a1b3 ext4: fix use-after-free in update_super_work when racing with umount
[ Upstream commit d15e4b0a41 ]

Commit b98535d091 ("ext4: fix bug_on in start_this_handle during umount
filesystem") moved ext4_unregister_sysfs() before flushing s_sb_upd_work
to prevent new error work from being queued via /proc/fs/ext4/xx/mb_groups
reads during unmount. However, this introduced a use-after-free because
update_super_work calls ext4_notify_error_sysfs() -> sysfs_notify() which
accesses the kobject's kernfs_node after it has been freed by kobject_del()
in ext4_unregister_sysfs():

  update_super_work                ext4_put_super
  -----------------                --------------
                                   ext4_unregister_sysfs(sb)
                                     kobject_del(&sbi->s_kobj)
                                       __kobject_del()
                                         sysfs_remove_dir()
                                           kobj->sd = NULL
                                         sysfs_put(sd)
                                           kernfs_put()  // RCU free
  ext4_notify_error_sysfs(sbi)
    sysfs_notify(&sbi->s_kobj)
      kn = kobj->sd              // stale pointer
      kernfs_get(kn)             // UAF on freed kernfs_node
                                   ext4_journal_destroy()
                                     flush_work(&sbi->s_sb_upd_work)

Instead of reordering the teardown sequence, fix this by making
ext4_notify_error_sysfs() detect that sysfs has already been torn down
by checking s_kobj.state_in_sysfs, and skipping the sysfs_notify() call
in that case. A dedicated mutex (s_error_notify_mutex) serializes
ext4_notify_error_sysfs() against kobject_del() in ext4_unregister_sysfs()
to prevent TOCTOU races where the kobject could be deleted between the
state_in_sysfs check and the sysfs_notify() call.

Fixes: b98535d091 ("ext4: fix bug_on in start_this_handle during umount filesystem")
Cc: Jiayuan Chen <jiayuan.chen@linux.dev>
Suggested-by: Jan Kara <jack@suse.cz>
Signed-off-by: Jiayuan Chen <jiayuan.chen@shopee.com>
Reviewed-by: Ritesh Harjani (IBM) <ritesh.list@gmail.com>
Reviewed-by: Jan Kara <jack@suse.cz>
Link: https://patch.msgid.link/20260319120336.157873-1-jiayuan.chen@linux.dev
Signed-off-by: Theodore Ts'o <tytso@mit.edu>
Cc: stable@kernel.org
[ adapted mutex_init placement ]
Signed-off-by: Sasha Levin <sashal@kernel.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
History 2026-04-18 10:33:38 +02:00
..
.kunitconfig ext4: add .kunitconfig fragment to enable ext4-specific tests 2021-02-11 23:16:30 -05:00
acl.c ext4: use ext4_journal_start/stop for fast commit transactions 2023-05-11 23:00:16 +09:00
acl.h ext4: apply umask if ACL support is disabled 2023-11-28 16:56:35 +00:00
balloc.c ext4: reorder capability check last 2025-06-04 14:37:56 +02:00
bitmap.c License cleanup: add SPDX GPL-2.0 license identifier to files with no license 2017-11-02 11:10:55 +01:00
block_validity.c ext4: make block validity check resistent to sb bh corruption 2025-05-02 07:44:38 +02:00
dir.c ext4: fix OOB read when checking dotdot dir 2025-04-10 14:32:06 +02:00
ext4.h ext4: fix use-after-free in update_super_work when racing with umount 2026-04-18 10:33:38 +02:00
ext4_extents.h ext4: fix sparse warnings 2021-08-30 23:36:50 -04:00
ext4_jbd2.c ext4: use ext4_debug() instead of jbd_debug() 2023-01-12 11:59:04 +01:00
ext4_jbd2.h ext4: Support for checksumming from journal triggers 2021-08-30 23:36:50 -04:00
extents.c ext4: drop extent cache when splitting extent fails 2026-04-18 10:33:19 +02:00
extents_status.c ext4: make ext4_es_insert_extent() return void 2024-08-19 05:45:28 +02:00
extents_status.h ext4: make ext4_es_insert_extent() return void 2024-08-19 05:45:28 +02:00
fast_commit.c ext4: publish jinode after initialization 2026-04-18 10:33:38 +02:00
fast_commit.h ext4: add missing validation of fast-commit record lengths 2023-01-12 11:59:05 +01:00
file.c ext4: fix checks for orphan inodes 2025-10-19 16:21:38 +02:00
fsmap.c ext4: correctly handle queries for metadata mappings 2025-10-19 16:21:49 +02:00
fsmap.h ext4: fsmap: fix the block/inode bitmap comment 2021-06-24 09:48:29 -04:00
fsync.c block: use an on-stack bio in blkdev_issue_flush 2021-01-27 09:51:48 -07:00
hash.c ext4: improve error handling from ext4_dirhash() 2023-05-17 11:50:30 +02:00
ialloc.c ext4: make recently_deleted() properly work with lazy itable initialization 2026-04-18 10:33:28 +02:00
indirect.c ext4: fix hole length calculation overflow in non-extent inodes 2025-08-28 16:24:28 +02:00
inline.c ext4: add i_data_sem protection in ext4_destroy_inline_data_nolock() 2026-01-19 13:09:20 +01:00
inode-test.c fs: ext4: Modify inode-test.c to use KUnit parameterized testing feature 2020-12-02 16:07:25 -07:00
inode.c ext4: publish jinode after initialization 2026-04-18 10:33:38 +02:00
ioctl.c ext4: mark group extend fast-commit ineligible 2026-03-04 07:20:08 -05:00
Kconfig ext: EXT4_KUNIT_TESTS should depend on EXT4_FS instead of selecting it 2021-02-11 23:12:59 -05:00
Makefile ext4: Move orphan inode handling into a separate file 2021-08-30 23:36:51 -04:00
mballoc.c ext4: fix the might_sleep() warnings in kvfree() 2026-04-18 10:33:38 +02:00
mballoc.h ext4: fix FS_IOC_GETFSMAP handling 2024-12-14 19:51:12 +01:00
migrate.c ext4: fix i_data_sem unlock order in ext4_ind_migrate() 2024-10-17 15:11:33 +02:00
mmp.c ext4: fix lockdep warning when enabling MMP 2023-05-24 17:36:43 +01:00
move_extent.c ext4: correct the checking of quota files before moving extents 2026-01-19 13:09:26 +01:00
namei.c ext4: fix off-by-one error in do_split 2025-05-02 07:44:02 +02:00
orphan.c ext4: align max orphan file size with e2fsprogs limit 2026-01-19 13:09:49 +01:00
page-io.c ext4: handle redirtying in ext4_bio_write_page() 2024-09-12 11:07:42 +02:00
readpage.c block: Add bio_max_segs 2021-02-26 15:49:51 -07:00
resize.c ext4: fix corruption during on-line resize 2024-04-10 16:18:40 +02:00
super.c ext4: fix use-after-free in update_super_work when racing with umount 2026-04-18 10:33:38 +02:00
symlink.c ext4: report correct st_size for encrypted symlinks 2021-07-25 20:01:06 -07:00
sysfs.c ext4: fix use-after-free in update_super_work when racing with umount 2026-04-18 10:33:38 +02:00
truncate.h ext4: Convert to use mapping->invalidate_lock 2021-07-13 14:29:00 +02:00
verity.c fs: ext4: initialize fsdata in pagecache_write() 2023-01-12 11:59:00 +01:00
xattr.c ext4: fix iloc.bh leak in ext4_xattr_inode_update_ref 2026-02-06 16:41:48 +01:00
xattr.h ext4: fix out-of-bound read in ext4_xattr_inode_dec_ref_all() 2026-01-19 13:10:14 +01:00
xattr_hurd.c acl: handle idmapped mounts 2021-01-24 14:27:17 +01:00
xattr_security.c acl: handle idmapped mounts 2021-01-24 14:27:17 +01:00
xattr_trusted.c acl: handle idmapped mounts 2021-01-24 14:27:17 +01:00
xattr_user.c acl: handle idmapped mounts 2021-01-24 14:27:17 +01:00