Return correct value of IA32_PERF_CAPABILITIES when userspace tries to read it after vCPU has already run. Previously, KVM will always return the guest cached value on get_msr() even if guest CPUID lacks X86_FEATURE_PDCM. The guest cached value on default is kvm_caps.supported_perf_cap. However, when userspace sets the value during live migration, the call fails because of the check on X86_FEATURE_PDCM. Initially, it sounds like a pure userspace issue. It is not. After vCPU has run, KVM should faithfully return correct value to satisify legitimate requests from userspace such as VM suspend/resume and live migrartion. In this case, KVM should return 0 when guest cpuid lacks X86_FEATURE_PDCM. So fix the problem by adding an additional check in vmx_set_msr(). Note that IA32_PERF_CAPABILITIES is emulated on AMD side, which is fine because it set_msr() is guarded by kvm_caps.supported_perf_cap which is always 0. Cc: Aaron Lewis <aaronlewis@xxxxxxxxxx> Cc: Jim Mattson <jmattson@xxxxxxxxxx> Signed-off-by: Mingwei Zhang <mizhang@xxxxxxxxxx> --- arch/x86/kvm/vmx/vmx.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/arch/x86/kvm/vmx/vmx.c b/arch/x86/kvm/vmx/vmx.c index 40e3780d73ae..6d8667b56091 100644 --- a/arch/x86/kvm/vmx/vmx.c +++ b/arch/x86/kvm/vmx/vmx.c @@ -2049,6 +2049,17 @@ static int vmx_get_msr(struct kvm_vcpu *vcpu, struct msr_data *msr_info) msr_info->data = to_vmx(vcpu)->msr_ia32_sgxlepubkeyhash [msr_info->index - MSR_IA32_SGXLEPUBKEYHASH0]; break; + case MSR_IA32_PERF_CAPABILITIES: + /* + * Host VMM should not get potentially invalid MSR value if vCPU + * has already run but guest cpuid lacks the support for the + * MSR. + */ + if (msr_info->host_initiated && + kvm_vcpu_has_run(vcpu) && + !guest_cpuid_has(vcpu, X86_FEATURE_PDCM)) + return 1; + break; case KVM_FIRST_EMULATED_VMX_MSR ... KVM_LAST_EMULATED_VMX_MSR: if (!guest_can_use(vcpu, X86_FEATURE_VMX)) return 1; base-commit: fd89499a5151d197ba30f7b801f6d8f4646cf446 -- 2.44.0.291.gc1ea87d7ee-goog