summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJay Vadayath <jay@artiphishell.com>2026-07-17 11:40:19 -0700
committerJan Kara <jack@suse.cz>2026-07-27 13:35:12 +0200
commitb8228f59dc58aea06dc024efd8f64c2d048c4578 (patch)
treee2922ddd3a78beef256677bc23ca56cc6f37b8df
parentd23eb7380d1594cda31a5dc8487dd2a5c8def8c7 (diff)
downloadlinux-next-b8228f59dc58aea06dc024efd8f64c2d048c4578.tar.gz
linux-next-b8228f59dc58aea06dc024efd8f64c2d048c4578.zip
udf: bound lengthAllocDescs from unallocated space entry
udf_read_inode() copies the on-disk lengthAllocDescs field of a USE (unallocSpaceEntry) inode into iinfo->i_lenAlloc without checking that it fits in the i_data buffer that is subsequently allocated for the inode. udf_count_free_table(), called from udf_statfs(), then walks the allocation descriptor array up to i_lenAlloc bytes, so a crafted UDF image with lengthAllocDescs larger than (blocksize - sizeof(struct unallocSpaceEntry)) causes udf_get_fileshortad() to read past the end of the kmalloc'd i_data buffer. KASAN report from mounting a crafted UDF image and calling statfs() from an unprivileged process: BUG: KASAN: slab-out-of-bounds in udf_get_fileshortad+0x126/0x130 Read of size 4 at addr ffff8880042137d8 by task poc/65 Call Trace: dump_stack_lvl+0x53/0x70 print_report+0xce/0x610 kasan_report+0xce/0x100 udf_get_fileshortad+0x126/0x130 udf_current_aext+0x3c4/0xa10 udf_next_aext+0x241/0x440 udf_statfs+0xb7d/0x11c0 statfs_by_dentry+0x117/0x1e0 user_statfs+0xac/0x130 __do_sys_statfs+0x80/0xe0 do_syscall_64+0x102/0x5a0 entry_SYSCALL_64_after_hwframe+0x77/0x7f Reject USE inodes whose lengthAllocDescs would place descriptors past the end of the i_data buffer, mirroring the checks the rest of the UDF code performs on descriptor lengths. This bug was discovered by Artiphishell's vTriage pipeline, which generated a userspace reproducer that reliably triggers the KASAN report on an unpatched kernel. The fix below was drafted with the Claude coding assistant; a userspace reproducer (and the crafted UDF image) is available on request. Assisted-by: LLM Signed-off-by: Jay Vadayath <jay@artiphishell.com> Link: https://patch.msgid.link/20260717184021.13476-1-jay@artiphishell.com Signed-off-by: Jan Kara <jack@suse.cz>
-rw-r--r--fs/udf/inode.c4
1 files changed, 4 insertions, 0 deletions
diff --git a/fs/udf/inode.c b/fs/udf/inode.c
index c97914aa8d8b..b6d79ecac44a 100644
--- a/fs/udf/inode.c
+++ b/fs/udf/inode.c
@@ -1475,6 +1475,10 @@ reread:
iinfo->i_lenAlloc = le32_to_cpu(
((struct unallocSpaceEntry *)bh->b_data)->
lengthAllocDescs);
+ if (iinfo->i_lenAlloc > bs - sizeof(struct unallocSpaceEntry)) {
+ ret = -EFSCORRUPTED;
+ goto out;
+ }
ret = udf_alloc_i_data(inode, bs -
sizeof(struct unallocSpaceEntry));
if (ret)