linux/io_uring
Jens Axboe c0325d6892 io_uring/sqpoll: be smarter on when to update the stime usage
Commit a94e065726 upstream.

The current approach is a bit naive, and hence calls the time querying
way too often. Only start the "doing work" timer when there's actual
work to do, and then use that information to terminate (and account) the
work time once done. This greatly reduces the frequency of these calls,
when they cannot have changed anyway.

Running a basic random reader that is setup to use SQPOLL, a profile
before this change shows these as the top cycle consumers:

+   32.60%  iou-sqp-1074  [kernel.kallsyms]  [k] thread_group_cputime_adjusted
+   19.97%  iou-sqp-1074  [kernel.kallsyms]  [k] thread_group_cputime
+   12.20%  io_uring      io_uring           [.] submitter_uring_fn
+    4.13%  iou-sqp-1074  [kernel.kallsyms]  [k] getrusage
+    2.45%  iou-sqp-1074  [kernel.kallsyms]  [k] io_submit_sqes
+    2.18%  iou-sqp-1074  [kernel.kallsyms]  [k] __pi_memset_generic
+    2.09%  iou-sqp-1074  [kernel.kallsyms]  [k] cputime_adjust

and after this change, top of profile looks as follows:

+   36.23%  io_uring     io_uring           [.] submitter_uring_fn
+   23.26%  iou-sqp-819  [kernel.kallsyms]  [k] io_sq_thread
+   10.14%  iou-sqp-819  [kernel.kallsyms]  [k] io_sq_tw
+    6.52%  iou-sqp-819  [kernel.kallsyms]  [k] tctx_task_work_run
+    4.82%  iou-sqp-819  [kernel.kallsyms]  [k] nvme_submit_cmds.part.0
+    2.91%  iou-sqp-819  [kernel.kallsyms]  [k] io_submit_sqes
[...]
     0.02%  iou-sqp-819  [kernel.kallsyms]  [k] cputime_adjust

where it's spending the cycles on things that actually matter.

Reported-by: Fengnan Chang <changfengnan@bytedance.com>
Cc: stable@vger.kernel.org
Fixes: 3fcb9d1720 ("io_uring/sqpoll: statistics of the true utilization of sq threads")
Signed-off-by: Jens Axboe <axboe@kernel.dk>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
History 2025-10-29 14:08:59 +01:00
..
advise.c io_uring/advise: support 64-bit lengths 2024-06-16 14:54:55 -06:00
advise.h io_uring: split out fadvise/madvise operations 2022-07-24 18:39:11 -06:00
alloc_cache.h io_uring/alloc_cache: switch to array based caching 2024-04-15 08:10:25 -06:00
cancel.c io_uring: fix warnings on shadow variables 2024-04-15 08:10:26 -06:00
cancel.h io_uring: fix cancellation overwriting req->flags 2024-06-13 19:25:28 -06:00
epoll.c io_uring: undeprecate epoll_ctl support 2023-05-26 20:22:41 -06:00
epoll.h io_uring: move epoll handler to its own file 2022-07-24 18:39:11 -06:00
eventfd.c io_uring/eventfd: ensure io_eventfd_signal() defers another RCU period 2025-01-17 13:40:58 +01:00
eventfd.h io_uring/eventfd: move eventfd handling to separate file 2024-06-16 14:54:55 -06:00
fdinfo.c io_uring/sqpoll: switch away from getrusage() for CPU accounting 2025-10-29 14:08:59 +01:00
fdinfo.h io_uring: move fdinfo helpers to its own file 2022-07-24 18:39:12 -06:00
filetable.c io_uring: correct __must_hold annotation in io_install_fixed_file 2025-10-29 14:08:59 +01:00
filetable.h io_uring: expand main struct io_kiocb flags to 64-bits 2024-02-08 13:27:03 -07:00
fs.c io_uring/fs: consider link->flags when getting path for LINKAT 2023-11-20 09:01:42 -07:00
fs.h io_uring: split out filesystem related operations 2022-07-24 18:39:11 -06:00
futex.c io_uring/futex: ensure io_futex_wait() cleans up properly on failure 2025-08-28 16:31:05 +02:00
futex.h io_uring/alloc_cache: switch to array based caching 2024-04-15 08:10:25 -06:00
io-wq.c io_uring: fix task leak issue in io_wq_create() 2025-06-27 11:11:36 +01:00
io-wq.h io_uring/io-wq: make io_wq_work flags atomic 2024-06-16 14:54:55 -06:00
io_uring.c io_uring/msg_ring: kill alloc_cache for io_kiocb allocations 2025-09-25 11:13:48 +02:00
io_uring.h io_uring: include dying ring in task_work "should cancel" state 2025-09-25 11:13:47 +02:00
kbuf.c io_uring/kbuf: flag partial buffer mappings 2025-07-06 11:01:48 +02:00
kbuf.h io_uring/kbuf: drop WARN_ON_ONCE() from incremental length check 2025-09-25 11:13:48 +02:00
Makefile io_uring: add GCOV_PROFILE_URING Kconfig option 2024-08-30 10:52:02 -06:00
memmap.c io_uring: check for overflows in io_pin_pages 2024-12-05 14:02:50 +01:00
memmap.h io_uring: move mapping/allocation helpers to a separate file 2024-04-15 08:10:26 -06:00
msg_ring.c io_uring/msg_ring: kill alloc_cache for io_kiocb allocations 2025-09-25 11:13:48 +02:00
msg_ring.h io_uring/msg_ring: add an alloc cache for io_kiocb entries 2024-06-24 08:39:55 -06:00
napi.c io_uring: user registered clockid for wait timeouts 2024-08-25 08:27:01 -06:00
napi.h io_uring/napi: postpone napi timeout adjustment 2024-08-25 08:27:01 -06:00
net.c io_uring/net: commit partial buffers on retry 2025-08-28 16:31:04 +02:00
net.h io_uring: Introduce IORING_OP_LISTEN 2024-06-19 07:57:21 -06:00
nop.c io_uring: support to inject result for NOP 2024-05-10 06:09:45 -06:00
nop.h io_uring: move nop into its own file 2022-07-24 18:39:11 -06:00
notif.c io_uring: fix incorrect io_kiocb reference in io_link_skb 2025-09-25 11:13:49 +02:00
notif.h io_uring/notif: implement notification stacking 2024-04-22 19:31:18 -06:00
opdef.c io_uring: make fallocate be hashed work 2025-07-17 18:37:21 +02:00
opdef.h io_uring: Fix probe of disabled operations 2024-06-19 08:58:00 -06:00
openclose.c io_uring: enable audit and restrict cred override for IORING_OP_FIXED_FD_INSTALL 2024-01-23 15:25:14 -07:00
openclose.h io_uring/openclose: add support for IORING_OP_FIXED_FD_INSTALL 2023-12-12 07:42:57 -07:00
poll.c io_uring: include dying ring in task_work "should cancel" state 2025-09-25 11:13:47 +02:00
poll.h io_uring/poll: shrink alloc cache size to 32 2024-04-15 08:10:25 -06:00
refs.h io_uring: always do atomic put from iowq 2025-05-02 07:59:21 +02:00
register.c io_uring: consistently use rcu semantics with sqpoll thread 2025-06-19 15:32:33 +02:00
register.h io_uring: clean up a type in io_uring_register_get_file() 2024-09-16 12:04:10 -06:00
rsrc.c io_uring/rsrc: don't rely on user vaddr alignment 2025-07-06 11:01:47 +02:00
rsrc.h io_uring/rsrc: don't rely on user vaddr alignment 2025-07-06 11:01:47 +02:00
rw.c Revert "io_uring/rw: drop -EOPNOTSUPP check in __io_complete_rw_common()" 2025-10-23 16:20:26 +02:00
rw.h io_uring/alloc_cache: switch to array based caching 2024-04-15 08:10:25 -06:00
slist.h io_uring: silence variable ‘prev’ set but not used warning 2023-03-09 10:10:58 -07:00
splice.c splice: return type ssize_t from all helpers 2023-12-12 16:19:59 +01:00
splice.h io_uring: split out splice related operations 2022-07-24 18:39:11 -06:00
sqpoll.c io_uring/sqpoll: be smarter on when to update the stime usage 2025-10-29 14:08:59 +01:00
sqpoll.h io_uring/sqpoll: switch away from getrusage() for CPU accounting 2025-10-29 14:08:59 +01:00
statx.c vfs: retire user_path_at_empty and drop empty arg from getname_flags 2024-06-05 17:03:57 +02:00
statx.h io_uring: move statx handling to its own file 2022-07-24 18:39:11 -06:00
sync.c io_uring: for requests that require async, force it 2023-01-29 15:18:26 -07:00
sync.h io_uring: split out fs related sync/fallocate functions 2022-07-24 18:39:11 -06:00
tctx.c io_uring/tctx: work around xa_store() allocation error issue 2024-12-14 20:04:10 +01:00
tctx.h io_uring: simplify __io_uring_add_tctx_node 2022-10-07 12:25:30 -06:00
timeout.c io_uring: include dying ring in task_work "should cancel" state 2025-09-25 11:13:47 +02:00
timeout.h io_uring: remove unused return from io_disarm_next 2022-09-21 13:15:01 -06:00
truncate.c io_uring: add support for ftruncate 2024-02-09 09:04:39 -07:00
truncate.h io_uring: add support for ftruncate 2024-02-09 09:04:39 -07:00
uring_cmd.c io_uring: include dying ring in task_work "should cancel" state 2025-09-25 11:13:47 +02:00
uring_cmd.h io_uring/alloc_cache: switch to array based caching 2024-04-15 08:10:25 -06:00
waitid.c io_uring/waitid: always prune wait queue entry in io_waitid_wait() 2025-10-15 12:00:20 +02:00
waitid.h io_uring: add IORING_OP_WAITID support 2023-09-21 12:04:45 -06:00
xattr.c vfs: retire user_path_at_empty and drop empty arg from getname_flags 2024-06-05 17:03:57 +02:00
xattr.h io_uring: move xattr related opcodes to its own file 2022-07-24 18:39:11 -06:00