From 022b489e7b99c53faf6501b155a8bbdc35e1a0b5 Mon Sep 17 00:00:00 2001 From: Jianyong Wu Date: Thu, 15 Jun 2023 11:41:59 +0800 Subject: [PATCH] arch: x86_64: Populate the APIC Id Program the APIC ID (CPUID leaf 0x1 EBX) with the CPU id. This resolves an issue where the EDKII firmware expects the APIC ID to vary per-CPU. Fixes: #5475 Signed-off-by: Jianyong Wu --- arch/src/x86_64/mod.rs | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/arch/src/x86_64/mod.rs b/arch/src/x86_64/mod.rs index 3bdc01ee7..44683a99d 100644 --- a/arch/src/x86_64/mod.rs +++ b/arch/src/x86_64/mod.rs @@ -776,6 +776,13 @@ pub fn configure_vcpu( CpuidPatch::set_cpuid_reg(&mut cpuid, 0xb, None, CpuidReg::EDX, u32::from(id)); CpuidPatch::set_cpuid_reg(&mut cpuid, 0x1f, None, CpuidReg::EDX, u32::from(id)); + // Set ApicId in cpuid for each vcpu + // SAFETY: get host cpuid when eax=1 + let mut cpu_ebx = unsafe { core::arch::x86_64::__cpuid(1) }.ebx; + cpu_ebx &= 0xffffff; + cpu_ebx |= (id as u32) << 24; + CpuidPatch::set_cpuid_reg(&mut cpuid, 0x1, None, CpuidReg::EBX, cpu_ebx); + // The TSC frequency CPUID leaf should not be included when running with HyperV emulation if !kvm_hyperv { if let Some(tsc_khz) = vcpu.tsc_khz().map_err(Error::GetTscFrequency)? {