From: Wanpeng Li <kernellwp@gmail.com>
To: Peter Zijlstra <peterz@infradead.org>,
Ingo Molnar <mingo@redhat.com>,
Thomas Gleixner <tglx@linutronix.de>,
Paolo Bonzini <pbonzini@redhat.com>,
Sean Christopherson <seanjc@google.com>
Cc: K Prateek Nayak <kprateek.nayak@amd.com>,
Christian Borntraeger <borntraeger@linux.ibm.com>,
Steven Rostedt <rostedt@goodmis.org>,
Vincent Guittot <vincent.guittot@linaro.org>,
Juri Lelli <juri.lelli@redhat.com>,
linux-kernel@vger.kernel.org, kvm@vger.kernel.org,
Wanpeng Li <wanpengli@tencent.com>,
Richie Buturla <richie@linux.ibm.com>
Subject: [PATCH v3 09/10] KVM: Add IPI-aware directed-yield candidate selection
Date: Fri, 12 Jun 2026 09:33:54 +0800 [thread overview]
Message-ID: <20260612013355.59231-10-kernellwp@gmail.com> (raw)
In-Reply-To: <20260612013355.59231-1-kernellwp@gmail.com>
From: Wanpeng Li <wanpengli@tencent.com>
kvm_vcpu_on_spin() selects a directed-yield target from coarse preempted
and preempted-in-kernel state. It cannot distinguish a vCPU spinning on an
IPI response from a vCPU spinning on a lock, and can therefore yield to an
unrelated vCPU.
Add kvm_vcpu_is_good_yield_candidate(), a priority-ordered filter. Prefer
a confirmed recent IPI receiver of the spinning vCPU, then an
arch-provided pending-interrupt hint, and finally the existing preempted
heuristic with the optional in-kernel filter.
Use the helper in the strict scan before falling back to the existing
directed-yield eligibility checks.
Signed-off-by: Wanpeng Li <wanpengli@tencent.com>
---
virt/kvm/kvm_main.c | 65 ++++++++++++++++++++++++++++++++++++++-------
1 file changed, 55 insertions(+), 10 deletions(-)
diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c
index 2e11c6cfc167..84cbd7a6183f 100644
--- a/virt/kvm/kvm_main.c
+++ b/virt/kvm/kvm_main.c
@@ -3963,12 +3963,51 @@ bool __weak kvm_vcpu_is_ipi_receiver(struct kvm_vcpu *sender,
return false;
}
+/*
+ * Priority-based candidate filter for directed yield.
+ *
+ * 1) Confirmed IPI receiver of @me within the recency window.
+ * This is the highest-confidence signal that selecting @vcpu
+ * may help @me complete its spin-on-IPI-response.
+ * 2) Arch-provided fast pending-interrupt hint (APICv / AVIC /
+ * arch_dy_has_pending_interrupt()). Covers cases where IPI
+ * tracking was bypassed by hardware acceleration.
+ * 3) Legacy preempted fallback, with the existing optional
+ * in-kernel filter when @yield_to_kernel_mode is set.
+ *
+ * Returning false asks kvm_vcpu_on_spin() to skip @vcpu in the
+ * strict (first) round; the relaxed (second) round applies only a
+ * vcpu->preempted check.
+ */
+static bool kvm_vcpu_is_good_yield_candidate(struct kvm_vcpu *me,
+ struct kvm_vcpu *vcpu,
+ bool yield_to_kernel_mode)
+{
+ /* Priority 1: confirmed recent IPI receiver. */
+ if (kvm_vcpu_is_ipi_receiver(me, vcpu))
+ return true;
+
+ /* Priority 2: arch-specific pending-interrupt hint. */
+ if (kvm_arch_dy_has_pending_interrupt(vcpu))
+ return true;
+
+ /* Priority 3: preempted, with optional in-kernel requirement. */
+ if (!READ_ONCE(vcpu->preempted))
+ return false;
+
+ if (yield_to_kernel_mode && !kvm_arch_vcpu_preempted_in_kernel(vcpu))
+ return false;
+
+ return true;
+}
+
void kvm_vcpu_on_spin(struct kvm_vcpu *me, bool yield_to_kernel_mode)
{
int nr_vcpus, start, i, idx, yielded;
struct kvm *kvm = me->kvm;
struct kvm_vcpu *vcpu;
int try = 3;
+ bool first_round = true;
nr_vcpus = atomic_read(&kvm->online_vcpus);
if (nr_vcpus < 2)
@@ -4010,16 +4049,21 @@ void kvm_vcpu_on_spin(struct kvm_vcpu *me, bool yield_to_kernel_mode)
if (kvm_vcpu_is_blocking(vcpu) && !vcpu_dy_runnable(vcpu))
continue;
- /*
- * Treat the target vCPU as being in-kernel if it has a pending
- * interrupt, as the vCPU trying to yield may be spinning
- * waiting on IPI delivery, i.e. the target vCPU is in-kernel
- * for the purposes of directed yield.
- */
- if (READ_ONCE(vcpu->preempted) && yield_to_kernel_mode &&
- !kvm_arch_dy_has_pending_interrupt(vcpu) &&
- !kvm_arch_vcpu_preempted_in_kernel(vcpu))
- continue;
+ if (first_round) {
+ /* Strict round: IPI-aware and legacy preempted filters. */
+ if (!kvm_vcpu_is_good_yield_candidate(me, vcpu,
+ yield_to_kernel_mode))
+ continue;
+ } else {
+ /*
+ * Relaxed round: only require preempted. This is the
+ * safety net for missed IPI tracking (e.g. APICv) or
+ * transient runnable-set changes since the strict
+ * scan.
+ */
+ if (!READ_ONCE(vcpu->preempted))
+ continue;
+ }
if (!kvm_vcpu_eligible_for_directed_yield(vcpu))
continue;
@@ -4032,6 +4076,7 @@ void kvm_vcpu_on_spin(struct kvm_vcpu *me, bool yield_to_kernel_mode)
break;
}
}
+
kvm_vcpu_set_in_spin_loop(me, false);
/* Ensure vcpu is not eligible during next spinloop */
--
2.43.0
next prev parent reply other threads:[~2026-06-12 1:34 UTC|newest]
Thread overview: 22+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-06-12 1:33 [PATCH v3 00/10] sched/fair, KVM: Semantics-aware directed yield for oversubscribed KVM Wanpeng Li
2026-06-12 1:33 ` [PATCH v3 01/10] sched/fair: Add EEVDF lag credit primitive for nominated next-buddy Wanpeng Li
2026-06-12 1:49 ` sashiko-bot
2026-06-12 5:34 ` K Prateek Nayak
2026-06-12 1:33 ` [PATCH v3 02/10] sched/fair: Credit a persistent, queue-depth-scaled vlag margin Wanpeng Li
2026-06-12 1:53 ` sashiko-bot
2026-06-12 6:07 ` K Prateek Nayak
2026-06-12 1:33 ` [PATCH v3 03/10] sched/fair: Credit queued next-buddy via canonical requeue Wanpeng Li
2026-06-12 1:55 ` sashiko-bot
2026-06-12 1:33 ` [PATCH v3 04/10] sched/fair: Credit nominated next-buddy in yield_to_task_fair() Wanpeng Li
2026-06-12 1:54 ` sashiko-bot
2026-06-12 1:33 ` [PATCH v3 05/10] sched/fair: Force a local resched on yield_to() so the buddy is picked Wanpeng Li
2026-06-12 1:50 ` sashiko-bot
2026-06-12 1:33 ` [PATCH v3 06/10] KVM: x86: Add IPI tracking infrastructure for directed yield Wanpeng Li
2026-06-12 1:33 ` [PATCH v3 07/10] KVM: x86/lapic: Track unicast fixed IPI delivery Wanpeng Li
2026-06-12 1:33 ` [PATCH v3 08/10] KVM: x86/lapic: Clear IPI tracking on matching-vector EOI Wanpeng Li
2026-06-12 3:46 ` sashiko-bot
2026-06-12 1:33 ` Wanpeng Li [this message]
2026-06-12 1:48 ` [PATCH v3 09/10] KVM: Add IPI-aware directed-yield candidate selection sashiko-bot
2026-06-12 1:33 ` [PATCH v3 10/10] KVM: Add relaxed preempted-only fallback for directed yield Wanpeng Li
2026-06-12 5:17 ` [PATCH v3 00/10] sched/fair, KVM: Semantics-aware directed yield for oversubscribed KVM K Prateek Nayak
2026-06-12 9:43 ` Shrikanth Hegde
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=20260612013355.59231-10-kernellwp@gmail.com \
--to=kernellwp@gmail.com \
--cc=borntraeger@linux.ibm.com \
--cc=juri.lelli@redhat.com \
--cc=kprateek.nayak@amd.com \
--cc=kvm@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=mingo@redhat.com \
--cc=pbonzini@redhat.com \
--cc=peterz@infradead.org \
--cc=richie@linux.ibm.com \
--cc=rostedt@goodmis.org \
--cc=seanjc@google.com \
--cc=tglx@linutronix.de \
--cc=vincent.guittot@linaro.org \
--cc=wanpengli@tencent.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 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.