aboutsummaryrefslogtreecommitdiff
path: root/target/i386/kvm.c
diff options
context:
space:
mode:
Diffstat (limited to 'target/i386/kvm.c')
-rw-r--r--target/i386/kvm.c20
1 files changed, 20 insertions, 0 deletions
diff --git a/target/i386/kvm.c b/target/i386/kvm.c
index ef2e0a8..b3c13cb 100644
--- a/target/i386/kvm.c
+++ b/target/i386/kvm.c
@@ -110,6 +110,7 @@ static bool has_msr_core_capabs;
static bool has_msr_vmx_vmfunc;
static bool has_msr_ucode_rev;
static bool has_msr_vmx_procbased_ctls2;
+static bool has_msr_perf_capabs;
static uint32_t has_architectural_pmu_version;
static uint32_t num_architectural_pmu_gp_counters;
@@ -2033,6 +2034,9 @@ static int kvm_get_supported_msrs(KVMState *s)
case MSR_IA32_CORE_CAPABILITY:
has_msr_core_capabs = true;
break;
+ case MSR_IA32_PERF_CAPABILITIES:
+ has_msr_perf_capabs = true;
+ break;
case MSR_IA32_VMX_VMFUNC:
has_msr_vmx_vmfunc = true;
break;
@@ -2649,6 +2653,18 @@ static void kvm_msr_entry_add_vmx(X86CPU *cpu, FeatureWordArray f)
VMCS12_MAX_FIELD_INDEX << 1);
}
+static void kvm_msr_entry_add_perf(X86CPU *cpu, FeatureWordArray f)
+{
+ uint64_t kvm_perf_cap =
+ kvm_arch_get_supported_msr_feature(kvm_state,
+ MSR_IA32_PERF_CAPABILITIES);
+
+ if (kvm_perf_cap) {
+ kvm_msr_entry_add(cpu, MSR_IA32_PERF_CAPABILITIES,
+ kvm_perf_cap & f[FEAT_PERF_CAPABILITIES]);
+ }
+}
+
static int kvm_buf_set_msrs(X86CPU *cpu)
{
int ret = kvm_vcpu_ioctl(CPU(cpu), KVM_SET_MSRS, cpu->kvm_msr_buf);
@@ -2681,6 +2697,10 @@ static void kvm_init_msrs(X86CPU *cpu)
env->features[FEAT_CORE_CAPABILITY]);
}
+ if (has_msr_perf_capabs && cpu->enable_pmu) {
+ kvm_msr_entry_add_perf(cpu, env->features);
+ }
+
if (has_msr_ucode_rev) {
kvm_msr_entry_add(cpu, MSR_IA32_UCODE_REV, cpu->ucode_rev);
}