diff --git a/io_uring/poll.c b/io_uring/poll.c index b9681d0f9f13..5df09e4e958d 100644 --- a/io_uring/poll.c +++ b/io_uring/poll.c @@ -922,6 +922,11 @@ int io_poll_remove(struct io_kiocb *req, unsigned int issue_flags) goto out; } + /* + * Set cancel res early, so io_poll_add() can overwrite it, if + * necessary. + */ + io_req_set_res(preq, -ECANCELED, 0); if (poll_update->update_events || poll_update->update_user_data) { /* only mask one event flags, keep behavior flags */ if (poll_update->update_events) { @@ -936,12 +941,12 @@ int io_poll_remove(struct io_kiocb *req, unsigned int issue_flags) ret2 = io_poll_add(preq, issue_flags & ~IO_URING_F_UNLOCKED); /* successfully updated, don't complete poll request */ - if (!ret2 || ret2 == -EIOCBQUEUED) + if (ret2 == IOU_ISSUE_SKIP_COMPLETE) goto out; } - req_set_fail(preq); - io_req_set_res(preq, -ECANCELED, 0); + if (preq->cqe.res < 0) + req_set_fail(preq); preq->io_task_work.func = io_req_task_complete; io_req_task_work_add(preq); out: