All of lore.kernel.org
 help / color / mirror / Atom feed
From: Chuck Lever <cel@kernel.org>
To: Trond Myklebust <trondmy@kernel.org>,
	Anna Schumaker <anna@kernel.org>,  Tejun Heo <tj@kernel.org>
Cc: Lai Jiangshan <jiangshanlai@gmail.com>,
	linux-nfs@vger.kernel.org,
	 open list <linux-kernel@vger.kernel.org>,
	Chuck Lever <cel@kernel.org>
Subject: [PATCH RFC v2 5/8] workqueue: add workqueue_set_affn_scope()
Date: Wed, 02 Sep 2026 15:28:50 -0400	[thread overview]
Message-ID: <20260902-performance-v2-5-b71c0c082f9d@kernel.org> (raw)
In-Reply-To: <20260902-performance-v2-0-b71c0c082f9d@kernel.org>

An unbound workqueue's affinity scope can be changed only through
sysfs. A module whose workqueue contends on the pool lock at the
default scope has no in-kernel way to select a finer one, because
alloc_workqueue_attrs() and apply_workqueue_attrs() are not
exported. Exporting them would also invite a caller to apply freshly
allocated attributes, which resets the nice level, cpumask, and
strict affinity the workqueue already carries.

Add workqueue_set_affn_scope(), which copies the workqueue's current
attributes, replaces only the scope, and applies the result under
wq_pool_mutex, as the sysfs affinity_scope store does. Export it so
that SUNRPC and NFS can set the scope of their workqueues when they
create them.

Signed-off-by: Chuck Lever <cel@kernel.org>
---
 include/linux/workqueue.h |  2 ++
 kernel/workqueue.c        | 37 +++++++++++++++++++++++++++++++++++++
 2 files changed, 39 insertions(+)

diff --git a/include/linux/workqueue.h b/include/linux/workqueue.h
index c8a36423cb34..585c32d8dc98 100644
--- a/include/linux/workqueue.h
+++ b/include/linux/workqueue.h
@@ -618,6 +618,8 @@ struct workqueue_attrs *alloc_workqueue_attrs_noprof(void);
 void free_workqueue_attrs(struct workqueue_attrs *attrs);
 int apply_workqueue_attrs(struct workqueue_struct *wq,
 			  const struct workqueue_attrs *attrs);
+int workqueue_set_affn_scope(struct workqueue_struct *wq,
+			     enum wq_affn_scope affn_scope);
 extern int workqueue_unbound_housekeeping_update(const struct cpumask *hk);
 
 extern bool queue_work_on(int cpu, struct workqueue_struct *wq,
diff --git a/kernel/workqueue.c b/kernel/workqueue.c
index 3c034cbc5bb3..0c2b8e87cd59 100644
--- a/kernel/workqueue.c
+++ b/kernel/workqueue.c
@@ -5610,6 +5610,43 @@ int apply_workqueue_attrs(struct workqueue_struct *wq,
 	return ret;
 }
 
+/**
+ * workqueue_set_affn_scope - change the affinity scope of an unbound workqueue
+ * @wq: the target unbound workqueue
+ * @affn_scope: the new scope, or %WQ_AFFN_DFL for the system default
+ *
+ * Reapply @wq's current attributes with only the affinity scope
+ * replaced, so the nice level, cpumask, and strict affinity the
+ * workqueue already carries survive. Pool-workqueue replacement
+ * proceeds as for apply_workqueue_attrs().
+ *
+ * Context: Process context. Takes wq_pool_mutex and performs
+ * GFP_KERNEL allocations.
+ *
+ * Return: 0 on success and -errno on failure.
+ */
+int workqueue_set_affn_scope(struct workqueue_struct *wq,
+			     enum wq_affn_scope affn_scope)
+{
+	struct workqueue_attrs *attrs;
+	int ret = -ENOMEM;
+
+	if ((unsigned int)affn_scope >= WQ_AFFN_NR_TYPES)
+		return -EINVAL;
+
+	mutex_lock(&wq_pool_mutex);
+	attrs = alloc_workqueue_attrs();
+	if (attrs) {
+		copy_workqueue_attrs(attrs, wq->attrs);
+		attrs->affn_scope = affn_scope;
+		ret = apply_workqueue_attrs_locked(wq, attrs);
+	}
+	mutex_unlock(&wq_pool_mutex);
+	free_workqueue_attrs(attrs);
+	return ret;
+}
+EXPORT_SYMBOL_GPL(workqueue_set_affn_scope);
+
 /**
  * unbound_wq_update_pwq - update a pwq slot for CPU hot[un]plug
  * @wq: the target workqueue

-- 
2.55.0


  parent reply	other threads:[~2026-09-02 19:29 UTC|newest]

Thread overview: 11+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-09-02 19:28 [PATCH RFC v2 0/8] Reduce lock contention in the NFS client Chuck Lever
2026-09-02 19:28 ` [PATCH RFC v2 1/8] SUNRPC: Use atomic_t for XID allocation Chuck Lever
2026-09-02 19:28 ` [PATCH RFC v2 2/8] SUNRPC: Split recv_lock out of xprt->queue_lock Chuck Lever
2026-09-02 19:28 ` [PATCH RFC v2 3/8] SUNRPC: Set WQ_SYSFS on rpciod and xprtiod Chuck Lever
2026-09-02 19:28 ` [PATCH RFC v2 4/8] NFS: Set WQ_SYSFS on nfsiod Chuck Lever
2026-09-02 19:28 ` Chuck Lever [this message]
2026-09-02 19:36   ` [PATCH RFC v2 5/8] workqueue: add workqueue_set_affn_scope() Tejun Heo
2026-09-03 13:41     ` Chuck Lever
2026-09-02 19:28 ` [PATCH RFC v2 6/8] SUNRPC: Reduce rpciod workqueue contention Chuck Lever
2026-09-02 19:28 ` [PATCH RFC v2 7/8] NFS: Reduce nfsiod " Chuck Lever
2026-09-02 19:28 ` [PATCH RFC v2 8/8] SUNRPC: Reduce xprtiod " Chuck Lever

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20260902-performance-v2-5-b71c0c082f9d@kernel.org \
    --to=cel@kernel.org \
    --cc=anna@kernel.org \
    --cc=jiangshanlai@gmail.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-nfs@vger.kernel.org \
    --cc=tj@kernel.org \
    --cc=trondmy@kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.