From: Madadi Vineeth Reddy <vineethr@linux.ibm.com>
To: "Shubhang Kaushik (Ampere)" <sh@gentwo.org>
Cc: Jonathan Corbet <corbet@lwn.net>,
Shuah Khan <skhan@linuxfoundation.org>,
Randy Dunlap <rdunlap@infradead.org>,
Ingo Molnar <mingo@redhat.com>,
Peter Zijlstra <peterz@infradead.org>,
Juri Lelli <juri.lelli@redhat.com>,
Vincent Guittot <vincent.guittot@linaro.org>,
Dietmar Eggemann <dietmar.eggemann@arm.com>,
Steven Rostedt <rostedt@goodmis.org>,
Ben Segall <bsegall@google.com>, Mel Gorman <mgorman@suse.de>,
Valentin Schneider <vschneid@redhat.com>,
K Prateek Nayak <kprateek.nayak@amd.com>,
Shubhang Kaushik <shubhang@os.amperecomputing.com>,
Christopher Lameter <clameter@amperecomputing.com>,
Shrikanth Hegde <sshegde@linux.ibm.com>,
linux-doc@vger.kernel.org, linux-kernel@vger.kernel.org,
Madadi Vineeth Reddy <vineethr@linux.ibm.com>
Subject: Re: [RFC PATCH 1/2] sched: Document WF_SYNC wakeup placement semantics
Date: Thu, 3 Sep 2026 08:15:48 +0530 [thread overview]
Message-ID: <d52d3775-ded0-4b7a-8315-6e940ba90f4a@linux.ibm.com> (raw)
In-Reply-To: <20260825-sched-wf-sync-doc-v1-1-f899edb44ff5@gentwo.org>
On 26/08/26 04:16, Shubhang Kaushik (Ampere) wrote:
> WF_SYNC is supplied by callers that expect the waker to schedule away
> soon. The fair-class wakeup path uses it as a heuristic, but its
> placement and preemption behavior is not documented.
>
> Document the current behavior from try_to_wake_up() through
> select_task_rq_fair(), select_idle_sibling(), and preempt_sync(). In
> particular, document that WF_SYNC does not bypass wake_wide(), does not
> make wake_affine()'s target final, and does not require immediate wakee
> preemption.
>
> This documents existing behavior only. It does not establish a new
> WF_SYNC placement policy.
>
> Signed-off-by: Shubhang Kaushik (Ampere) <sh@gentwo.org>
> ---
> Documentation/scheduler/index.rst | 1 +
> Documentation/scheduler/sched-wake-affinity.rst | 133 ++++++++++++++++++++++++
> 2 files changed, 134 insertions(+)
>
> diff --git a/Documentation/scheduler/index.rst b/Documentation/scheduler/index.rst
> index 17ce8d76befc1bb1dc289e9243bdca98c9ccb172..ac95c79617fd2c03564ea4a9dad362091b9d1b86 100644
> --- a/Documentation/scheduler/index.rst
> +++ b/Documentation/scheduler/index.rst
> @@ -14,6 +14,7 @@ Scheduler
> sched-design-CFS
> sched-eevdf
> sched-domains
> + sched-wake-affinity
> sched-capacity
> sched-energy
> schedutil
> diff --git a/Documentation/scheduler/sched-wake-affinity.rst b/Documentation/scheduler/sched-wake-affinity.rst
> new file mode 100644
> index 0000000000000000000000000000000000000000..6b0dc83da537ad576130ef165a2bb1cf5abd814a
> --- /dev/null
> +++ b/Documentation/scheduler/sched-wake-affinity.rst
> @@ -0,0 +1,133 @@
> +.. SPDX-License-Identifier: GPL-2.0
> +
> +==============================
> +WF_SYNC Wakeup Placement Hints
> +==============================
> +
> +WF_SYNC is a wakeup flag supplied by callers that expect the waking task
> +to schedule away soon after waking another task. It is a scheduler hint,
> +not a CPU-placement request.
> +
> +The synchronous waitqueue helpers pass WF_SYNC to try_to_wake_up(). The
> +wakeup path adds WF_TTWU before invoking the scheduler. WF_SYNC itself
> +does not block, yield, or otherwise change the state of the waker.
> +
> +This document describes the current behavior for the fair scheduler.
> +Other scheduler classes may ignore WF_SYNC or apply their own policy.
> +
> +Wakeup paths
> +============
> +
> +A successful wakeup does not always select a CPU. If the wakee is already
> +queued, try_to_wake_up() can complete the wakeup through ttwu_runnable().
> +That path retains the wakee's current runqueue, although it can still
> +invoke wakeup_preempt().
> +
> +For a wakee that is not queued, try_to_wake_up() calls
> +select_task_rq(). If the wakee has one allowed CPU or migration is
> +disabled, select_task_rq() bypasses the scheduler-class CPU-selection
> +method and selects an allowed CPU directly.
> +
> +Fair-class CPU selection
> +========================
> +
> +For a fair-class wakee, select_task_rq_fair() derives its local sync
> +state as::
> +
> + sync = (wake_flags & WF_SYNC) &&
> + !(current->flags & PF_EXITING);
> +
> +Thus, WF_SYNC does not influence wake-affine selection when the current
> +task is exiting.
> +
> +For WF_TTWU wakeups, select_task_rq_fair() first calls record_wakee().
> +It can then return before wake-affine selection in either of these cases:
> +
> +* WF_CURRENT_CPU is set and the waking CPU is allowed; or
> +* find_energy_efficient_cpu() selects a CPU while the root domain is not
> + overutilized.
> +
> +Otherwise, the fair scheduler computes::
> +
> + want_affine = !wake_wide(p) &&
> + cpumask_test_cpu(cpu, p->cpus_ptr);
> +
> +wake_wide() uses the wakee-flip state maintained by record_wakee() to
> +identify broad wakeup relationships. WF_SYNC does not override this
> +classification.
> +
> +Wake affinity is considered only when want_affine is true, the domain has
> +SD_WAKE_AFFINE set, and the wakee's previous CPU belongs to that domain.
> +wake_affine() considers only two CPUs: the waking CPU and the wakee's
> +previous CPU.
> +
> +With WF_SYNC, wake_affine_idle() can prefer the waking CPU when::
> +
> + rq->nr_running - cfs_h_nr_delayed(rq) == 1
> +
> +wake_affine_weight() also adjusts the effective load comparison by
> +removing the current task's load from the waking CPU and biasing the
> +previous-CPU effective load.
> +
> +The result of wake_affine() is only a candidate. For WF_TTWU wakeups,
> +select_task_rq_fair() passes that candidate to select_idle_sibling().
This document reproduces the implementation literally like want_affine,
nr_running, helper names. This could quickly go stale with code changes
and nothing will tell us then. I think the contract doesn't need the
call flow.
Thanks,
Vineeth
> +
> +Idle CPU selection
> +==================
> +
> +select_idle_sibling() first tests whether the candidate CPU is idle and
> +can run the wakee. If not, it can select:
> +
> +* the previous CPU when it is cache-affine and idle;
> +* a recently used CPU when it is cache-affine and idle;
> +* an idle SMT sibling; or
> +* another idle CPU in the relevant search domain.
> +
> +On asymmetric-capacity systems, the search uses sd_asym_cpucapacity when
> +available. Otherwise, it uses sd_llc for the candidate CPU.
> +
> +Consequently, WF_SYNC does not guarantee that the wakee runs on the
> +waker CPU, remains on its previous CPU, avoids migration, or shares a
> +core with the waker.
> +
> +Fair-class wakeup preemption
> +============================
> +
> +WF_SYNC can also affect wakeup_preempt_fair(). The normal fair-class
> +preemption checks run first. In particular, a non-idle wakee can preempt
> +an idle entity, and PREEMPT_SHORT can select the wakee before the
> +WF_SYNC-specific path is reached.
> +
> +If the wakee becomes the next buddy after those checks, preempt_sync()
> +uses WF_SYNC to decide whether to request rescheduling. The wakee must
> +be earlier than the current entity, and the current entity must have run
> +for at least the applicable threshold. The threshold is
> +sysctl_sched_migration_cost, divided by four when WF_RQ_SELECTED is set.
> +
> +If those conditions are not met, preempt_sync() returns
> +PREEMPT_WAKEUP_NONE. Consequently, WF_SYNC neither guarantees nor
> +prevents immediate wakee preemption. On UP, it can avoid an unnecessary
> +preemption when the waker is expected to schedule away.
> +
> +Semantics and policy
> +====================
> +
> +WF_SYNC is a non-binding hint. It does not guarantee that the wakee:
> +
> +* runs on the waker CPU;
> +* remains on its previous CPU;
> +* avoids migration;
> +* shares a core with the waker; or
> +* immediately preempts the current task.
> +
> +The scheduler does not verify that the waker subsequently blocks.
> +Callers may therefore use WF_SYNC where the waker continues to execute,
> +or where several wakeups are issued before it schedules away.
> +
> +The current policy leaves the locality, parallelism, topology, load, and
> +capacity tradeoffs to the scheduler. It does not require the wakee to
> +remain on the waker CPU when that CPU has no other runnable task.
> +
> +Any future policy that strengthens WF_SYNC placement semantics must
> +consider the different call sites, workload patterns, and hardware
> +topologies that use the flag.
>
next prev parent reply other threads:[~2026-09-03 2:47 UTC|newest]
Thread overview: 4+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-08-25 22:46 [RFC PATCH 0/2] sched: Document WF_SYNC wakeup placement semantics Shubhang Kaushik (Ampere)
2026-08-25 22:46 ` [RFC PATCH 1/2] " Shubhang Kaushik (Ampere)
2026-09-03 2:45 ` Madadi Vineeth Reddy [this message]
2026-08-25 22:46 ` [RFC PATCH 2/2] sched/wait: Clarify WF_SYNC wakeup semantics Shubhang Kaushik (Ampere)
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=d52d3775-ded0-4b7a-8315-6e940ba90f4a@linux.ibm.com \
--to=vineethr@linux.ibm.com \
--cc=bsegall@google.com \
--cc=clameter@amperecomputing.com \
--cc=corbet@lwn.net \
--cc=dietmar.eggemann@arm.com \
--cc=juri.lelli@redhat.com \
--cc=kprateek.nayak@amd.com \
--cc=linux-doc@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=mgorman@suse.de \
--cc=mingo@redhat.com \
--cc=peterz@infradead.org \
--cc=rdunlap@infradead.org \
--cc=rostedt@goodmis.org \
--cc=sh@gentwo.org \
--cc=shubhang@os.amperecomputing.com \
--cc=skhan@linuxfoundation.org \
--cc=sshegde@linux.ibm.com \
--cc=vincent.guittot@linaro.org \
--cc=vschneid@redhat.com \
/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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox