public inbox for linux-kernel@vger.kernel.org
 help / color / mirror / Atom feed
* Testcases for "eip canonical" kvm fixes?
@ 2015-03-10 18:37 Denys Vlasenko
  2015-03-11 13:03 ` Nadav Amit
  0 siblings, 1 reply; 5+ messages in thread
From: Denys Vlasenko @ 2015-03-10 18:37 UTC (permalink / raw)
  To: Nadav Amit; +Cc: Paolo Bonzini, X86 ML, Linux Kernel Mailing List

Hi,

I wonder how did you trigger the bug for your following fix?


commit 234f3ce485d54017f15cf5e0699cff4100121601
Author: Nadav Amit <namit@cs.technion.ac.il>
Date:   Thu Sep 18 22:39:38 2014 +0300

    KVM: x86: Emulator fixes for eip canonical checks on near branches

    Before changing rip (during jmp, call, ret, etc.) the target
should be asserted
    to be canonical one, as real CPUs do.  During sysret, both target
rsp and rip
    should be canonical. If any of these values is noncanonical, a #GP exception
    should occur.  The exception to this rule are syscall and sysenter
instructions
    in which the assigned rip is checked during the assignment to the relevant
    MSRs.

    This patch fixes the emulator to behave as real CPUs do for near branches.
    Far branches are handled by the next patch.


Non-canonical addresses result in #GP, but KVM doesn't
intercept guest #GP, according to code below:

static void update_exception_bitmap(struct kvm_vcpu *vcpu)
{
        u32 eb;

        eb = (1u << PF_VECTOR) | (1u << UD_VECTOR) | (1u << MC_VECTOR) |
             (1u << NM_VECTOR) | (1u << DB_VECTOR);
        if ((vcpu->guest_debug &
             (KVM_GUESTDBG_ENABLE | KVM_GUESTDBG_USE_SW_BP)) ==
            (KVM_GUESTDBG_ENABLE | KVM_GUESTDBG_USE_SW_BP))
                eb |= 1u << BP_VECTOR;
        if (to_vmx(vcpu)->rmode.vm86_active)
                eb = ~0;
        if (enable_ept)
                eb &= ~(1u << PF_VECTOR); /* bypass_guest_pf = 0 */
        if (vcpu->fpu_active)
                eb &= ~(1u << NM_VECTOR);

        /* When we are running a nested L2 guest and L1 specified for it a
         * certain exception bitmap, we must trap the same exceptions and pass
         * them to L1. When running L2, we will only handle the exceptions
         * specified above if L1 did not want them.
         */
        if (is_guest_mode(vcpu))
                eb |= get_vmcs12(vcpu)->exception_bitmap;

        vmcs_write32(EXCEPTION_BITMAP, eb);
}


That what seems to be happening to me when I try to reproduce
the bug on unpatched kernel: CPU simply emulates #GP, and
everything works as it should.

In particular:
I'm trying "RET far" with noncanonical address on stack (and valid CS).
I expect that buggy behavior would be that #GP happens
after "RET far". Instead, #GP happens _on_ "RET far" insn.

-- 
vda

^ permalink raw reply	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2015-03-11 14:16 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2015-03-10 18:37 Testcases for "eip canonical" kvm fixes? Denys Vlasenko
2015-03-11 13:03 ` Nadav Amit
2015-03-11 13:27   ` Denys Vlasenko
2015-03-11 13:50     ` Nadav Amit
2015-03-11 14:12     ` Paolo Bonzini

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox