On Sat, 2021-08-07 at 17:13 -0700, Nadav Amit wrote: > From: Nadav Amit <namit@xxxxxxxxxx> > > When using SQPOLL, the submission queue polling thread calls > task_work_run() to run queued work. However, when work is added with > TWA_SIGNAL - as done by io_uring itself - the TIF_NOTIFY_SIGNAL remains > set afterwards and is never cleared. > > Consequently, when the submission queue polling thread checks whether > signal_pending(), it may always find a pending signal, if > task_work_add() was ever called before. > > The impact of this bug might be different on different kernel versions. > It appears that on 5.14 it would only cause unnecessary calculation and > prevent the polling thread from sleeping. On 5.13, where the bug was > found, it stops the polling thread from finding newly submitted work. > > Instead of task_work_run(), use tracehook_notify_signal() that clears > TIF_NOTIFY_SIGNAL. Test for TIF_NOTIFY_SIGNAL in addition to > current->task_works to avoid a race in which task_works is cleared but > the TIF_NOTIFY_SIGNAL is set. > > Fixes: 685fe7feedb96 ("io-wq: eliminate the need for a manager thread") > Cc: Jens Axboe <axboe@xxxxxxxxx> > Cc: Pavel Begunkov <asml.silence@xxxxxxxxx> > Signed-off-by: Nadav Amit <namit@xxxxxxxxxx> > --- > fs/io_uring.c | 5 +++-- > 1 file changed, 3 insertions(+), 2 deletions(-) > > diff --git a/fs/io_uring.c b/fs/io_uring.c > index 5a0fd6bcd318..f39244d35f90 100644 > --- a/fs/io_uring.c > +++ b/fs/io_uring.c > @@ -78,6 +78,7 @@ > #include <linux/task_work.h> > #include <linux/pagemap.h> > #include <linux/io_uring.h> > +#include <linux/tracehook.h> > > #define CREATE_TRACE_POINTS > #include <trace/events/io_uring.h> > @@ -2203,9 +2204,9 @@ static inline unsigned int io_put_rw_kbuf(struct > io_kiocb *req) > > static inline bool io_run_task_work(void) > { > - if (current->task_works) { > + if (test_thread_flag(TIF_NOTIFY_SIGNAL) || current->task_works) > { > __set_current_state(TASK_RUNNING); > - task_work_run(); > + tracehook_notify_signal(); > return true; > } > thx a lot for this patch! This explains what I am seeing here: https://lore.kernel.org/io-uring/4d93d0600e4a9590a48d320c5a7dd4c54d66f095.camel@xxxxxxxxxxxxxx/ I was under the impression that task_work_run() was clearing TIF_NOTIFY_SIGNAL. your patch made me realize that it does not...