Commit f26c08b4 authored by Hillf Danton's avatar Hillf Danton Committed by Jens Axboe

io_uring: fix file leak on error path of io ctx creation

Put file as part of error handling when setting up io ctx to fix
memory leaks like the following one.

   BUG: memory leak
   unreferenced object 0xffff888101ea2200 (size 256):
     comm "syz-executor355", pid 8470, jiffies 4294953658 (age 32.400s)
     hex dump (first 32 bytes):
       00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00  ................
       20 59 03 01 81 88 ff ff 80 87 a8 10 81 88 ff ff   Y..............
     backtrace:
       [<000000002e0a7c5f>] kmem_cache_zalloc include/linux/slab.h:654 [inline]
       [<000000002e0a7c5f>] __alloc_file+0x1f/0x130 fs/file_table.c:101
       [<000000001a55b73a>] alloc_empty_file+0x69/0x120 fs/file_table.c:151
       [<00000000fb22349e>] alloc_file+0x33/0x1b0 fs/file_table.c:193
       [<000000006e1465bb>] alloc_file_pseudo+0xb2/0x140 fs/file_table.c:233
       [<000000007118092a>] anon_inode_getfile fs/anon_inodes.c:91 [inline]
       [<000000007118092a>] anon_inode_getfile+0xaa/0x120 fs/anon_inodes.c:74
       [<000000002ae99012>] io_uring_get_fd fs/io_uring.c:9198 [inline]
       [<000000002ae99012>] io_uring_create fs/io_uring.c:9377 [inline]
       [<000000002ae99012>] io_uring_setup+0x1125/0x1630 fs/io_uring.c:9411
       [<000000008280baad>] do_syscall_64+0x2d/0x70 arch/x86/entry/common.c:46
       [<00000000685d8cf0>] entry_SYSCALL_64_after_hwframe+0x44/0xa9

Reported-by: syzbot+71c4697e27c99fddcf17@syzkaller.appspotmail.com
Fixes: 0f212204 ("io_uring: don't rely on weak ->files references")
Cc: Pavel Begunkov <asml.silence@gmail.com>
Signed-off-by: default avatarHillf Danton <hdanton@sina.com>
Signed-off-by: default avatarJens Axboe <axboe@kernel.dk>
parent e8c954df
...@@ -9183,6 +9183,7 @@ static int io_uring_get_fd(struct io_ring_ctx *ctx) ...@@ -9183,6 +9183,7 @@ static int io_uring_get_fd(struct io_ring_ctx *ctx)
{ {
struct file *file; struct file *file;
int ret; int ret;
int fd;
#if defined(CONFIG_UNIX) #if defined(CONFIG_UNIX)
ret = sock_create_kern(&init_net, PF_UNIX, SOCK_RAW, IPPROTO_IP, ret = sock_create_kern(&init_net, PF_UNIX, SOCK_RAW, IPPROTO_IP,
...@@ -9194,12 +9195,12 @@ static int io_uring_get_fd(struct io_ring_ctx *ctx) ...@@ -9194,12 +9195,12 @@ static int io_uring_get_fd(struct io_ring_ctx *ctx)
ret = get_unused_fd_flags(O_RDWR | O_CLOEXEC); ret = get_unused_fd_flags(O_RDWR | O_CLOEXEC);
if (ret < 0) if (ret < 0)
goto err; goto err;
fd = ret;
file = anon_inode_getfile("[io_uring]", &io_uring_fops, ctx, file = anon_inode_getfile("[io_uring]", &io_uring_fops, ctx,
O_RDWR | O_CLOEXEC); O_RDWR | O_CLOEXEC);
if (IS_ERR(file)) { if (IS_ERR(file)) {
err_fd: put_unused_fd(fd);
put_unused_fd(ret);
ret = PTR_ERR(file); ret = PTR_ERR(file);
goto err; goto err;
} }
...@@ -9207,12 +9208,14 @@ static int io_uring_get_fd(struct io_ring_ctx *ctx) ...@@ -9207,12 +9208,14 @@ static int io_uring_get_fd(struct io_ring_ctx *ctx)
#if defined(CONFIG_UNIX) #if defined(CONFIG_UNIX)
ctx->ring_sock->file = file; ctx->ring_sock->file = file;
#endif #endif
if (unlikely(io_uring_add_task_file(ctx, file))) { ret = io_uring_add_task_file(ctx, file);
file = ERR_PTR(-ENOMEM); if (ret) {
goto err_fd; fput(file);
put_unused_fd(fd);
goto err;
} }
fd_install(ret, file); fd_install(fd, file);
return ret; return fd;
err: err:
#if defined(CONFIG_UNIX) #if defined(CONFIG_UNIX)
sock_release(ctx->ring_sock); sock_release(ctx->ring_sock);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment