From: Sean Christopherson <seanjc@google.com>
To: John Stultz <jstultz@google.com>
Cc: "Paolo Bonzini" <pbonzini@redhat.com>,
kvm@vger.kernel.org, "Peter Zijlstra" <peterz@infradead.org>,
"Frederic Weisbecker" <fweisbec@gmail.com>,
"Andy Lutomirski" <luto@kernel.org>,
"Borislav Petkov" <bp@suse.de>,
"Jim Mattson" <jmattson@google.com>,
"Alex Bennée" <alex.bennee@linaro.org>,
"Will Deacon" <will@kernel.org>,
"Thomas Gleixner" <tglx@linutronix.de>,
"Dave Hansen" <dave.hansen@linux.intel.com>,
LKML <linux-kernel@vger.kernel.org>,
kernel-team@android.com
Subject: Re: BUG: Occasional unexpected DR6 value seen with nested virtualization on x86
Date: Wed, 22 Jan 2025 16:32:21 -0800 [thread overview]
Message-ID: <Z5GOFVFO6ocd1sli@google.com> (raw)
In-Reply-To: <CANDhNCogn0KogQ6HQJ0+XDwoT4QQFGmqfvTJmtmi65bo=zK=9w@mail.gmail.com>
On Wed, Jan 22, 2025, John Stultz wrote:
> On Wed, Jan 22, 2025 at 12:55 PM Sean Christopherson <seanjc@google.com> wrote:
> > On Tue, Jan 21, 2025, John Stultz wrote:
> > @@ -5043,6 +5041,7 @@ static struct kvm_x86_ops svm_x86_ops __initdata = {
> > .set_idt = svm_set_idt,
> > .get_gdt = svm_get_gdt,
> > .set_gdt = svm_set_gdt,
> > + .set_dr6 = svm_set_dr6,
>
>
> Just fyi, to get this to build (svm_set_dr6 takes a *svm not a *vcpu)
> I needed to create a little wrapper to get the types right:
>
> static void svm_set_dr6_vcpu(struct kvm_vcpu *vcpu, unsigned long value)
> {
> struct vcpu_svm *svm = to_svm(vcpu);
> svm_set_dr6(svm, value);
> }
Heh, yeah, I discovered as much when I tried to build wht my more generic kconfig.
> But otherwise, this looks like it has fixed the issue! I've not been
> able to trip a failure with the bionic ptrace test, nor with the debug
> test in kvm-unit-tests, both running in loops for several minutes.
FWIW, I ran the testcase in L2 for ~45 minutes and saw one failure ~3 minutes in,
but unfortunately I didn't have any tracing running so I have zero insight into
what went wrong. I'm fairly certain the failure was due to running an unpatched
kernel in L1, i.e. that I hit the ultra-rare scenario where an L2=>L1 fastpath
exit between the #DB and read from DR6 clobbered hardware DR6.
For giggle and extra confidence, I hacked KVM to emulate HLT as a nop in the
fastpath, and verified failure (and the fix) in a non-nested setup with the below
selftest, on both AMD and Intel.
Sadly, KVM doesn't handle many exits in the fastpath on AMD, so having a regression
test that isn't Intel-specific isn't really possible at the momemnt. I'm mildly
tempted to use testing as an excuse to handle some CPUID emulation in the fastpath,
as Linux userspace does a _lot_ of CPUID, e.g. a kernel build generates tens of
thousands of CPUID exits.
Anyways, this all makes me confident in the fix. I'll post it properly tomorrow.
diff --git a/tools/testing/selftests/kvm/x86/debug_regs.c b/tools/testing/selftests/kvm/x86/debug_regs.c
index 2d814c1d1dc4..a34b65052f4e 100644
--- a/tools/testing/selftests/kvm/x86/debug_regs.c
+++ b/tools/testing/selftests/kvm/x86/debug_regs.c
@@ -22,11 +22,25 @@ extern unsigned char sw_bp, hw_bp, write_data, ss_start, bd_start;
static void guest_code(void)
{
+ unsigned long val = 0xffff0ffful;
+
/* Create a pending interrupt on current vCPU */
x2apic_enable();
x2apic_write_reg(APIC_ICR, APIC_DEST_SELF | APIC_INT_ASSERT |
APIC_DM_FIXED | IRQ_VECTOR);
+ /*
+ * Debug Register Interception tests.
+ */
+ asm volatile("mov %%rax, %%dr6\n\t"
+ "hlt\n\t"
+ "mov %%dr6, %%rax\n\t"
+ : "+r" (val));
+
+ __GUEST_ASSERT(val == 0xffff0ffful,
+ "Wanted DR6 = 0xffff0ffful, got %lx\n", val);
+ GUEST_SYNC(0);
+
/*
* Software BP tests.
*
@@ -103,6 +117,9 @@ int main(void)
vm = vm_create_with_one_vcpu(&vcpu, guest_code);
run = vcpu->run;
+ vcpu_run(vcpu);
+ TEST_ASSERT_EQ(get_ucall(vcpu, NULL), UCALL_SYNC);
+
/* Test software BPs - int3 */
memset(&debug, 0, sizeof(debug));
debug.control = KVM_GUESTDBG_ENABLE | KVM_GUESTDBG_USE_SW_BP;
prev parent reply other threads:[~2025-01-23 0:32 UTC|newest]
Thread overview: 7+ messages / expand[flat|nested] mbox.gz Atom feed top
2025-01-22 6:02 BUG: Occasional unexpected DR6 value seen with nested virtualization on x86 John Stultz
2025-01-22 9:00 ` Paolo Bonzini
2025-01-22 16:55 ` Jim Mattson
2025-01-22 18:24 ` John Stultz
2025-01-22 20:55 ` Sean Christopherson
2025-01-22 23:00 ` John Stultz
2025-01-23 0:32 ` Sean Christopherson [this message]
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=Z5GOFVFO6ocd1sli@google.com \
--to=seanjc@google.com \
--cc=alex.bennee@linaro.org \
--cc=bp@suse.de \
--cc=dave.hansen@linux.intel.com \
--cc=fweisbec@gmail.com \
--cc=jmattson@google.com \
--cc=jstultz@google.com \
--cc=kernel-team@android.com \
--cc=kvm@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=luto@kernel.org \
--cc=pbonzini@redhat.com \
--cc=peterz@infradead.org \
--cc=tglx@linutronix.de \
--cc=will@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.