Skip to content

Commit f331c5d

Browse files
committed
Merge tag 'io_uring-6.3-2023-03-09' of git://git.kernel.dk/linux
Pull io_uring fixes from Jens Axboe: - Stop setting PF_NO_SETAFFINITY on io-wq workers. This has been reported in the past as it confuses some applications, as some of their threads will fail with -1/EINVAL if attempted affinitized. Most recent report was on cpusets, where enabling that with io-wq workers active will fail. Just deal with the mask changing by checking when a worker times out, and then exit if we have no work pending. - Fix an issue with passthrough support where we don't properly check if the file type has pollable uring_cmd support. - Fix a reported W=1 warning on a variable being set and unused. Add a special helper for iterating these lists that doesn't save the previous list element, if that iterator never ends up using it. * tag 'io_uring-6.3-2023-03-09' of git://git.kernel.dk/linux: io_uring: silence variable ‘prev’ set but not used warning io_uring/uring_cmd: ensure that device supports IOPOLL io_uring/io-wq: stop setting PF_NO_SETAFFINITY on io-wq workers
2 parents 49be4fb + fa78033 commit f331c5d

File tree

4 files changed

+20
-9
lines changed

4 files changed

+20
-9
lines changed

io_uring/io-wq.c

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -616,7 +616,7 @@ static int io_wqe_worker(void *data)
616616
struct io_wqe_acct *acct = io_wqe_get_acct(worker);
617617
struct io_wqe *wqe = worker->wqe;
618618
struct io_wq *wq = wqe->wq;
619-
bool last_timeout = false;
619+
bool exit_mask = false, last_timeout = false;
620620
char buf[TASK_COMM_LEN];
621621

622622
worker->flags |= (IO_WORKER_F_UP | IO_WORKER_F_RUNNING);
@@ -632,8 +632,11 @@ static int io_wqe_worker(void *data)
632632
io_worker_handle_work(worker);
633633

634634
raw_spin_lock(&wqe->lock);
635-
/* timed out, exit unless we're the last worker */
636-
if (last_timeout && acct->nr_workers > 1) {
635+
/*
636+
* Last sleep timed out. Exit if we're not the last worker,
637+
* or if someone modified our affinity.
638+
*/
639+
if (last_timeout && (exit_mask || acct->nr_workers > 1)) {
637640
acct->nr_workers--;
638641
raw_spin_unlock(&wqe->lock);
639642
__set_current_state(TASK_RUNNING);
@@ -652,7 +655,11 @@ static int io_wqe_worker(void *data)
652655
continue;
653656
break;
654657
}
655-
last_timeout = !ret;
658+
if (!ret) {
659+
last_timeout = true;
660+
exit_mask = !cpumask_test_cpu(raw_smp_processor_id(),
661+
wqe->cpu_mask);
662+
}
656663
}
657664

658665
if (test_bit(IO_WQ_BIT_EXIT, &wq->state))
@@ -704,7 +711,6 @@ static void io_init_new_worker(struct io_wqe *wqe, struct io_worker *worker,
704711
tsk->worker_private = worker;
705712
worker->task = tsk;
706713
set_cpus_allowed_ptr(tsk, wqe->cpu_mask);
707-
tsk->flags |= PF_NO_SETAFFINITY;
708714

709715
raw_spin_lock(&wqe->lock);
710716
hlist_nulls_add_head_rcu(&worker->nulls_node, &wqe->free_list);

io_uring/io_uring.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1499,14 +1499,14 @@ void io_free_batch_list(struct io_ring_ctx *ctx, struct io_wq_work_node *node)
14991499
static void __io_submit_flush_completions(struct io_ring_ctx *ctx)
15001500
__must_hold(&ctx->uring_lock)
15011501
{
1502-
struct io_wq_work_node *node, *prev;
15031502
struct io_submit_state *state = &ctx->submit_state;
1503+
struct io_wq_work_node *node;
15041504

15051505
__io_cq_lock(ctx);
15061506
/* must come first to preserve CQE ordering in failure cases */
15071507
if (state->cqes_count)
15081508
__io_flush_post_cqes(ctx);
1509-
wq_list_for_each(node, prev, &state->compl_reqs) {
1509+
__wq_list_for_each(node, &state->compl_reqs) {
15101510
struct io_kiocb *req = container_of(node, struct io_kiocb,
15111511
comp_list);
15121512

io_uring/slist.h

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,9 @@
33

44
#include <linux/io_uring_types.h>
55

6+
#define __wq_list_for_each(pos, head) \
7+
for (pos = (head)->first; pos; pos = (pos)->next)
8+
69
#define wq_list_for_each(pos, prv, head) \
710
for (pos = (head)->first, prv = NULL; pos; prv = pos, pos = (pos)->next)
811

@@ -113,4 +116,4 @@ static inline struct io_wq_work *wq_next_work(struct io_wq_work *work)
113116
return container_of(work->list.next, struct io_wq_work, list);
114117
}
115118

116-
#endif // INTERNAL_IO_SLIST_H
119+
#endif // INTERNAL_IO_SLIST_H

io_uring/uring_cmd.c

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -108,7 +108,7 @@ int io_uring_cmd(struct io_kiocb *req, unsigned int issue_flags)
108108
struct file *file = req->file;
109109
int ret;
110110

111-
if (!req->file->f_op->uring_cmd)
111+
if (!file->f_op->uring_cmd)
112112
return -EOPNOTSUPP;
113113

114114
ret = security_uring_cmd(ioucmd);
@@ -120,6 +120,8 @@ int io_uring_cmd(struct io_kiocb *req, unsigned int issue_flags)
120120
if (ctx->flags & IORING_SETUP_CQE32)
121121
issue_flags |= IO_URING_F_CQE32;
122122
if (ctx->flags & IORING_SETUP_IOPOLL) {
123+
if (!file->f_op->uring_cmd_iopoll)
124+
return -EOPNOTSUPP;
123125
issue_flags |= IO_URING_F_IOPOLL;
124126
req->iopoll_completed = 0;
125127
WRITE_ONCE(ioucmd->cookie, NULL);

0 commit comments

Comments
 (0)