Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

fs: replace use of system_wq with system_percpu_wq

Currently if a user enqueue a work item using schedule_delayed_work() the
used wq is "system_wq" (per-cpu wq) while queue_delayed_work() use
WORK_CPU_UNBOUND (used when a cpu is not specified). The same applies to
schedule_work() that is using system_wq and queue_work(), that makes use
again of WORK_CPU_UNBOUND.

This lack of consistentcy cannot be addressed without refactoring the API.

system_wq is a per-CPU worqueue, yet nothing in its name tells about that
CPU affinity constraint, which is very often not required by users.
Make it clear by adding a system_percpu_wq to all the fs subsystem.

The old wq will be kept for a few release cylces.

Suggested-by: Tejun Heo <tj@kernel.org>
Signed-off-by: Marco Crivellari <marco.crivellari@suse.com>
Link: https://lore.kernel.org/20250916082906.77439-3-marco.crivellari@suse.com
Signed-off-by: Christian Brauner <brauner@kernel.org>

authored by

Marco Crivellari and committed by
Christian Brauner
4ef64db0 7a4f92d3

+6 -6
+1 -1
fs/aio.c
··· 636 636 637 637 /* Synchronize against RCU protected table->table[] dereferences */ 638 638 INIT_RCU_WORK(&ctx->free_rwork, free_ioctx); 639 - queue_rcu_work(system_wq, &ctx->free_rwork); 639 + queue_rcu_work(system_percpu_wq, &ctx->free_rwork); 640 640 } 641 641 642 642 /*
+1 -1
fs/fs-writeback.c
··· 2442 2442 2443 2443 ret = proc_dointvec_minmax(table, write, buffer, lenp, ppos); 2444 2444 if (ret == 0 && write) 2445 - mod_delayed_work(system_wq, &dirtytime_work, 0); 2445 + mod_delayed_work(system_percpu_wq, &dirtytime_work, 0); 2446 2446 return ret; 2447 2447 } 2448 2448
+1 -1
fs/fuse/dev.c
··· 119 119 goto abort_conn; 120 120 121 121 out: 122 - queue_delayed_work(system_wq, &fc->timeout.work, 122 + queue_delayed_work(system_percpu_wq, &fc->timeout.work, 123 123 fuse_timeout_timer_freq); 124 124 return; 125 125
+1 -1
fs/fuse/inode.c
··· 1273 1273 { 1274 1274 fc->timeout.req_timeout = secs_to_jiffies(timeout); 1275 1275 INIT_DELAYED_WORK(&fc->timeout.work, fuse_check_timeout); 1276 - queue_delayed_work(system_wq, &fc->timeout.work, 1276 + queue_delayed_work(system_percpu_wq, &fc->timeout.work, 1277 1277 fuse_timeout_timer_freq); 1278 1278 } 1279 1279
+1 -1
fs/nfs/namespace.c
··· 335 335 num *= HZ; 336 336 *((int *)kp->arg) = num; 337 337 if (!list_empty(&nfs_automount_list)) 338 - mod_delayed_work(system_wq, &nfs_automount_task, num); 338 + mod_delayed_work(system_percpu_wq, &nfs_automount_task, num); 339 339 } else { 340 340 *((int *)kp->arg) = -1*HZ; 341 341 cancel_delayed_work(&nfs_automount_task);
+1 -1
fs/nfs/nfs4renewd.c
··· 122 122 timeout = 5 * HZ; 123 123 dprintk("%s: requeueing work. Lease period = %ld\n", 124 124 __func__, (timeout + HZ - 1) / HZ); 125 - mod_delayed_work(system_wq, &clp->cl_renewd, timeout); 125 + mod_delayed_work(system_percpu_wq, &clp->cl_renewd, timeout); 126 126 set_bit(NFS_CS_RENEWD, &clp->cl_res_state); 127 127 spin_unlock(&clp->cl_lock); 128 128 }