diff --git a/vmm/src/vm.rs b/vmm/src/vm.rs index b8c78e197..d14b8dbed 100755 --- a/vmm/src/vm.rs +++ b/vmm/src/vm.rs @@ -202,6 +202,73 @@ enum CpuidReg { EDX, } +struct CpuidPatch { + function: u32, + index: u32, + flags_bit: Option, + eax_bit: Option, + ebx_bit: Option, + ecx_bit: Option, + edx_bit: Option, +} + +impl CpuidPatch { + fn set_cpuid_reg( + cpuid: &mut CpuId, + function: u32, + index: Option, + reg: CpuidReg, + value: u32, + ) { + let entries = cpuid.mut_entries_slice(); + + for entry in entries.iter_mut() { + if entry.function == function && (index == None || index.unwrap() == entry.index) { + match reg { + CpuidReg::EAX => { + entry.eax = value; + } + CpuidReg::EBX => { + entry.ebx = value; + } + CpuidReg::ECX => { + entry.ecx = value; + } + CpuidReg::EDX => { + entry.edx = value; + } + } + } + } + } + + fn patch_cpuid(cpuid: &mut CpuId, patches: Vec) { + let entries = cpuid.mut_entries_slice(); + + for entry in entries.iter_mut() { + for patch in patches.iter() { + if entry.function == patch.function && entry.index == patch.index { + if let Some(flags_bit) = patch.flags_bit { + entry.flags |= 1 << flags_bit; + } + if let Some(eax_bit) = patch.eax_bit { + entry.eax |= 1 << eax_bit; + } + if let Some(ebx_bit) = patch.ebx_bit { + entry.ebx |= 1 << ebx_bit; + } + if let Some(ecx_bit) = patch.ecx_bit { + entry.ecx |= 1 << ecx_bit; + } + if let Some(edx_bit) = patch.edx_bit { + entry.edx |= 1 << edx_bit; + } + } + } + } + } +} + /// A wrapper around creating and using a kvm-based VCPU. pub struct Vcpu { fd: VcpuFd, @@ -237,7 +304,7 @@ impl Vcpu { /// * `vm` - The virtual machine this vcpu will get attached to. pub fn configure(&mut self, kernel_start_addr: GuestAddress, vm: &Vm) -> Result<()> { let mut cpuid = vm.cpuid.clone(); - Vcpu::set_cpuid_reg(&mut cpuid, 0xb, None, CpuidReg::EDX, u32::from(self.id)); + CpuidPatch::set_cpuid_reg(&mut cpuid, 0xb, None, CpuidReg::EDX, u32::from(self.id)); self.fd .set_cpuid2(&cpuid) .map_err(Error::SetSupportedCpusFailed)?; @@ -296,35 +363,6 @@ impl Vcpu { }, } } - - fn set_cpuid_reg( - cpuid: &mut CpuId, - function: u32, - index: Option, - reg: CpuidReg, - value: u32, - ) { - let entries = cpuid.mut_entries_slice(); - - for entry in entries.iter_mut() { - if entry.function == function && (index == None || index.unwrap() == entry.index) { - match reg { - CpuidReg::EAX => { - entry.eax = value; - } - CpuidReg::EBX => { - entry.ebx = value; - } - CpuidReg::ECX => { - entry.ecx = value; - } - CpuidReg::EDX => { - entry.edx = value; - } - } - } - } - } } struct DeviceManager { @@ -624,16 +662,6 @@ impl AsRawFd for EpollContext { } } -struct CpuidPatch { - function: u32, - index: u32, - flags_bit: Option, - eax_bit: Option, - ebx_bit: Option, - ecx_bit: Option, - edx_bit: Option, -} - pub struct Vm<'a> { fd: Arc, kernel: File, @@ -715,7 +743,7 @@ impl<'a> Vm<'a> { edx_bit: None, }); - Vm::patch_cpuid(&mut cpuid, cpuid_patches); + CpuidPatch::patch_cpuid(&mut cpuid, cpuid_patches); // Let's allocate 64 GiB of addressable MMIO space, starting at 0. let mut allocator = SystemAllocator::new( @@ -914,32 +942,6 @@ impl<'a> Vm<'a> { pub fn get_memory(&self) -> &GuestMemoryMmap { &self.memory } - - fn patch_cpuid(cpuid: &mut CpuId, patches: Vec) { - let entries = cpuid.mut_entries_slice(); - - for entry in entries.iter_mut() { - for patch in patches.iter() { - if entry.function == patch.function && entry.index == patch.index { - if let Some(flags_bit) = patch.flags_bit { - entry.flags |= 1 << flags_bit; - } - if let Some(eax_bit) = patch.eax_bit { - entry.eax |= 1 << eax_bit; - } - if let Some(ebx_bit) = patch.ebx_bit { - entry.ebx |= 1 << ebx_bit; - } - if let Some(ecx_bit) = patch.ecx_bit { - entry.ecx |= 1 << ecx_bit; - } - if let Some(edx_bit) = patch.edx_bit { - entry.edx |= 1 << edx_bit; - } - } - } - } - } } #[allow(unused)]