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

[Xen-changelog] [xen-unstable] fix vmce MCi_ADDR/MCi_MISC wrmsr bug


  • To: xen-changelog@xxxxxxxxxxxxxxxxxxx
  • From: Xen patchbot-unstable <patchbot@xxxxxxx>
  • Date: Mon, 14 May 2012 16:32:16 +0000
  • Delivery-date: Mon, 14 May 2012 16:32:21 +0000
  • List-id: "Change log for Mercurial \(receive only\)" <xen-changelog.lists.xen.org>

# HG changeset patch
# User Liu, Jinsong <jinsong.liu@xxxxxxxxx>
# Date 1336476984 -7200
# Node ID 8a86d841e6d42fbffc9e20d3028875dd4990882d
# Parent  ea7c9cabd7ad9ccbdf0c2d1a71e479b69d24ea5b
fix vmce MCi_ADDR/MCi_MISC wrmsr bug

This patch fixes a bug related to wrmsr vmce MCi_ADDR/MCi_MISC
registers, since they are not read-only.

Intel SDM recommanded os mce driver clear MCi_ADDR/MCi_MISC, so guest
MCE driver may clear MCi_ADDR/MCi_MISC registers. In such case, old
vmce wrmsr logic would generate a #GP fault in guest MCE context,
causing the guest to crash.

When wrmsr MCi_ADDR/MCi_MISC, writing all 1s will cause #GP.

Signed-off-by: Liu, Jinsong <jinsong.liu@xxxxxxxxx>
Signed-off-by: Jan Beulich <jbeulich@xxxxxxxx>
Committed-by: Jan Beulich <jbeulich@xxxxxxxx>
---


diff -r ea7c9cabd7ad -r 8a86d841e6d4 xen/arch/x86/cpu/mcheck/vmce.c
--- a/xen/arch/x86/cpu/mcheck/vmce.c    Tue May 08 13:34:14 2012 +0200
+++ b/xen/arch/x86/cpu/mcheck/vmce.c    Tue May 08 13:36:24 2012 +0200
@@ -209,6 +209,14 @@ static int bank_mce_wrmsr(struct vcpu *v
     struct domain_mca_msrs *vmce = dom_vmce(v->domain);
     struct bank_entry *entry = NULL;
 
+    /* Give the first entry of the list, it corresponds to current
+     * vMCE# injection. When vMCE# is finished processing by the
+     * the guest, this node will be deleted.
+     * Only error bank is written. Non-error banks simply return.
+     */
+    if ( !list_empty(&vmce->impact_header) )
+        entry = list_entry(vmce->impact_header.next, struct bank_entry, list);
+
     switch ( msr & (MSR_IA32_MC0_CTL | 3) )
     {
     case MSR_IA32_MC0_CTL:
@@ -216,17 +224,9 @@ static int bank_mce_wrmsr(struct vcpu *v
             vmce->mci_ctl[bank] = val;
         break;
     case MSR_IA32_MC0_STATUS:
-        /* Give the first entry of the list, it corresponds to current
-         * vMCE# injection. When vMCE# is finished processing by the
-         * the guest, this node will be deleted.
-         * Only error bank is written. Non-error banks simply return.
-         */
-        if ( !list_empty(&vmce->impact_header) )
+        if ( entry && (entry->bank == bank) )
         {
-            entry = list_entry(vmce->impact_header.next,
-                               struct bank_entry, list);
-            if ( entry->bank == bank )
-                entry->mci_status = val;
+            entry->mci_status = val;
             mce_printk(MCE_VERBOSE,
                        "MCE: wr MC%u_STATUS %"PRIx64" in vMCE#\n",
                        bank, val);
@@ -236,12 +236,38 @@ static int bank_mce_wrmsr(struct vcpu *v
                        "MCE: wr MC%u_STATUS %"PRIx64"\n", bank, val);
         break;
     case MSR_IA32_MC0_ADDR:
-        mce_printk(MCE_QUIET, "MCE: MC%u_ADDR is read-only\n", bank);
-        ret = -1;
+        if ( !~val )
+        {
+            mce_printk(MCE_QUIET,
+                       "MCE: wr MC%u_ADDR with all 1s will cause #GP\n", bank);
+            ret = -1;
+        }
+        else if ( entry && (entry->bank == bank) )
+        {
+            entry->mci_addr = val;
+            mce_printk(MCE_VERBOSE,
+                       "MCE: wr MC%u_ADDR %"PRIx64" in vMCE#\n", bank, val);
+        }
+        else
+            mce_printk(MCE_VERBOSE,
+                       "MCE: wr MC%u_ADDR %"PRIx64"\n", bank, val);
         break;
     case MSR_IA32_MC0_MISC:
-        mce_printk(MCE_QUIET, "MCE: MC%u_MISC is read-only\n", bank);
-        ret = -1;
+        if ( !~val )
+        {
+            mce_printk(MCE_QUIET,
+                       "MCE: wr MC%u_MISC with all 1s will cause #GP\n", bank);
+            ret = -1;
+        }
+        else if ( entry && (entry->bank == bank) )
+        {
+            entry->mci_misc = val;
+            mce_printk(MCE_VERBOSE,
+                       "MCE: wr MC%u_MISC %"PRIx64" in vMCE#\n", bank, val);
+        }
+        else
+            mce_printk(MCE_VERBOSE,
+                       "MCE: wr MC%u_MISC %"PRIx64"\n", bank, val);
         break;
     default:
         switch ( boot_cpu_data.x86_vendor )

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.