diff --git a/hypervisor/arch/x86/guest/vmsr.c b/hypervisor/arch/x86/guest/vmsr.c
index 96ce15151..daa385a50 100644
--- a/hypervisor/arch/x86/guest/vmsr.c
+++ b/hypervisor/arch/x86/guest/vmsr.c
@@ -305,24 +305,32 @@ static void intercept_x2apic_msrs(uint8_t *msr_bitmap_arg, uint32_t mode)
}
/**
- * @pre vcpu != NULL
+ * @pre vcpu != NULL && vcpu->vm != NULL && vcpu->vm->vm_id < CONFIG_MAX_VM_NUM
+ * @pre (is_platform_rdt_capable() == false()) || (is_platform_rdt_capable() && get_vm_config(vcpu->vm->vm_id)->pclosids != NULL)
*/
-static void prepare_auto_msr_area (struct acrn_vcpu *vcpu)
+static void prepare_auto_msr_area(struct acrn_vcpu *vcpu)
{
- struct acrn_vm_config *cfg = get_vm_config(vcpu->vm->vm_id);
- uint16_t vcpu_clos = cfg->clos[vcpu->vcpu_id];
-
vcpu->arch.msr_area.count = 0U;
- /* only load/restore MSR IA32_PQR_ASSOC when hv and guest have differnt settings */
- if (is_platform_rdt_capable() && (vcpu_clos != hv_clos)) {
- vcpu->arch.msr_area.guest[MSR_AREA_IA32_PQR_ASSOC].msr_index = MSR_IA32_PQR_ASSOC;
- vcpu->arch.msr_area.guest[MSR_AREA_IA32_PQR_ASSOC].value = clos2pqr_msr(vcpu_clos);
- vcpu->arch.msr_area.host[MSR_AREA_IA32_PQR_ASSOC].msr_index = MSR_IA32_PQR_ASSOC;
- vcpu->arch.msr_area.host[MSR_AREA_IA32_PQR_ASSOC].value = clos2pqr_msr(hv_clos);
- vcpu->arch.msr_area.count++;
- pr_acrnlog("switch clos for VM %u vcpu_id %u, host 0x%x, guest 0x%x",
- vcpu->vm->vm_id, vcpu->vcpu_id, hv_clos, vcpu_clos);
+ if (is_platform_rdt_capable()) {
+ struct acrn_vm_config *cfg = get_vm_config(vcpu->vm->vm_id);
+ uint16_t vcpu_clos;
+
+ ASSERT(cfg->pclosids != NULL, "error, cfg->pclosids is NULL");
+
+ vcpu_clos = cfg->pclosids[vcpu->vcpu_id%cfg->num_pclosids];
+
+ /* RDT: only load/restore MSR_IA32_PQR_ASSOC when hv and guest have different settings */
+ if (vcpu_clos != hv_clos) {
+ vcpu->arch.msr_area.guest[MSR_AREA_IA32_PQR_ASSOC].msr_index = MSR_IA32_PQR_ASSOC;
+ vcpu->arch.msr_area.guest[MSR_AREA_IA32_PQR_ASSOC].value = clos2pqr_msr(vcpu_clos);
+ vcpu->arch.msr_area.host[MSR_AREA_IA32_PQR_ASSOC].msr_index = MSR_IA32_PQR_ASSOC;
+ vcpu->arch.msr_area.host[MSR_AREA_IA32_PQR_ASSOC].value = clos2pqr_msr(hv_clos);
+ vcpu->arch.msr_area.count++;
+
+ pr_acrnlog("switch clos for VM %u vcpu_id %u, host 0x%x, guest 0x%x",
+ vcpu->vm->vm_id, vcpu->vcpu_id, hv_clos, vcpu_clos);
+ }
}
}
@@ -392,7 +400,7 @@ void init_msr_emulation(struct acrn_vcpu *vcpu)
pr_dbg("VMX_MSR_BITMAP: 0x%016lx ", value64);
/* Initialize the MSR save/store area */
- prepare_auto_msr_area (vcpu);
+ prepare_auto_msr_area(vcpu);
/* Setup initial value for emulated MSRs */
init_emulated_msrs(vcpu);
diff --git a/hypervisor/include/arch/x86/asm/vm_config.h b/hypervisor/include/arch/x86/asm/vm_config.h
index 528210375..051c07148 100644
--- a/hypervisor/include/arch/x86/asm/vm_config.h
+++ b/hypervisor/include/arch/x86/asm/vm_config.h
@@ -182,9 +182,24 @@ struct acrn_vm_config {
* SOS can get the vm_configs[] array through hypercall, but SOS may not
* need to parse these members.
*/
- uint16_t clos[MAX_VCPUS_PER_VM]; /* Class of Service, effective only if CONFIG_RDT_ENABLED
- * is defined on CAT capable platforms
- */
+
+ uint16_t num_pclosids; /* This defines the number of elements in the array pointed to by pclosids */
+ /* pclosids: a pointer to an array of physical CLOSIDs (pCLOSIDs)) that is defined in vm_configurations.c
+ * by vmconfig,
+ * applicable only if CONFIG_RDT_ENABLED is defined on CAT capable platforms.
+ * The number of elements in the array must be equal to the value given by num_pclosids
+ */
+ uint16_t *pclosids;
+
+ /* max_type_pcbm (type: l2 or l3) specifies the allocated portion of physical cache
+ * for the VM and is a contiguous capacity bitmask (CBM) starting at bit position low
+ * (the lowest assigned physical cache way) and ending at position high
+ * (the highest assigned physical cache way, inclusive).
+ * As CBM only allows contiguous '1' combinations, so max_type_pcbm essentially
+ * is a bitmask that selects/covers all the physical cache ways assigned to the VM.
+ */
+ uint32_t max_l2_pcbm;
+ uint32_t max_l3_pcbm;
struct vuart_config vuart[MAX_VUART_NUM_PER_VM];/* vuart configuration for VM */
diff --git a/misc/config_tools/xforms/lib.xsl b/misc/config_tools/xforms/lib.xsl
index 57345d419..cc26ebddb 100644
--- a/misc/config_tools/xforms/lib.xsl
+++ b/misc/config_tools/xforms/lib.xsl
@@ -376,6 +376,17 @@
+
+
+
+
+
+
+
+
+
+
+
diff --git a/misc/config_tools/xforms/misc_cfg.h.xsl b/misc/config_tools/xforms/misc_cfg.h.xsl
index 35fa10740..b409acf0a 100644
--- a/misc/config_tools/xforms/misc_cfg.h.xsl
+++ b/misc/config_tools/xforms/misc_cfg.h.xsl
@@ -122,12 +122,6 @@
-
-
-
-
-
-
@@ -70,7 +85,11 @@
-
+
+
+
+
+
@@ -133,7 +152,23 @@
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -148,13 +183,13 @@
-
+
},
-
+
diff --git a/misc/hv_prebuild/vm_cfg_checks.c b/misc/hv_prebuild/vm_cfg_checks.c
index 8620c1580..a966883ae 100644
--- a/misc/hv_prebuild/vm_cfg_checks.c
+++ b/misc/hv_prebuild/vm_cfg_checks.c
@@ -84,13 +84,12 @@ static bool check_vm_clos_config(uint16_t vm_id)
uint16_t platform_clos_num = HV_SUPPORTED_MAX_CLOS;
bool ret = true;
struct acrn_vm_config *vm_config = get_vm_config(vm_id);
- uint16_t vcpu_num = bitmap_weight(vm_config->cpu_affinity);
- for (i = 0U; i < vcpu_num; i++) {
- if (((platform_clos_num != 0U) && (vm_config->clos[i] == platform_clos_num))
- || (vm_config->clos[i] > platform_clos_num)) {
+ for (i = 0U; i < vm_config->num_pclosids; i++) {
+ if (((platform_clos_num != 0U) && (vm_config->pclosids[i] == platform_clos_num))
+ || (vm_config->pclosids[i] > platform_clos_num)) {
printf("vm%u: vcpu%u clos(%u) exceed the max clos(%u).",
- vm_id, i, vm_config->clos[i], platform_clos_num);
+ vm_id, i, vm_config->pclosids[i], platform_clos_num);
ret = false;
break;
}