hv: fix using cpuid does not clear the upper 32-bit registers.

In HV, cpuid uses the lower 32 bits of rax\rbx\rcx\rdx registers to pass parameters,
But the software does not clear the upper 32-bit registers,  if the guest
uses 64-bit variables to pass parameters to cpuid,guest will use rax\rbx\rcx\rdx,
not eax\ebx\ecx\edx, the previous value of the high 32 registers will affect the guest.

Tracked-On: #8605
Reviewed-by: Junjie Mao <junjie.mao@intel.com>
Signed-off-by: andi6 <andi6@xiaomi.com>
This commit is contained in:
andi6 2024-05-27 15:12:07 +08:00 committed by acrnsi-robot
parent 30aeeedcb6
commit 46a860bf04
1 changed files with 11 additions and 12 deletions

View File

@ -354,19 +354,18 @@ static int32_t hlt_vmexit_handler(struct acrn_vcpu *vcpu)
int32_t cpuid_vmexit_handler(struct acrn_vcpu *vcpu)
{
uint64_t rax, rbx, rcx, rdx;
uint32_t eax, ebx, ecx, edx;
rax = vcpu_get_gpreg(vcpu, CPU_REG_RAX);
rbx = vcpu_get_gpreg(vcpu, CPU_REG_RBX);
rcx = vcpu_get_gpreg(vcpu, CPU_REG_RCX);
rdx = vcpu_get_gpreg(vcpu, CPU_REG_RDX);
TRACE_2L(TRACE_VMEXIT_CPUID, rax, rcx);
guest_cpuid(vcpu, (uint32_t *)&rax, (uint32_t *)&rbx,
(uint32_t *)&rcx, (uint32_t *)&rdx);
vcpu_set_gpreg(vcpu, CPU_REG_RAX, rax);
vcpu_set_gpreg(vcpu, CPU_REG_RBX, rbx);
vcpu_set_gpreg(vcpu, CPU_REG_RCX, rcx);
vcpu_set_gpreg(vcpu, CPU_REG_RDX, rdx);
eax = (uint32_t)vcpu_get_gpreg(vcpu, CPU_REG_RAX);
ebx = (uint32_t)vcpu_get_gpreg(vcpu, CPU_REG_RBX);
ecx = (uint32_t)vcpu_get_gpreg(vcpu, CPU_REG_RCX);
edx = (uint32_t)vcpu_get_gpreg(vcpu, CPU_REG_RDX);
TRACE_2L(TRACE_VMEXIT_CPUID, (uint64_t)eax, (uint64_t)ecx);
guest_cpuid(vcpu, &eax, &ebx, &ecx, &edx);
vcpu_set_gpreg(vcpu, CPU_REG_RAX, (uint64_t)eax);
vcpu_set_gpreg(vcpu, CPU_REG_RBX, (uint64_t)ebx);
vcpu_set_gpreg(vcpu, CPU_REG_RCX, (uint64_t)ecx);
vcpu_set_gpreg(vcpu, CPU_REG_RDX, (uint64_t)edx);
return 0;
}