Skip to content

Commit b22fa62

Browse files
isilenceaxboe
authored andcommitted
io_uring: apply worker limits to previous users
Another change to the API io-wq worker limitation API added in 5.15, apply the limit to all prior users that already registered a tctx. It may be confusing as it's now, in particular the change covers the following 2 cases: TASK1 | TASK2 _________________________________________________ ring = create() | | limit_iowq_workers() *not limited* | TASK1 | TASK2 _________________________________________________ ring = create() | | issue_requests() limit_iowq_workers() | | *not limited* A note on locking, it's safe to traverse ->tctx_list as we hold ->uring_lock, but do that after dropping sqd->lock to avoid possible problems. It's also safe to access tctx->io_wq there because tasks kill it only after removing themselves from tctx_list, see io_uring_cancel_generic() -> io_uring_clean_tctx() Signed-off-by: Pavel Begunkov <[email protected]> Link: https://lore.kernel.org/r/d6e09ecc3545e4dc56e43c906ee3d71b7ae21bed.1634818641.git.asml.silence@gmail.com Reviewed-by: Hao Xu <[email protected]> Signed-off-by: Jens Axboe <[email protected]>
1 parent 4ea672a commit b22fa62

File tree

1 file changed

+18
-0
lines changed

1 file changed

+18
-0
lines changed

fs/io_uring.c

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10649,7 +10649,9 @@ static int io_unregister_iowq_aff(struct io_ring_ctx *ctx)
1064910649

1065010650
static int io_register_iowq_max_workers(struct io_ring_ctx *ctx,
1065110651
void __user *arg)
10652+
__must_hold(&ctx->uring_lock)
1065210653
{
10654+
struct io_tctx_node *node;
1065310655
struct io_uring_task *tctx = NULL;
1065410656
struct io_sq_data *sqd = NULL;
1065510657
__u32 new_count[2];
@@ -10702,6 +10704,22 @@ static int io_register_iowq_max_workers(struct io_ring_ctx *ctx,
1070210704
if (copy_to_user(arg, new_count, sizeof(new_count)))
1070310705
return -EFAULT;
1070410706

10707+
/* that's it for SQPOLL, only the SQPOLL task creates requests */
10708+
if (sqd)
10709+
return 0;
10710+
10711+
/* now propagate the restriction to all registered users */
10712+
list_for_each_entry(node, &ctx->tctx_list, ctx_node) {
10713+
struct io_uring_task *tctx = node->task->io_uring;
10714+
10715+
if (WARN_ON_ONCE(!tctx->io_wq))
10716+
continue;
10717+
10718+
for (i = 0; i < ARRAY_SIZE(new_count); i++)
10719+
new_count[i] = ctx->iowq_limits[i];
10720+
/* ignore errors, it always returns zero anyway */
10721+
(void)io_wq_max_workers(tctx->io_wq, new_count);
10722+
}
1070510723
return 0;
1070610724
err:
1070710725
if (sqd) {

0 commit comments

Comments
 (0)