KVM: x86: ensure all MSRs can always be KVM_GET/SET_MSR'd
Some of the MSRs returned by GET_MSR_INDEX_LIST currently cannot be sent back to KVM_GET_MSR and/or KVM_SET_MSR; either they can never be sent back, or you they are only accepted under special conditions. This makes the API a pain to use. To avoid this pain, this patch makes it so that the result of the get-list ioctl can always be used for host-initiated get and set. Since we don't have a separate way to check for read-only MSRs, this means some Hyper-V MSRs are ignored when written. Arguably they should not even be in the result of GET_MSR_INDEX_LIST, but I am leaving there in case userspace is using the outcome of GET_MSR_INDEX_LIST to derive the support for the corresponding Hyper-V feature. Cc: stable@vger.kernel.org Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
This commit is contained in:
@@ -2160,10 +2160,11 @@ static int set_msr_mce(struct kvm_vcpu *vcpu, struct msr_data *msr_info)
|
||||
vcpu->arch.mcg_status = data;
|
||||
break;
|
||||
case MSR_IA32_MCG_CTL:
|
||||
if (!(mcg_cap & MCG_CTL_P))
|
||||
if (!(mcg_cap & MCG_CTL_P) &&
|
||||
(data || !msr_info->host_initiated))
|
||||
return 1;
|
||||
if (data != 0 && data != ~(u64)0)
|
||||
return -1;
|
||||
return 1;
|
||||
vcpu->arch.mcg_ctl = data;
|
||||
break;
|
||||
default:
|
||||
@@ -2551,7 +2552,7 @@ int kvm_get_msr(struct kvm_vcpu *vcpu, struct msr_data *msr)
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(kvm_get_msr);
|
||||
|
||||
static int get_msr_mce(struct kvm_vcpu *vcpu, u32 msr, u64 *pdata)
|
||||
static int get_msr_mce(struct kvm_vcpu *vcpu, u32 msr, u64 *pdata, bool host)
|
||||
{
|
||||
u64 data;
|
||||
u64 mcg_cap = vcpu->arch.mcg_cap;
|
||||
@@ -2566,7 +2567,7 @@ static int get_msr_mce(struct kvm_vcpu *vcpu, u32 msr, u64 *pdata)
|
||||
data = vcpu->arch.mcg_cap;
|
||||
break;
|
||||
case MSR_IA32_MCG_CTL:
|
||||
if (!(mcg_cap & MCG_CTL_P))
|
||||
if (!(mcg_cap & MCG_CTL_P) && !host)
|
||||
return 1;
|
||||
data = vcpu->arch.mcg_ctl;
|
||||
break;
|
||||
@@ -2699,7 +2700,8 @@ int kvm_get_msr_common(struct kvm_vcpu *vcpu, struct msr_data *msr_info)
|
||||
case MSR_IA32_MCG_CTL:
|
||||
case MSR_IA32_MCG_STATUS:
|
||||
case MSR_IA32_MC0_CTL ... MSR_IA32_MCx_CTL(KVM_MAX_MCE_BANKS) - 1:
|
||||
return get_msr_mce(vcpu, msr_info->index, &msr_info->data);
|
||||
return get_msr_mce(vcpu, msr_info->index, &msr_info->data,
|
||||
msr_info->host_initiated);
|
||||
case MSR_K7_CLK_CTL:
|
||||
/*
|
||||
* Provide expected ramp-up count for K7. All other
|
||||
@@ -2720,7 +2722,8 @@ int kvm_get_msr_common(struct kvm_vcpu *vcpu, struct msr_data *msr_info)
|
||||
case HV_X64_MSR_TSC_EMULATION_CONTROL:
|
||||
case HV_X64_MSR_TSC_EMULATION_STATUS:
|
||||
return kvm_hv_get_msr_common(vcpu,
|
||||
msr_info->index, &msr_info->data);
|
||||
msr_info->index, &msr_info->data,
|
||||
msr_info->host_initiated);
|
||||
break;
|
||||
case MSR_IA32_BBL_CR_CTL3:
|
||||
/* This legacy MSR exists but isn't fully documented in current
|
||||
|
Reference in New Issue
Block a user