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

[Xen-changelog] [xen-unstable] hvm svm: Avoid intercepts when accessing a number of architectural MSRs.



# HG changeset patch
# User kfraser@xxxxxxxxxxxxxxxxxxxxx
# Date 1175684248 -3600
# Node ID bc43ac9631e3cca3c6ba8467d028d252584dd502
# Parent  c278b1c580db2a5d04066b9e2443a49e796e1e73
hvm svm: Avoid intercepts when accessing a number of architectural MSRs.

1. Removes intercept of guest-specific MSRs
MSR_IA32_SYSENTER_{CS,ESP,EIP}, MSR_{L,C,}STAR, MSR_SYSCALL_MASK,
MSR_SHADOW_GS_BASE.

2. Removes code to deal with those intercepts, as well as the
FS/GS-base. Since long_mode_do_msr_read now became essentially a
switch of a single case + default, I removed the entire function and
inlined the remaining single case-statement into the original
MSR-access function.

Signed-off-by: Mats Petersson <mats.petersson@xxxxxxx>
---
 xen/arch/x86/hvm/svm/svm.c  |  125 +-------------------------------------------
 xen/arch/x86/hvm/svm/vmcb.c |    8 ++
 2 files changed, 12 insertions(+), 121 deletions(-)

diff -r c278b1c580db -r bc43ac9631e3 xen/arch/x86/hvm/svm/svm.c
--- a/xen/arch/x86/hvm/svm/svm.c        Wed Apr 04 11:49:37 2007 +0100
+++ b/xen/arch/x86/hvm/svm/svm.c        Wed Apr 04 11:57:28 2007 +0100
@@ -131,66 +131,6 @@ static void svm_store_cpu_guest_regs(
     }
 }
 
-
-static inline int long_mode_do_msr_read(struct cpu_user_regs *regs)
-{
-    u64 msr_content = 0;
-    struct vcpu *v = current;
-    struct vmcb_struct *vmcb = v->arch.hvm_svm.vmcb;
-
-    switch ((u32)regs->ecx)
-    {
-    case MSR_EFER:
-        msr_content = v->arch.hvm_svm.cpu_shadow_efer;
-        break;
-
-#ifdef __x86_64__
-    case MSR_FS_BASE:
-        msr_content = vmcb->fs.base;
-        goto check_long_mode;
-
-    case MSR_GS_BASE:
-        msr_content = vmcb->gs.base;
-        goto check_long_mode;
-
-    case MSR_SHADOW_GS_BASE:
-        msr_content = vmcb->kerngsbase;
-    check_long_mode:
-        if ( !svm_long_mode_enabled(v) )
-        {
-            svm_inject_exception(v, TRAP_gp_fault, 1, 0);
-            return 0;
-        }
-        break;
-#endif
-
-    case MSR_STAR:
-        msr_content = vmcb->star;
-        break;
- 
-    case MSR_LSTAR:
-        msr_content = vmcb->lstar;
-        break;
- 
-    case MSR_CSTAR:
-        msr_content = vmcb->cstar;
-        break;
- 
-    case MSR_SYSCALL_MASK:
-        msr_content = vmcb->sfmask;
-        break;
-    default:
-        return 0;
-    }
-
-    HVM_DBG_LOG(DBG_LEVEL_2, "msr_content: %"PRIx64"\n",
-                msr_content);
-
-    regs->eax = (u32)(msr_content >>  0);
-    regs->edx = (u32)(msr_content >> 32);
-    return 1;
-}
-
 static inline int long_mode_do_msr_write(struct cpu_user_regs *regs)
 {
     u64 msr_content = (u32)regs->eax | ((u64)regs->edx << 32);
@@ -242,52 +182,12 @@ static inline int long_mode_do_msr_write
 
         break;
 
-#ifdef __x86_64__
-    case MSR_FS_BASE:
-    case MSR_GS_BASE:
-    case MSR_SHADOW_GS_BASE:
-        if ( !svm_long_mode_enabled(v) )
-            goto gp_fault;
-
-        if ( !is_canonical_address(msr_content) )
-            goto uncanonical_address;
-
-        if ( ecx == MSR_FS_BASE )
-            vmcb->fs.base = msr_content;
-        else if ( ecx == MSR_GS_BASE )
-            vmcb->gs.base = msr_content;
-        else
-            vmcb->kerngsbase = msr_content;
-        break;
-#endif
- 
-    case MSR_STAR:
-        vmcb->star = msr_content;
-        break;
- 
-    case MSR_LSTAR:
-    case MSR_CSTAR:
-        if ( !is_canonical_address(msr_content) )
-            goto uncanonical_address;
-
-        if ( ecx == MSR_LSTAR )
-            vmcb->lstar = msr_content;
-        else
-            vmcb->cstar = msr_content;
-        break;
- 
-    case MSR_SYSCALL_MASK:
-        vmcb->sfmask = msr_content;
-        break;
-
     default:
         return 0;
     }
 
     return 1;
 
- uncanonical_address:
-    HVM_DBG_LOG(DBG_LEVEL_1, "Not cano address of msr write %x\n", ecx);
  gp_fault:
     svm_inject_exception(v, TRAP_gp_fault, 1, 0);
     return 0;
@@ -2013,22 +1913,14 @@ static inline void svm_do_msr_access(
         case MSR_IA32_TIME_STAMP_COUNTER:
             msr_content = hvm_get_guest_time(v);
             break;
-        case MSR_IA32_SYSENTER_CS:
-            msr_content = vmcb->sysenter_cs;
-            break;
-        case MSR_IA32_SYSENTER_ESP: 
-            msr_content = vmcb->sysenter_esp;
-            break;
-        case MSR_IA32_SYSENTER_EIP:     
-            msr_content = vmcb->sysenter_eip;
-            break;
         case MSR_IA32_APICBASE:
             msr_content = vcpu_vlapic(v)->hw.apic_base_msr;
             break;
+        case MSR_EFER:
+            msr_content = v->arch.hvm_svm.cpu_shadow_efer;
+            break;
+
         default:
-            if (long_mode_do_msr_read(regs))
-                goto done;
-
             if ( rdmsr_hypervisor_regs(ecx, &eax, &edx) ||
                  rdmsr_safe(ecx, eax, edx) == 0 )
             {
@@ -2060,15 +1952,6 @@ static inline void svm_do_msr_access(
         case MSR_IA32_TIME_STAMP_COUNTER:
             hvm_set_guest_time(v, msr_content);
             pt_reset(v);
-            break;
-        case MSR_IA32_SYSENTER_CS:
-            vmcb->sysenter_cs = msr_content;
-            break;
-        case MSR_IA32_SYSENTER_ESP: 
-            vmcb->sysenter_esp = msr_content;
-            break;
-        case MSR_IA32_SYSENTER_EIP:     
-            vmcb->sysenter_eip = msr_content;
             break;
         case MSR_IA32_APICBASE:
             vlapic_msr_set(vcpu_vlapic(v), msr_content);
diff -r c278b1c580db -r bc43ac9631e3 xen/arch/x86/hvm/svm/vmcb.c
--- a/xen/arch/x86/hvm/svm/vmcb.c       Wed Apr 04 11:49:37 2007 +0100
+++ b/xen/arch/x86/hvm/svm/vmcb.c       Wed Apr 04 11:57:28 2007 +0100
@@ -141,6 +141,14 @@ static int construct_vmcb(struct vcpu *v
 
     disable_intercept_for_msr((char *)arch_svm->msrpm, MSR_FS_BASE);
     disable_intercept_for_msr((char *)arch_svm->msrpm, MSR_GS_BASE);
+    disable_intercept_for_msr((char *)arch_svm->msrpm, MSR_SHADOW_GS_BASE);
+    disable_intercept_for_msr((char *)arch_svm->msrpm, MSR_CSTAR);
+    disable_intercept_for_msr((char *)arch_svm->msrpm, MSR_LSTAR);
+    disable_intercept_for_msr((char *)arch_svm->msrpm, MSR_STAR);
+    disable_intercept_for_msr((char *)arch_svm->msrpm, MSR_SYSCALL_MASK);
+    disable_intercept_for_msr((char *)arch_svm->msrpm, MSR_IA32_SYSENTER_CS);
+    disable_intercept_for_msr((char *)arch_svm->msrpm, MSR_IA32_SYSENTER_ESP);
+    disable_intercept_for_msr((char *)arch_svm->msrpm, MSR_IA32_SYSENTER_EIP);
 
     vmcb->msrpm_base_pa = (u64)virt_to_maddr(arch_svm->msrpm);
     vmcb->iopm_base_pa  = (u64)virt_to_maddr(hvm_io_bitmap);

_______________________________________________
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®.