Skip to content

Commit e0e4ab5

Browse files
isilenceaxboe
authored andcommitted
io_uring: refactor DEFER_TASKRUN multishot checks
We disallow DEFER_TASKRUN multishots from running by io-wq, which is checked by individual opcodes in the issue path. We can consolidate all it in io_wq_submit_work() at the same time moving the checks out of the hot path. Suggested-by: Jens Axboe <axboe@kernel.dk> Signed-off-by: Pavel Begunkov <asml.silence@gmail.com> Link: https://lore.kernel.org/r/e492f0f11588bb5aa11d7d24e6f53b7c7628afdb.1709905727.git.asml.silence@gmail.com Signed-off-by: Jens Axboe <axboe@kernel.dk>
1 parent 3a96378 commit e0e4ab5

File tree

3 files changed

+20
-23
lines changed

3 files changed

+20
-23
lines changed

io_uring/io_uring.c

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -944,6 +944,8 @@ bool io_fill_cqe_req_aux(struct io_kiocb *req, bool defer, s32 res, u32 cflags)
944944
u64 user_data = req->cqe.user_data;
945945
struct io_uring_cqe *cqe;
946946

947+
lockdep_assert(!io_wq_current_is_worker());
948+
947949
if (!defer)
948950
return __io_post_aux_cqe(ctx, user_data, res, cflags, false);
949951

@@ -1968,6 +1970,24 @@ void io_wq_submit_work(struct io_wq_work *work)
19681970
goto fail;
19691971
}
19701972

1973+
/*
1974+
* If DEFER_TASKRUN is set, it's only allowed to post CQEs from the
1975+
* submitter task context. Final request completions are handed to the
1976+
* right context, however this is not the case of auxiliary CQEs,
1977+
* which is the main mean of operation for multishot requests.
1978+
* Don't allow any multishot execution from io-wq. It's more restrictive
1979+
* than necessary and also cleaner.
1980+
*/
1981+
if (req->flags & REQ_F_APOLL_MULTISHOT) {
1982+
err = -EBADFD;
1983+
if (!io_file_can_poll(req))
1984+
goto fail;
1985+
err = -ECANCELED;
1986+
if (io_arm_poll_handler(req, issue_flags) != IO_APOLL_OK)
1987+
goto fail;
1988+
return;
1989+
}
1990+
19711991
if (req->flags & REQ_F_FORCE_ASYNC) {
19721992
bool opcode_poll = def->pollin || def->pollout;
19731993

io_uring/net.c

Lines changed: 0 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -78,19 +78,6 @@ struct io_sr_msg {
7878
*/
7979
#define MULTISHOT_MAX_RETRY 32
8080

81-
static inline bool io_check_multishot(struct io_kiocb *req,
82-
unsigned int issue_flags)
83-
{
84-
/*
85-
* When ->locked_cq is set we only allow to post CQEs from the original
86-
* task context. Usual request completions will be handled in other
87-
* generic paths but multipoll may decide to post extra cqes.
88-
*/
89-
return !(issue_flags & IO_URING_F_IOWQ) ||
90-
!(req->flags & REQ_F_APOLL_MULTISHOT) ||
91-
!req->ctx->task_complete;
92-
}
93-
9481
int io_shutdown_prep(struct io_kiocb *req, const struct io_uring_sqe *sqe)
9582
{
9683
struct io_shutdown *shutdown = io_kiocb_to_cmd(req, struct io_shutdown);
@@ -862,9 +849,6 @@ int io_recvmsg(struct io_kiocb *req, unsigned int issue_flags)
862849
(sr->flags & IORING_RECVSEND_POLL_FIRST))
863850
return io_setup_async_msg(req, kmsg, issue_flags);
864851

865-
if (!io_check_multishot(req, issue_flags))
866-
return io_setup_async_msg(req, kmsg, issue_flags);
867-
868852
flags = sr->msg_flags;
869853
if (force_nonblock)
870854
flags |= MSG_DONTWAIT;
@@ -956,9 +940,6 @@ int io_recv(struct io_kiocb *req, unsigned int issue_flags)
956940
(sr->flags & IORING_RECVSEND_POLL_FIRST))
957941
return -EAGAIN;
958942

959-
if (!io_check_multishot(req, issue_flags))
960-
return -EAGAIN;
961-
962943
sock = sock_from_file(req->file);
963944
if (unlikely(!sock))
964945
return -ENOTSOCK;
@@ -1408,8 +1389,6 @@ int io_accept(struct io_kiocb *req, unsigned int issue_flags)
14081389
struct file *file;
14091390
int ret, fd;
14101391

1411-
if (!io_check_multishot(req, issue_flags))
1412-
return -EAGAIN;
14131392
retry:
14141393
if (!fixed) {
14151394
fd = __get_unused_fd_flags(accept->flags, accept->nofile);

io_uring/rw.c

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -933,8 +933,6 @@ int io_read_mshot(struct io_kiocb *req, unsigned int issue_flags)
933933
*/
934934
if (!io_file_can_poll(req))
935935
return -EBADFD;
936-
if (issue_flags & IO_URING_F_IOWQ)
937-
return -EAGAIN;
938936

939937
ret = __io_read(req, issue_flags);
940938

0 commit comments

Comments
 (0)