diff options
Diffstat (limited to 'arch/x86/kvm/vmx/nested.c')
| -rw-r--r-- | arch/x86/kvm/vmx/nested.c | 30 |
1 files changed, 20 insertions, 10 deletions
diff --git a/arch/x86/kvm/vmx/nested.c b/arch/x86/kvm/vmx/nested.c index 3170e291215d..d737a51a53ca 100644 --- a/arch/x86/kvm/vmx/nested.c +++ b/arch/x86/kvm/vmx/nested.c | |||
| @@ -55,7 +55,7 @@ static u16 shadow_read_write_fields[] = { | |||
| 55 | static int max_shadow_read_write_fields = | 55 | static int max_shadow_read_write_fields = |
| 56 | ARRAY_SIZE(shadow_read_write_fields); | 56 | ARRAY_SIZE(shadow_read_write_fields); |
| 57 | 57 | ||
| 58 | void init_vmcs_shadow_fields(void) | 58 | static void init_vmcs_shadow_fields(void) |
| 59 | { | 59 | { |
| 60 | int i, j; | 60 | int i, j; |
| 61 | 61 | ||
| @@ -211,6 +211,7 @@ static void free_nested(struct kvm_vcpu *vcpu) | |||
| 211 | if (!vmx->nested.vmxon && !vmx->nested.smm.vmxon) | 211 | if (!vmx->nested.vmxon && !vmx->nested.smm.vmxon) |
| 212 | return; | 212 | return; |
| 213 | 213 | ||
| 214 | hrtimer_cancel(&vmx->nested.preemption_timer); | ||
| 214 | vmx->nested.vmxon = false; | 215 | vmx->nested.vmxon = false; |
| 215 | vmx->nested.smm.vmxon = false; | 216 | vmx->nested.smm.vmxon = false; |
| 216 | free_vpid(vmx->nested.vpid02); | 217 | free_vpid(vmx->nested.vpid02); |
| @@ -2472,6 +2473,10 @@ static int nested_check_vm_execution_controls(struct kvm_vcpu *vcpu, | |||
| 2472 | (nested_cpu_has_vpid(vmcs12) && !vmcs12->virtual_processor_id)) | 2473 | (nested_cpu_has_vpid(vmcs12) && !vmcs12->virtual_processor_id)) |
| 2473 | return -EINVAL; | 2474 | return -EINVAL; |
| 2474 | 2475 | ||
| 2476 | if (!nested_cpu_has_preemption_timer(vmcs12) && | ||
| 2477 | nested_cpu_has_save_preemption_timer(vmcs12)) | ||
| 2478 | return -EINVAL; | ||
| 2479 | |||
| 2475 | if (nested_cpu_has_ept(vmcs12) && | 2480 | if (nested_cpu_has_ept(vmcs12) && |
| 2476 | !valid_ept_address(vcpu, vmcs12->ept_pointer)) | 2481 | !valid_ept_address(vcpu, vmcs12->ept_pointer)) |
| 2477 | return -EINVAL; | 2482 | return -EINVAL; |
| @@ -4140,11 +4145,11 @@ static int enter_vmx_operation(struct kvm_vcpu *vcpu) | |||
| 4140 | if (r < 0) | 4145 | if (r < 0) |
| 4141 | goto out_vmcs02; | 4146 | goto out_vmcs02; |
| 4142 | 4147 | ||
| 4143 | vmx->nested.cached_vmcs12 = kmalloc(VMCS12_SIZE, GFP_KERNEL); | 4148 | vmx->nested.cached_vmcs12 = kzalloc(VMCS12_SIZE, GFP_KERNEL); |
| 4144 | if (!vmx->nested.cached_vmcs12) | 4149 | if (!vmx->nested.cached_vmcs12) |
| 4145 | goto out_cached_vmcs12; | 4150 | goto out_cached_vmcs12; |
| 4146 | 4151 | ||
| 4147 | vmx->nested.cached_shadow_vmcs12 = kmalloc(VMCS12_SIZE, GFP_KERNEL); | 4152 | vmx->nested.cached_shadow_vmcs12 = kzalloc(VMCS12_SIZE, GFP_KERNEL); |
| 4148 | if (!vmx->nested.cached_shadow_vmcs12) | 4153 | if (!vmx->nested.cached_shadow_vmcs12) |
| 4149 | goto out_cached_shadow_vmcs12; | 4154 | goto out_cached_shadow_vmcs12; |
| 4150 | 4155 | ||
| @@ -4540,9 +4545,8 @@ static int handle_vmptrld(struct kvm_vcpu *vcpu) | |||
| 4540 | * given physical address won't match the required | 4545 | * given physical address won't match the required |
| 4541 | * VMCS12_REVISION identifier. | 4546 | * VMCS12_REVISION identifier. |
| 4542 | */ | 4547 | */ |
| 4543 | nested_vmx_failValid(vcpu, | 4548 | return nested_vmx_failValid(vcpu, |
| 4544 | VMXERR_VMPTRLD_INCORRECT_VMCS_REVISION_ID); | 4549 | VMXERR_VMPTRLD_INCORRECT_VMCS_REVISION_ID); |
| 4545 | return kvm_skip_emulated_instruction(vcpu); | ||
| 4546 | } | 4550 | } |
| 4547 | new_vmcs12 = kmap(page); | 4551 | new_vmcs12 = kmap(page); |
| 4548 | if (new_vmcs12->hdr.revision_id != VMCS12_REVISION || | 4552 | if (new_vmcs12->hdr.revision_id != VMCS12_REVISION || |
| @@ -5264,13 +5268,17 @@ static int vmx_get_nested_state(struct kvm_vcpu *vcpu, | |||
| 5264 | copy_shadow_to_vmcs12(vmx); | 5268 | copy_shadow_to_vmcs12(vmx); |
| 5265 | } | 5269 | } |
| 5266 | 5270 | ||
| 5267 | if (copy_to_user(user_kvm_nested_state->data, vmcs12, sizeof(*vmcs12))) | 5271 | /* |
| 5272 | * Copy over the full allocated size of vmcs12 rather than just the size | ||
| 5273 | * of the struct. | ||
| 5274 | */ | ||
| 5275 | if (copy_to_user(user_kvm_nested_state->data, vmcs12, VMCS12_SIZE)) | ||
| 5268 | return -EFAULT; | 5276 | return -EFAULT; |
| 5269 | 5277 | ||
| 5270 | if (nested_cpu_has_shadow_vmcs(vmcs12) && | 5278 | if (nested_cpu_has_shadow_vmcs(vmcs12) && |
| 5271 | vmcs12->vmcs_link_pointer != -1ull) { | 5279 | vmcs12->vmcs_link_pointer != -1ull) { |
| 5272 | if (copy_to_user(user_kvm_nested_state->data + VMCS12_SIZE, | 5280 | if (copy_to_user(user_kvm_nested_state->data + VMCS12_SIZE, |
| 5273 | get_shadow_vmcs12(vcpu), sizeof(*vmcs12))) | 5281 | get_shadow_vmcs12(vcpu), VMCS12_SIZE)) |
| 5274 | return -EFAULT; | 5282 | return -EFAULT; |
| 5275 | } | 5283 | } |
| 5276 | 5284 | ||
| @@ -5553,9 +5561,11 @@ void nested_vmx_setup_ctls_msrs(struct nested_vmx_msrs *msrs, u32 ept_caps, | |||
| 5553 | * secondary cpu-based controls. Do not include those that | 5561 | * secondary cpu-based controls. Do not include those that |
| 5554 | * depend on CPUID bits, they are added later by vmx_cpuid_update. | 5562 | * depend on CPUID bits, they are added later by vmx_cpuid_update. |
| 5555 | */ | 5563 | */ |
| 5556 | rdmsr(MSR_IA32_VMX_PROCBASED_CTLS2, | 5564 | if (msrs->procbased_ctls_high & CPU_BASED_ACTIVATE_SECONDARY_CONTROLS) |
| 5557 | msrs->secondary_ctls_low, | 5565 | rdmsr(MSR_IA32_VMX_PROCBASED_CTLS2, |
| 5558 | msrs->secondary_ctls_high); | 5566 | msrs->secondary_ctls_low, |
| 5567 | msrs->secondary_ctls_high); | ||
| 5568 | |||
| 5559 | msrs->secondary_ctls_low = 0; | 5569 | msrs->secondary_ctls_low = 0; |
| 5560 | msrs->secondary_ctls_high &= | 5570 | msrs->secondary_ctls_high &= |
| 5561 | SECONDARY_EXEC_DESC | | 5571 | SECONDARY_EXEC_DESC | |
