[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <20240522001817.619072-21-dwmw2@infradead.org>
Date: Wed, 22 May 2024 01:17:15 +0100
From: David Woodhouse <dwmw2@...radead.org>
To: kvm@...r.kernel.org
Cc: Paolo Bonzini <pbonzini@...hat.com>,
Jonathan Corbet <corbet@....net>,
Sean Christopherson <seanjc@...gle.com>,
Thomas Gleixner <tglx@...utronix.de>,
Ingo Molnar <mingo@...hat.com>,
Borislav Petkov <bp@...en8.de>,
Dave Hansen <dave.hansen@...ux.intel.com>,
x86@...nel.org,
"H. Peter Anvin" <hpa@...or.com>,
Paul Durrant <paul@....org>,
Peter Zijlstra <peterz@...radead.org>,
Juri Lelli <juri.lelli@...hat.com>,
Vincent Guittot <vincent.guittot@...aro.org>,
Dietmar Eggemann <dietmar.eggemann@....com>,
Steven Rostedt <rostedt@...dmis.org>,
Ben Segall <bsegall@...gle.com>,
Mel Gorman <mgorman@...e.de>,
Daniel Bristot de Oliveira <bristot@...hat.com>,
Valentin Schneider <vschneid@...hat.com>,
Shuah Khan <shuah@...nel.org>,
linux-doc@...r.kernel.org,
linux-kernel@...r.kernel.org,
jalliste@...zon.co.uk,
sveith@...zon.de,
zide.chen@...el.com,
Dongli Zhang <dongli.zhang@...cle.com>,
Chenyi Qiang <chenyi.qiang@...el.com>
Subject: [RFC PATCH v3 20/21] KVM: x86/xen: Prevent runstate times from becoming negative
From: David Woodhouse <dwmw@...zon.co.uk>
When kvm_xen_update_runstate() is invoked to set a vCPU's runstate, the
time spent in the previous runstate is accounted. This is based on the
delta between the current KVM clock time, and the previous value stored
in vcpu->arch.xen.runstate_entry_time.
If the KVM clock goes backwards, that delta will be negative. Or, since
it's an unsigned 64-bit integer, very *large*. Linux guests deal with
that particularly badly, reporting 100% steal time for ever more (well,
for *centuries* at least, until the delta has been consumed).
So when a negative delta is detected, just refrain from updating the
runstates until the KVM clock catches up with runstate_entry_time again.
The userspace APIs for setting the runstate times do not allow them to
be set past the current KVM clock, but userspace can still adjust the
KVM clock *after* setting the runstate times, which would cause this
situation to occur.
Signed-off-by: David Woodhouse <dwmw@...zon.co.uk>
---
arch/x86/kvm/xen.c | 18 ++++++++++++++----
1 file changed, 14 insertions(+), 4 deletions(-)
diff --git a/arch/x86/kvm/xen.c b/arch/x86/kvm/xen.c
index 014048c22652..3d4111de4472 100644
--- a/arch/x86/kvm/xen.c
+++ b/arch/x86/kvm/xen.c
@@ -538,24 +538,34 @@ void kvm_xen_update_runstate(struct kvm_vcpu *v, int state)
{
struct kvm_vcpu_xen *vx = &v->arch.xen;
u64 now = get_kvmclock_ns(v->kvm);
- u64 delta_ns = now - vx->runstate_entry_time;
u64 run_delay = current->sched_info.run_delay;
+ s64 delta_ns = now - vx->runstate_entry_time;
+ s64 steal_ns = run_delay - vx->last_steal;
if (unlikely(!vx->runstate_entry_time))
vx->current_runstate = RUNSTATE_offline;
+ vx->last_steal = run_delay;
+
+ /*
+ * If KVM clock time went backwards, stop updating until it
+ * catches up (or the runstates are reset by userspace).
+ */
+ if (delta_ns < 0)
+ return;
+
/*
* Time waiting for the scheduler isn't "stolen" if the
* vCPU wasn't running anyway.
*/
- if (vx->current_runstate == RUNSTATE_running) {
- u64 steal_ns = run_delay - vx->last_steal;
+ if (vx->current_runstate == RUNSTATE_running && steal_ns > 0) {
+ if (steal_ns > delta_ns)
+ steal_ns = delta_ns;
delta_ns -= steal_ns;
vx->runstate_times[RUNSTATE_runnable] += steal_ns;
}
- vx->last_steal = run_delay;
vx->runstate_times[vx->current_runstate] += delta_ns;
vx->current_runstate = state;
--
2.44.0
Powered by blists - more mailing lists