Hi all, On Sun, Dec 13, 2020 at 06:53:10AM -0800, syzbot wrote: > BUG: memory leak > unreferenced object 0xffff88810f897940 (size 64): > comm "syz-executor991", pid 8502, jiffies 4294942194 (age 14.080s) > hex dump (first 32 bytes): > 7f 00 00 00 80 00 00 00 00 00 00 00 00 00 00 00 ................ > 00 a0 37 0c 81 88 ff ff 00 00 00 00 00 00 00 00 ..7............. > backtrace: > [<00000000639d0dd1>] xskq_create+0x23/0xd0 include/linux/slab.h:552 > [<00000000b680b035>] xsk_init_queue net/xdp/xsk.c:508 [inline] > [<00000000b680b035>] xsk_setsockopt+0x1c4/0x590 net/xdp/xsk.c:875 > [<000000002b302260>] __sys_setsockopt+0x1b0/0x360 net/socket.c:2132 > [<00000000ae03723e>] __do_sys_setsockopt net/socket.c:2143 [inline] > [<00000000ae03723e>] __se_sys_setsockopt net/socket.c:2140 [inline] > [<00000000ae03723e>] __x64_sys_setsockopt+0x22/0x30 net/socket.c:2140 > [<0000000005c2b4a0>] do_syscall_64+0x2d/0x70 arch/x86/entry/common.c:46 > [<0000000003db140f>] entry_SYSCALL_64_after_hwframe+0x44/0xa9 I have tested the following diff locally against syzbot's reproducer, and sent a patch to it [1] for testing. I will send a real patch here tomorrow if syzbot is happy about it. Please see explanation below. --- a/net/xdp/xsk_buff_pool.c +++ b/net/xdp/xsk_buff_pool.c @@ -37,6 +37,9 @@ void xp_destroy(struct xsk_buff_pool *pool) if (!pool) return; + xskq_destroy(pool->fq); + xskq_destroy(pool->cq); + kvfree(pool->heads); kvfree(pool); } @@ -234,16 +237,6 @@ static void xp_release_deferred(struct work_struct *work) xp_clear_dev(pool); rtnl_unlock(); - if (pool->fq) { - xskq_destroy(pool->fq); - pool->fq = NULL; - } - - if (pool->cq) { - xskq_destroy(pool->cq); - pool->cq = NULL; - } - xdp_put_umem(pool->umem, false); xp_destroy(pool); } When xsk_bind() allocates `xs->pool` but something else goes wrong: xs->pool = xp_create_and_assign_umem(xs, xs->umem); [...] if (err) { xp_destroy(xs->pool); xp_destroy() doesn't free `pool->{f,c}q`, causing a memory leak. Move `xskq_destroy(pool->{f,c}q)` from xp_release_deferred() to xp_destroy(). Also, since xskq_destroy() already does null check, I think it's unnecessary to do it again here? Thanks, Peilin Ye [1] https://syzkaller.appspot.com/bug?id=fea808dfe3c6dfdd6ba9778becbffe0b14e91294