Line data Source code
1 : // SPDX-License-Identifier: GPL-2.0 2 : #include <linux/kernel.h> 3 : #include <linux/errno.h> 4 : #include <linux/file.h> 5 : #include <linux/fs.h> 6 : #include <linux/uaccess.h> 7 : #include <linux/io_uring.h> 8 : #include <linux/eventpoll.h> 9 : 10 : #include <uapi/linux/io_uring.h> 11 : 12 : #include "io_uring.h" 13 : #include "epoll.h" 14 : 15 : #if defined(CONFIG_EPOLL) 16 : struct io_epoll { 17 : struct file *file; 18 : int epfd; 19 : int op; 20 : int fd; 21 : struct epoll_event event; 22 : }; 23 : 24 0 : int io_epoll_ctl_prep(struct io_kiocb *req, const struct io_uring_sqe *sqe) 25 : { 26 0 : struct io_epoll *epoll = io_kiocb_to_cmd(req, struct io_epoll); 27 : 28 0 : pr_warn_once("%s: epoll_ctl support in io_uring is deprecated and will " 29 : "be removed in a future Linux kernel version.\n", 30 : current->comm); 31 : 32 0 : if (sqe->buf_index || sqe->splice_fd_in) 33 : return -EINVAL; 34 : 35 0 : epoll->epfd = READ_ONCE(sqe->fd); 36 0 : epoll->op = READ_ONCE(sqe->len); 37 0 : epoll->fd = READ_ONCE(sqe->off); 38 : 39 0 : if (ep_op_has_event(epoll->op)) { 40 : struct epoll_event __user *ev; 41 : 42 0 : ev = u64_to_user_ptr(READ_ONCE(sqe->addr)); 43 0 : if (copy_from_user(&epoll->event, ev, sizeof(*ev))) 44 : return -EFAULT; 45 : } 46 : 47 : return 0; 48 : } 49 : 50 0 : int io_epoll_ctl(struct io_kiocb *req, unsigned int issue_flags) 51 : { 52 0 : struct io_epoll *ie = io_kiocb_to_cmd(req, struct io_epoll); 53 : int ret; 54 0 : bool force_nonblock = issue_flags & IO_URING_F_NONBLOCK; 55 : 56 0 : ret = do_epoll_ctl(ie->epfd, ie->op, ie->fd, &ie->event, force_nonblock); 57 0 : if (force_nonblock && ret == -EAGAIN) 58 : return -EAGAIN; 59 : 60 0 : if (ret < 0) 61 0 : req_set_fail(req); 62 0 : io_req_set_res(req, ret, 0); 63 0 : return IOU_OK; 64 : } 65 : #endif