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

[Xen-changelog] [xen-3.4-testing] AMD OSVW (OS Visible Workaround) for Xen



# HG changeset patch
# User Keith Coleman <keith.coleman@xxxxxxxxxxxxx>
# Date 1324425818 18000
# Node ID 985c41cd52dad9fd77e111904ffdfd71cea39036
# Parent  a9e081fd41aedb1cfe0676e10cad30094dd1fbd1
AMD OSVW (OS Visible Workaround) for Xen

This path enables AMD OSVW (OS Visible Workaround) feature for Xen. New
AMD errata will have a OSVW id assigned in the future. OS is
supposed to check OSVW status MSR to find out whether CPU has a specific
erratum. Legacy errata are also supported in this patch:
traditional family/model/stepping approach will be used if OSVW feature
isn't applicable.  This patch is adapted from Hans Rosenfeld's
patch submitted to Linux kernel.

Signed-off-by: Wei Huang <wei.huang2@xxxxxxx>
Signed-off-by: Hans Rosenfeld <hands.rosenfeld@xxxxxxx>
Acked-by: Jan Beulich <jbeulich@xxxxxxxxxx>
---


diff -r a9e081fd41ae -r 985c41cd52da xen/arch/x86/cpu/amd.c
--- a/xen/arch/x86/cpu/amd.c    Tue Dec 20 19:02:41 2011 -0500
+++ b/xen/arch/x86/cpu/amd.c    Tue Dec 20 19:03:38 2011 -0500
@@ -7,10 +7,10 @@
 #include <asm/io.h>
 #include <asm/msr.h>
 #include <asm/processor.h>
+#include <asm/amd.h>
 #include <asm/hvm/support.h>
 
 #include "cpu.h"
-#include "amd.h"
 
 void start_svm(struct cpuinfo_x86 *c);
 
@@ -156,6 +156,54 @@
 }
 
 /*
+ * Check for the presence of an AMD erratum. Arguments are defined in amd.h 
+ * for each known erratum. Return 1 if erratum is found.
+ */
+int cpu_has_amd_erratum(const struct cpuinfo_x86 *cpu, int osvw, ...) 
+{
+       va_list ap;
+       u32 range;
+       u32 ms;
+       
+       if (cpu->x86_vendor != X86_VENDOR_AMD)
+               return 0;
+
+       va_start(ap, osvw);
+
+       if (osvw) {
+               u16 osvw_id = va_arg(ap, int);
+
+               if (cpu_has(cpu, X86_FEATURE_OSVW)) {
+                       u64 osvw_len;
+                       rdmsrl(MSR_AMD_OSVW_ID_LENGTH, osvw_len);
+
+                       if (osvw_id < osvw_len) {
+                               u64 osvw_bits;
+                               rdmsrl(MSR_AMD_OSVW_STATUS + (osvw_id >> 6), 
+                                      osvw_bits);
+
+                               va_end(ap);
+                               return (osvw_bits >> (osvw_id & 0x3f)) & 0x01;
+                       }
+               }
+       }
+
+       /* OSVW unavailable or ID unknown, match family-model-stepping range */
+       ms = (cpu->x86_model << 8) | cpu->x86_mask;
+       while ((range = va_arg(ap, int))) {
+               if ((cpu->x86 == AMD_MODEL_RANGE_FAMILY(range)) &&
+                   (ms >= AMD_MODEL_RANGE_START(range)) &&
+                   (ms <= AMD_MODEL_RANGE_END(range))) {
+                       va_end(ap);
+                       return 1;
+               }
+       }
+
+       va_end(ap);
+       return 0;
+}
+
+/*
  * amd_flush_filter={on,off}. Forcibly Enable or disable the TLB flush
  * filter on AMD 64-bit processors.
  */
diff -r a9e081fd41ae -r 985c41cd52da xen/arch/x86/hvm/svm/asid.c
--- a/xen/arch/x86/hvm/svm/asid.c       Tue Dec 20 19:02:41 2011 -0500
+++ b/xen/arch/x86/hvm/svm/asid.c       Tue Dec 20 19:03:38 2011 -0500
@@ -21,6 +21,7 @@
 #include <xen/lib.h>
 #include <xen/perfc.h>
 #include <asm/hvm/svm/asid.h>
+#include <asm/amd.h>
 
 /*
  * This is the interface to SVM's ASID management.  ASIDs partition the
@@ -96,9 +97,7 @@
     data->max_asid = nasids - 1;
 
     /* Check if we can use ASIDs. */
-    data->erratum170 =
-        !((c->x86 == 0x10) ||
-          ((c->x86 == 0xf) && (c->x86_model >= 0x68) && (c->x86_mask >= 1)));
+    data->erratum170 = cpu_has_amd_erratum(c, AMD_ERRATUM_170);
 
     printk("AMD SVM: ASIDs %s \n",
            (data->erratum170 ? "disabled." : "enabled."));
diff -r a9e081fd41ae -r 985c41cd52da xen/arch/x86/hvm/svm/svm.c
--- a/xen/arch/x86/hvm/svm/svm.c        Tue Dec 20 19:02:41 2011 -0500
+++ b/xen/arch/x86/hvm/svm/svm.c        Tue Dec 20 19:03:38 2011 -0500
@@ -33,6 +33,7 @@
 #include <asm/regs.h>
 #include <asm/cpufeature.h>
 #include <asm/processor.h>
+#include <asm/amd.h>
 #include <asm/types.h>
 #include <asm/debugreg.h>
 #include <asm/msr.h>
@@ -844,8 +845,8 @@
 {
     uint64_t msr_content;
 
-    /* only family 10h is affected */
-    if ( c->x86 != 0x10 )
+    /* check whether CPU is affected */
+    if ( !cpu_has_amd_erratum(c, AMD_ERRATUM_383) )
         return;
 
     rdmsrl(MSR_AMD64_DC_CFG, msr_content);
diff -r a9e081fd41ae -r 985c41cd52da xen/include/asm-x86/msr-index.h
--- a/xen/include/asm-x86/msr-index.h   Tue Dec 20 19:02:41 2011 -0500
+++ b/xen/include/asm-x86/msr-index.h   Tue Dec 20 19:03:38 2011 -0500
@@ -248,6 +248,10 @@
 #define MSR_AMD_PATCHLEVEL             0x0000008b
 #define MSR_AMD_PATCHLOADER            0xc0010020
 
+/* AMD OS Visible Workaround MSRs */
+#define MSR_AMD_OSVW_ID_LENGTH          0xc0010140
+#define MSR_AMD_OSVW_STATUS             0xc0010141
+
 /* K6 MSRs */
 #define MSR_K6_EFER                    0xc0000080
 #define MSR_K6_STAR                    0xc0000081

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
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®.