Thread (6 messages) flat view 6 messages, 3 authors, 25d ago

[BUG] KASAN: slab-use-after-free Read in slip_receive_buf

From: Jaeyoung Chung <hidden>
Date: 2026-08-25 15:07:03
Also in: lkml
Subsystem: networking drivers, the rest · Maintainers: Andrew Lunn, "David S. Miller", Eric Dumazet, Jakub Kicinski, Paolo Abeni, Linus Torvalds

Hello,

We found a "KASAN: slab-use-after-free Read in slip_receive_buf" on Linux v7.2.
The issue was found by our own race fuzzer. We have not analyzed the root cause,
so we do not have a proposed fix to offer.

To reproduce the race reliably, we applied the delay patch below to the
kernel and ran the C reproducer as root inside an x86_64 QEMU guest. The
crash log we observed, the delay patch and the reproducer are all included
below.

The following kernel config options are required to reproduce the issue:
    CONFIG_SLIP=y
    CONFIG_LEGACY_TIOCSTI=y
    CONFIG_UNIX98_PTYS=y
    CONFIG_TTY=y
    CONFIG_KASAN=y

We hope this report is useful. Please let us know if any further
information would help.

Reported-by: Eulgyu Kim <redacted>
Reported-by: Jaeyoung Chung <redacted>

Kernel delay patch:
==================================================================
diff --git a/drivers/net/slip/slip.c b/drivers/net/slip/slip.c
index faae711cf793..328f54553cb5 100644
--- a/drivers/net/slip/slip.c
+++ b/drivers/net/slip/slip.c
@@ -689,6 +689,9 @@ static void slip_receive_buf(struct tty_struct *tty, const u8 *cp, const u8 *fp,
 			     size_t count)
 {
 	struct slip *sl = tty->disc_data;
+	if (sl && strncmp(current->comm, "syzrepro0", 10) == 0) {
+		mdelay(1500);
+	}
 
 	if (!sl || sl->magic != SLIP_MAGIC || !netif_running(sl->dev))
 		return;
==================================================================

C reproducer:
==================================================================
#define _GNU_SOURCE

#include <errno.h>
#include <fcntl.h>
#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/ioctl.h>
#include <sys/prctl.h>
#include <sys/types.h>
#include <unistd.h>

#ifndef N_SLIP
#define N_SLIP 1
#endif
#ifndef TIOCSETD
#define TIOCSETD 0x5423
#endif
#ifndef TIOCSTI
#define TIOCSTI 0x5412
#endif
#ifndef TIOCVHANGUP
#define TIOCVHANGUP 0x5437
#endif

#define T1_HEAD_START_US 30000

static char g_marker[16] = "syzrepro";
static int g_fd = -1;

static void set_thread_name(int idx)
{
	char nm[16];

	snprintf(nm, sizeof(nm), "%s%d", g_marker, idx);
	nm[15] = '\0';
	if (prctl(PR_SET_NAME, nm, 0, 0, 0) != 0)
		printf("repro: prctl(PR_SET_NAME, %s) failed: %s\n",
		       nm, strerror(errno));
}

static void *thread_use(void *arg)
{
	unsigned char ch = 0x40;
	int r;

	(void)arg;
	set_thread_name(0);

	r = ioctl(g_fd, TIOCSTI, &ch);
	if (r != 0)
		printf("repro: T0 TIOCSTI -> %d (%s)\n", r, strerror(errno));
	return NULL;
}

static void *thread_free(void *arg)
{
	int r;

	(void)arg;
	set_thread_name(1);

	usleep(T1_HEAD_START_US);

	r = ioctl(g_fd, TIOCVHANGUP, 0);
	if (r != 0)
		printf("repro: T1 TIOCVHANGUP -> %d (%s)\n", r, strerror(errno));
	return NULL;
}

int main(void)
{
	int iters = 10;
	int i;

	setvbuf(stdout, NULL, _IONBF, 0);


	for (i = 0; i < iters; i++) {
		int fd, ldisc = N_SLIP;
		pthread_t t0, t1;

		fd = open("/dev/ptmx", O_RDWR | O_NOCTTY);
		if (fd < 0) {
			usleep(200000);
			continue;
		}

		if (ioctl(fd, TIOCSETD, &ldisc) != 0) {
			close(fd);
			usleep(200000);
			continue;
		}

		g_fd = fd;

		if (pthread_create(&t0, NULL, thread_use, NULL) != 0) {
			close(fd);
			continue;
		}
		if (pthread_create(&t1, NULL, thread_free, NULL) != 0) {
			pthread_join(t0, NULL);
			close(fd);
			continue;
		}

		pthread_join(t0, NULL);
		pthread_join(t1, NULL);

		g_fd = -1;
		close(fd);
	}

	return 0;
}
==================================================================

Crash log:
==================================================================
BUG: KASAN: slab-use-after-free in slip_receive_buf+0x89b/0x8b0 drivers/net/slip/slip.c:696
Read of size 4 at addr ffff888107d24a80 by task syzrepro0/400

CPU: 2 UID: 0 PID: 400 Comm: syzrepro0 Not tainted 7.2.0-dirty #3 PREEMPT 
Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.13.0-1ubuntu1.1 04/01/2014
Call Trace:
 <TASK>
 dump_stack_lvl+0x5e/0x80 lib/dump_stack.c:120
 print_address_description+0x77/0x200 mm/kasan/report.c:378
 print_report+0x64/0x70 mm/kasan/report.c:482
 kasan_report+0x118/0x150 mm/kasan/report.c:595
 slip_receive_buf+0x89b/0x8b0 drivers/net/slip/slip.c:696
 tiocsti+0x165/0x1c0 drivers/tty/tty_io.c:2290
 tty_ioctl+0x76c/0xa40 drivers/tty/tty_io.c:2706
 vfs_ioctl fs/ioctl.c:51 [inline]
 __do_sys_ioctl fs/ioctl.c:597 [inline]
 __se_sys_ioctl+0xb6/0x100 fs/ioctl.c:583
 do_syscall_x64 arch/x86/entry/syscall_64.c:63 [inline]
 do_syscall_64+0xf7/0x370 arch/x86/entry/syscall_64.c:94
 entry_SYSCALL_64_after_hwframe+0x76/0x7e
RIP: 0033:0x7b142e575d6b
Code: 00 48 89 44 24 18 31 c0 48 8d 44 24 60 c7 04 24 10 00 00 00 48 89 44 24 08 48 8d 44 24 20 48 89 44 24 10 b8 10 00 00 00 0f 05 <89> c2 3d 00 f0 ff ff 77 1c 48 8b 44 24 18 64 48 2b 04 25 28 00 00
RSP: 002b:00007b142e473e60 EFLAGS: 00000246 ORIG_RAX: 0000000000000010
RAX: ffffffffffffffda RBX: 00007b142e4746c0 RCX: 00007b142e575d6b
RDX: 00007b142e473ec7 RSI: 0000000000005412 RDI: 0000000000000003
RBP: 0000000000000000 R08: 0000000000000000 R09: 0000000000000064
R10: 0000000000000000 R11: 0000000000000246 R12: ffffffffffffff80
R13: 0000000000000000 R14: 00007ffc1370b9a0 R15: 00007b142dc74000
 </TASK>

Allocated by task 399:
 kasan_save_stack mm/kasan/common.c:57 [inline]
 kasan_save_track+0x3e/0x80 mm/kasan/common.c:78
 poison_kmalloc_redzone mm/kasan/common.c:398 [inline]
 __kasan_kmalloc+0x72/0x90 mm/kasan/common.c:415
 kasan_kmalloc include/linux/kasan.h:263 [inline]
 __do_kmalloc_node mm/slub.c:5334 [inline]
 __kvmalloc_node_noprof+0x36a/0x620 mm/slub.c:6905
 alloc_netdev_mqs+0x8c/0x1170 net/core/dev.c:12059
 sl_alloc drivers/net/slip/slip.c:763 [inline]
 slip_open+0x280/0x970 drivers/net/slip/slip.c:824
 tty_ldisc_open+0x83/0xc0 drivers/tty/tty_ldisc.c:432
 tty_set_ldisc+0x2f8/0x4b0 drivers/tty/tty_ldisc.c:563
 tty_ioctl+0x822/0xa40 drivers/tty/tty_io.c:2728
 vfs_ioctl fs/ioctl.c:51 [inline]
 __do_sys_ioctl fs/ioctl.c:597 [inline]
 __se_sys_ioctl+0xb6/0x100 fs/ioctl.c:583
 do_syscall_x64 arch/x86/entry/syscall_64.c:63 [inline]
 do_syscall_64+0xf7/0x370 arch/x86/entry/syscall_64.c:94
 entry_SYSCALL_64_after_hwframe+0x76/0x7e

Freed by task 401:
 kasan_save_stack mm/kasan/common.c:57 [inline]
 kasan_save_track+0x3e/0x80 mm/kasan/common.c:78
 kasan_save_free_info+0x46/0x50 mm/kasan/generic.c:584
 poison_slab_object mm/kasan/common.c:253 [inline]
 __kasan_slab_free+0x3a/0x60 mm/kasan/common.c:285
 kasan_slab_free include/linux/kasan.h:235 [inline]
 slab_free_hook mm/slub.c:2677 [inline]
 slab_free mm/slub.c:6377 [inline]
 kfree+0x16c/0x3e0 mm/slub.c:6692
 device_release+0xbc/0x1b0 drivers/base/core.c:-1
 kobject_cleanup lib/kobject.c:689 [inline]
 kobject_release lib/kobject.c:720 [inline]
 kref_put include/linux/kref.h:65 [inline]
 kobject_put+0x142/0x1c0 lib/kobject.c:737
 netdev_run_todo+0x392/0x10b0 net/core/dev.c:11760
 rtnl_net_unlock include/linux/rtnetlink.h:135 [inline]
 rtnl_net_dev_unlock net/core/dev.c:2180 [inline]
 unregister_netdev+0x10d/0x160 net/core/dev.c:12532
 tty_ldisc_hangup+0x163/0x3d0 drivers/tty/tty_ldisc.c:705
 __tty_hangup+0x50c/0x770 drivers/tty/tty_io.c:621
 tty_vhangup drivers/tty/tty_io.c:691 [inline]
 tty_ioctl+0x27f/0xa40 drivers/tty/tty_io.c:2732
 vfs_ioctl fs/ioctl.c:51 [inline]
 __do_sys_ioctl fs/ioctl.c:597 [inline]
 __se_sys_ioctl+0xb6/0x100 fs/ioctl.c:583
 do_syscall_x64 arch/x86/entry/syscall_64.c:63 [inline]
 do_syscall_64+0xf7/0x370 arch/x86/entry/syscall_64.c:94
 entry_SYSCALL_64_after_hwframe+0x76/0x7e

The buggy address belongs to the object at ffff888107d24000
 which belongs to the cache kmalloc-cg-4k of size 4096
The buggy address is located 2688 bytes inside of
 freed 4096-byte region [ffff888107d24000, ffff888107d25000)

The buggy address belongs to the physical page:
page: refcount:0 mapcount:0 mapping:0000000000000000 index:0x0 pfn:0x107d20
head: order:3 mapcount:0 entire_mapcount:0 nr_pages_mapped:0 pincount:0
memcg:ffff888107d21011
flags: 0x200000000000040(head|node=0|zone=2)
page_type: f5(slab)
raw: 0200000000000040 ffff88810004a280 dead000000000100 dead000000000122
raw: 0000000000000000 0000200000040004 00000000f5000000 ffff888107d21011
head: 0200000000000040 ffff88810004a280 dead000000000100 dead000000000122
head: 0000000000000000 0000200000040004 00000000f5000000 ffff888107d21011
head: 0200000000000003 fffffffffffffe01 00000000ffffffff 00000000ffffffff
head: ffffffffffffffff 0000000000000000 00000000ffffffff 0000000000000008
page dumped because: kasan: bad access detected

Memory state around the buggy address:
 ffff888107d24980: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb
 ffff888107d24a00: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb
ffff888107d24a80: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb
                   ^
 ffff888107d24b00: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb
 ffff888107d24b80: fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb fb
==================================================================

Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help