Add MSR Bitmap support in VMX so that some execution of RDMSR or WRMSR won't cause a VM exit.
Signed-off-by: Sheng Yang <[EMAIL PROTECTED]> Signed-off-by: Qing He <[EMAIL PROTECTED]> --- drivers/kvm/vmx.c | 44 +++++++++++++++++++++++++++++++++++++++++++- drivers/kvm/vmx.h | 3 +++ 2 files changed, 46 insertions(+), 1 deletions(-) diff --git a/drivers/kvm/vmx.c b/drivers/kvm/vmx.c index 3b901fe..bebe0d4 100644 --- a/drivers/kvm/vmx.c +++ b/drivers/kvm/vmx.c @@ -71,6 +71,7 @@ static DEFINE_PER_CPU(struct vmcs *, current_vmcs); static struct page *vmx_io_bitmap_a; static struct page *vmx_io_bitmap_b; +static struct page *vmx_msr_bitmap; #define EFER_SAVE_RESTORE_BITS ((u64)EFER_SCE) @@ -867,7 +868,7 @@ static __init int setup_vmcs_config(struct vmcs_config *vmcs_conf) CPU_BASED_USE_IO_BITMAPS | CPU_BASED_MOV_DR_EXITING | CPU_BASED_USE_TSC_OFFSETING; - opt = 0; + opt = CPU_BASED_USE_MSR_BITMAPS; if (adjust_vmx_controls(min, opt, MSR_IA32_VMX_PROCBASED_CTLS, &_cpu_based_exec_control) < 0) return -EIO; @@ -1426,6 +1427,10 @@ static int vmx_vcpu_setup(struct vcpu_vmx *vmx) vmcs_write64(IO_BITMAP_A, page_to_phys(vmx_io_bitmap_a)); vmcs_write64(IO_BITMAP_B, page_to_phys(vmx_io_bitmap_b)); + /* MSR bitmap */ + if (cpu_has_vmx_msr_bitmap) + vmcs_write64(MSR_BITMAP, page_to_phys(vmx_msr_bitmap)); + guest_write_tsc(0); vmcs_write64(VMCS_LINK_POINTER, -1ull); /* 22.3.1.5 */ @@ -2424,6 +2429,19 @@ static void __init vmx_check_processor_compat(void *rtn) } } +static void __init disable_intercept_for_msr(u32 msr, void *msr_bitmap_va) +{ + /* See Intel PRM Vol. 3, 20.6.9 (MSR-Bitmap Address). */ + if (msr <= 0x1fff) { /* read and write bitmaps for low MSRs */ + __clear_bit(msr, msr_bitmap_va + 0x000); + __clear_bit(msr, msr_bitmap_va + 0x800); + } else if ((msr >= 0xc0000000) && (msr <= 0xc0001fff)) { + msr &= 0x1fff; /* read and write bitmaps for high MSRs */ + __clear_bit(msr, msr_bitmap_va + 0x400); + __clear_bit(msr, msr_bitmap_va + 0xc00); + } +} + static struct kvm_arch_ops vmx_arch_ops = { .cpu_has_kvm_support = cpu_has_kvm_support, .disabled_by_bios = vmx_disabled_by_bios, @@ -2505,6 +2523,28 @@ static int __init vmx_init(void) if (r) goto out1; + if (cpu_has_vmx_msr_bitmap) { + vmx_msr_bitmap = alloc_page(GFP_KERNEL | __GFP_HIGHMEM); + if (!vmx_msr_bitmap) { + r = -ENOMEM; + goto out1; + } + + printk(KERN_INFO "kvm: Enable MSR bitmap support.\n"); + + va = kmap(vmx_msr_bitmap); + memset(va, 0xff, PAGE_SIZE); + + disable_intercept_for_msr(MSR_FS_BASE, va); + disable_intercept_for_msr(MSR_GS_BASE, va); + + disable_intercept_for_msr(MSR_IA32_SYSENTER_CS, va); + disable_intercept_for_msr(MSR_IA32_SYSENTER_ESP, va); + disable_intercept_for_msr(MSR_IA32_SYSENTER_EIP, va); + + kunmap(vmx_msr_bitmap); + } + return 0; out1: @@ -2516,6 +2556,8 @@ out: static void __exit vmx_exit(void) { + if (cpu_has_vmx_msr_bitmap) + __free_page(vmx_msr_bitmap); __free_page(vmx_io_bitmap_b); __free_page(vmx_io_bitmap_a); diff --git a/drivers/kvm/vmx.h b/drivers/kvm/vmx.h index 7e4dc12..b61c7f3 100644 --- a/drivers/kvm/vmx.h +++ b/drivers/kvm/vmx.h @@ -309,4 +309,7 @@ enum vmcs_field { #define MSR_IA32_FEATURE_CONTROL_LOCKED 0x1 #define MSR_IA32_FEATURE_CONTROL_VMXON_ENABLED 0x4 +#define cpu_has_vmx_msr_bitmap \ + (vmcs_config.cpu_based_exec_ctrl & CPU_BASED_USE_MSR_BITMAPS) + #endif -- 1.5.2
Add-MSR-Bitmap-support-for-VMX.patch
Description: Add-MSR-Bitmap-support-for-VMX.patch
------------------------------------------------------------------------- This SF.net email is sponsored by: Splunk Inc. Still grepping through log files to find problems? Stop. Now Search log events and configuration files using AJAX and a browser. Download your FREE copy of Splunk now >> http://get.splunk.com/
_______________________________________________ kvm-devel mailing list kvm-devel@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/kvm-devel