linux/security/landlock
Günther Noack 3e271a27c4
landlock: Fix superblock use-after-free in release_inode()
Without this fix, release_inode() (task 1) can race with a umount
operation in hook_sb_delete() (task 2).  The order of operations in
which the race occurs is:

* task 2: hook_sb_delete() arrives at the end of the function, waiting
  for landlock_superblock(sb)->inode_refs to become zero.
* task 1: release_inode(): does atomic_long_dec_and_test(), decrementing
  inode_refs to zero.
* task 2: gets woken up through some other means, sees that inode_refs
  is zero and returns.  The caller is the unmount operation and proceeds
  to release the superblock.
* task 1: Runs wake_up_var(&landlock_superblock(sb)->inode_refs),
  *dereferencing the sb_security on the freed-up superblock*.

Notably, wake_up_var() does not dereference the pointer passed to it,
and only uses it to determine an overapproximated set of tasks to wake
up. So while it's potentially possible for an attacker to provide a
different value for that pointer, this only results in the wrong set of
tasks getting woken up, and in this scenario, no further tasks are
actually waiting.

Nevertheless, KASAN detects it as a slab-use-after-free read on
sb->s_security:

  BUG: KASAN: slab-use-after-free in release_inode+0x196/0x290
  Read of size 8 at addr ffff888103b6c0a8 by task repro/217
   release_inode+0x196/0x290
   landlock_put_object+0x71/0x90
   landlock_free_rules+0x38/0xc0
   landlock_put_ruleset+0x47/0x130
   fop_ruleset_release+0x33/0x40
   __fput+0x305/0x780
  Freed by task 54:
   kfree+0x11c/0x390
   process_scheduled_works+0x766/0xe50
   worker_thread+0x7bc/0xb20

The fix is to determine &landlock_superblock(inode->i_sb)->inode_refs only once
earlier in release_inode(), and later use that precalculated address for the
wake_up_var() call, without having to dereference through the superblock.

Cc: stable@vger.kernel.org
Fixes: cb2c7d1a17 ("landlock: Support filesystem access-control")
Assisted-by: LLM
Signed-off-by: Günther Noack <gnoack@google.com>
Link: https://patch.msgid.link/20261006105847.2541190-1-gnoack@google.com
Signed-off-by: Mickaël Salaün <mic@digikod.net>
2026-10-20 16:47:24 +02:00
..
errata landlock: Require LANDLOCK_ACCESS_FS_MAKE_REG for whiteout creation 2026-08-15 09:14:43 +02:00
.kunitconfig landlock: Test trace path output boundaries 2026-09-08 11:49:39 +02:00
access.h landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
audit.c landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
audit.h landlock: Decouple the per-denial logging decision from CONFIG_AUDIT 2026-08-17 10:17:12 +02:00
cap.c landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
cap.h landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
common.h landlock: Add support for KUnit tests 2024-02-27 11:21:45 +01:00
cred.c landlock: Split denial logging from audit into common framework 2026-08-17 10:17:11 +02:00
cred.h landlock: Wrap per-layer access masks in struct layer_config 2026-10-20 16:47:19 +02:00
domain.c landlock: Enforce namespace use restrictions 2026-10-20 16:47:19 +02:00
domain.h landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
errata.h landlock: Prepare to add second errata 2025-03-21 12:12:21 +01:00
fs.c landlock: Fix superblock use-after-free in release_inode() 2026-10-20 16:47:24 +02:00
fs.h landlock: Add landlock_add_rule_fs and landlock_add_rule_net tracepoints 2026-08-17 10:17:14 +02:00
id.c landlock: Improve kernel-doc "Return:" section consistency 2026-04-07 18:51:04 +02:00
id.h landlock: Split denial logging from audit into common framework 2026-08-17 10:17:11 +02:00
Kconfig landlock: Add create_ruleset and free_ruleset tracepoints 2026-08-17 10:17:13 +02:00
limits.h landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
log.c landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
log.h landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
Makefile landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
net.c landlock: Wrap per-layer access masks in struct layer_config 2026-10-20 16:47:19 +02:00
net.h landlock: Add API support and docs for the quiet flags 2026-06-14 20:17:19 +02:00
ns.c landlock: Enforce namespace use restrictions 2026-10-20 16:47:19 +02:00
ns.h landlock: Enforce namespace use restrictions 2026-10-20 16:47:19 +02:00
object.c treewide: Replace kmalloc with kmalloc_obj for non-scalar types 2026-02-21 01:02:28 -08:00
object.h landlock: Format with clang-format 2022-05-09 12:31:10 +02:00
ruleset.c landlock: Enforce namespace use restrictions 2026-10-20 16:47:19 +02:00
ruleset.h landlock: Enforce namespace use restrictions 2026-10-20 16:47:19 +02:00
setup.c landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
setup.h landlock: Add the errata interface 2025-03-21 12:12:19 +01:00
syscalls.c landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
task.c landlock: Report the effective signal number 2026-09-20 11:08:05 +02:00
task.h landlock: Rename "ptrace" files to "task" 2024-03-08 18:22:16 +01:00
trace.c landlock: Enforce capability restrictions 2026-10-20 16:47:20 +02:00
trace.h landlock: Add landlock_deny_access_fs and landlock_deny_access_net 2026-08-17 10:17:16 +02:00
tsync.c landlock: Add landlock_enforce_domain tracepoint 2026-08-17 10:17:15 +02:00
tsync.h landlock: Add LANDLOCK_RESTRICT_SELF_NO_NEW_PRIVS 2026-08-15 09:14:46 +02:00