in io-wq.c: io_wq_max_workers(), new_count[] was changed right after each node's value was set. this cause the next node got the setting of the previous one, following patch fixed it. returned values are copied from node 0. Signed-off-by: Beld Zhang <beldzhang@xxxxxxxxx> --- diff --git a/fs/io-wq.c b/fs/io-wq.c index c51691262208..b6f903fa41bd 100644 --- a/fs/io-wq.c +++ b/fs/io-wq.c @@ -1308,7 +1308,8 @@ int io_wq_cpu_affinity(struct io_wq *wq, cpumask_var_t mask) */ int io_wq_max_workers(struct io_wq *wq, int *new_count) { - int i, node, prev = 0; + int i, node; + int prev[IO_WQ_ACCT_NR]; BUILD_BUG_ON((int) IO_WQ_ACCT_BOUND != (int) IO_WQ_BOUND); BUILD_BUG_ON((int) IO_WQ_ACCT_UNBOUND != (int) IO_WQ_UNBOUND); @@ -1319,6 +1320,9 @@ int io_wq_max_workers(struct io_wq *wq, int *new_count) new_count[i] = task_rlimit(current, RLIMIT_NPROC); } + for (i = 0; i < IO_WQ_ACCT_NR; i++) + prev[i] = 0; + rcu_read_lock(); for_each_node(node) { struct io_wqe *wqe = wq->wqes[node]; @@ -1327,13 +1331,16 @@ int io_wq_max_workers(struct io_wq *wq, int *new_count) raw_spin_lock(&wqe->lock); for (i = 0; i < IO_WQ_ACCT_NR; i++) { acct = &wqe->acct[i]; - prev = max_t(int, acct->max_workers, prev); + if (node == 0) + prev[i] = max_t(int, acct->max_workers, prev[i]); if (new_count[i]) acct->max_workers = new_count[i]; - new_count[i] = prev; } raw_spin_unlock(&wqe->lock); } + for (i = 0; i < IO_WQ_ACCT_NR; i++) + new_count[i] = prev[i]; + rcu_read_unlock(); return 0; }