[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Bug#599507: KVM: SVM: Fix wrong intercept masks on 32 bit



Package: linux-2.6.32
Severity: normal

When trying to reboot an ia32 guest, an ia32 kvm running on an Amd64
cpu reports the following error:
 kvm: unhandled exit ffffffff
 kvm_run returned -22

This bug was fixed for linux-2.6.34 but is still present in 2.6.32.
<http://git.kernel.org/?p=linux/kernel/git/torvalds/linux-2.6.git;a=commit;h=061e2fd16863009c8005b4b5fdfb75c7215c0b99>
> KVM: SVM: Fix wrong intercept masks on 32 bit
> 
> This patch makes KVM on 32 bit SVM working again by
> correcting the masks used for iret interception. With the
> wrong masks the upper 32 bits of the intercepts are masked
> out which leaves vmrun unintercepted. This is not legal on
> svm and the vmrun fails.
> Bug was introduced by commits 95ba827313 and 3cfc3092.

It only happens on Amd cpus, Intel cpus are unaffected.

Please conside applying this patch to the 2.6.32 stable branch as well.

Sincerely
Philipp Hahn
-- System Information:
Debian Release: 5.0.1
Architecture: amd64 (x86_64)
Shell:  /bin/sh linked to /bin/bash
Kernel: Linux 2.6.32-ucs11-amd64
Locale: LANG=de_DE.UTF-8, LC_CTYPE=de_DE.UTF-8 (charmap=UTF-8)
commit 061e2fd16863009c8005b4b5fdfb75c7215c0b99
Author: Joerg Roedel <joerg.roedel@amd.com>
Date:   Wed May 5 16:04:43 2010 +0200

    KVM: SVM: Fix wrong intercept masks on 32 bit
    
    This patch makes KVM on 32 bit SVM working again by
    correcting the masks used for iret interception. With the
    wrong masks the upper 32 bits of the intercepts are masked
    out which leaves vmrun unintercepted. This is not legal on
    svm and the vmrun fails.
    Bug was introduced by commits 95ba827313 and 3cfc3092.
    
    Cc: Jan Kiszka <jan.kiszka@siemens.com>
    Cc: Gleb Natapov <gleb@redhat.com>
    Cc: stable@kernel.org
    Signed-off-by: Joerg Roedel <joerg.roedel@amd.com>
    Signed-off-by: Avi Kivity <avi@redhat.com>

diff --git a/arch/x86/kvm/svm.c b/arch/x86/kvm/svm.c
index 2ba5820..737361f 100644
--- a/arch/x86/kvm/svm.c
+++ b/arch/x86/kvm/svm.c
@@ -2067,7 +2067,7 @@ static int cpuid_interception(struct vcpu_svm *svm)
 static int iret_interception(struct vcpu_svm *svm)
 {
 	++svm->vcpu.stat.nmi_window_exits;
-	svm->vmcb->control.intercept &= ~(1UL << INTERCEPT_IRET);
+	svm->vmcb->control.intercept &= ~(1ULL << INTERCEPT_IRET);
 	svm->vcpu.arch.hflags |= HF_IRET_MASK;
 	return 1;
 }
@@ -2479,7 +2479,7 @@ static void svm_inject_nmi(struct kvm_vcpu *vcpu)
 
 	svm->vmcb->control.event_inj = SVM_EVTINJ_VALID | SVM_EVTINJ_TYPE_NMI;
 	vcpu->arch.hflags |= HF_NMI_MASK;
-	svm->vmcb->control.intercept |= (1UL << INTERCEPT_IRET);
+	svm->vmcb->control.intercept |= (1ULL << INTERCEPT_IRET);
 	++vcpu->stat.nmi_injections;
 }
 
@@ -2539,10 +2539,10 @@ static void svm_set_nmi_mask(struct kvm_vcpu *vcpu, bool masked)
 
 	if (masked) {
 		svm->vcpu.arch.hflags |= HF_NMI_MASK;
-		svm->vmcb->control.intercept |= (1UL << INTERCEPT_IRET);
+		svm->vmcb->control.intercept |= (1ULL << INTERCEPT_IRET);
 	} else {
 		svm->vcpu.arch.hflags &= ~HF_NMI_MASK;
-		svm->vmcb->control.intercept &= ~(1UL << INTERCEPT_IRET);
+		svm->vmcb->control.intercept &= ~(1ULL << INTERCEPT_IRET);
 	}
 }
 

Attachment: signature.asc
Description: Digital signature


Reply to: