Skip to content

Commit 1e18f2c

Browse files
bchaliosManciukic
authored andcommitted
refactor(vm): move Bus objects to Vm
We had previously added MMIO and Port IO buses inside ResourceAllocator so that we could implement DeviceRelocation for the type. Now, we will delegate device relocation responsibilities to ArchVm instead. That is because device relocation requires access to the Vm file descriptor as well. As a result, we can move buses to the Vm object itself. Add MMIO bus to VmCommon as both architectures use it. Add PortIO bus for x86 architecture only. Not that we don't still support DeviceRelocation. VirtIO devices should not request us to relocate them. Also, for adding such support we would need to also support VirtIO reset. We will look into adding this functionaliyt later on. Signed-off-by: Babis Chalios <[email protected]>
1 parent cc8d082 commit 1e18f2c

File tree

10 files changed

+73
-88
lines changed

10 files changed

+73
-88
lines changed

src/vmm/src/arch/x86_64/vm.rs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
// SPDX-License-Identifier: Apache-2.0
33

44
use std::fmt;
5+
use std::sync::Arc;
56

67
use kvm_bindings::{
78
KVM_CLOCK_TSC_STABLE, KVM_IRQCHIP_IOAPIC, KVM_IRQCHIP_PIC_MASTER, KVM_IRQCHIP_PIC_SLAVE,
@@ -58,6 +59,8 @@ pub struct ArchVm {
5859
///
5960
/// `None` if `KVM_CAP_XSAVE2` not supported.
6061
xsave2_size: Option<usize>,
62+
/// Port IO bus
63+
pub pio_bus: Arc<vm_device::Bus>,
6164
}
6265

6366
impl ArchVm {
@@ -92,10 +95,13 @@ impl ArchVm {
9295
.set_tss_address(u64_to_usize(crate::arch::x86_64::layout::KVM_TSS_ADDRESS))
9396
.map_err(ArchVmError::SetTssAddress)?;
9497

98+
let pio_bus = Arc::new(vm_device::Bus::new());
99+
95100
Ok(ArchVm {
96101
common,
97102
msrs_to_save,
98103
xsave2_size,
104+
pio_bus,
99105
})
100106
}
101107

src/vmm/src/device_manager/legacy.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -119,7 +119,7 @@ impl PortIODeviceManager {
119119
input: None,
120120
}));
121121

122-
let io_bus = &vm.common.resource_allocator.pio_bus;
122+
let io_bus = &vm.pio_bus;
123123
io_bus.insert(
124124
self.stdio_serial.clone(),
125125
Self::SERIAL_PORT_ADDRESSES[0],

src/vmm/src/device_manager/mmio.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -201,7 +201,7 @@ impl MMIODeviceManager {
201201
.map_err(MmioError::RegisterIrqFd)?;
202202
}
203203

204-
vm.common.resource_allocator.mmio_bus.insert(
204+
vm.common.mmio_bus.insert(
205205
device.inner.clone(),
206206
device.resources.addr,
207207
device.resources.len,
@@ -295,7 +295,7 @@ impl MMIODeviceManager {
295295
inner: serial,
296296
};
297297

298-
vm.common.resource_allocator.mmio_bus.insert(
298+
vm.common.mmio_bus.insert(
299299
device.inner.clone(),
300300
device.resources.addr,
301301
device.resources.len,
@@ -326,7 +326,7 @@ impl MMIODeviceManager {
326326
/// given as parameter, otherwise allocate a new MMIO resources for it.
327327
pub fn register_mmio_rtc(
328328
&mut self,
329-
resource_allocator: &ResourceAllocator,
329+
vm: &Vm,
330330
rtc: Arc<Mutex<RTCDevice>>,
331331
device_info_opt: Option<MMIODeviceInfo>,
332332
) -> Result<(), MmioError> {
@@ -335,7 +335,7 @@ impl MMIODeviceManager {
335335
let device_info = if let Some(device_info) = device_info_opt {
336336
device_info
337337
} else {
338-
let gsi = resource_allocator.allocate_gsi(1)?;
338+
let gsi = vm.common.resource_allocator.allocate_gsi(1)?;
339339
MMIODeviceInfo {
340340
addr: RTC_MEM_START,
341341
len: MMIO_LEN,
@@ -348,7 +348,7 @@ impl MMIODeviceManager {
348348
inner: rtc,
349349
};
350350

351-
resource_allocator.mmio_bus.insert(
351+
vm.common.mmio_bus.insert(
352352
device.inner.clone(),
353353
device.resources.addr,
354354
device.resources.len,

src/vmm/src/device_manager/mod.rs

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -217,7 +217,7 @@ impl DeviceManager {
217217
let boot_timer = Arc::new(Mutex::new(BootTimer::new(request_ts)));
218218

219219
self.mmio_devices
220-
.register_mmio_boot_timer(&vm.common.resource_allocator.mmio_bus, boot_timer)?;
220+
.register_mmio_boot_timer(&vm.common.mmio_bus, boot_timer)?;
221221

222222
Ok(())
223223
}
@@ -256,8 +256,7 @@ impl DeviceManager {
256256
}
257257

258258
let rtc = Arc::new(Mutex::new(RTCDevice::new()));
259-
self.mmio_devices
260-
.register_mmio_rtc(&vm.common.resource_allocator, rtc, None)?;
259+
self.mmio_devices.register_mmio_rtc(vm, rtc, None)?;
261260
Ok(())
262261
}
263262

src/vmm/src/device_manager/pci_mngr.rs

Lines changed: 9 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,6 @@ use crate::devices::virtio::{TYPE_BALLOON, TYPE_BLOCK, TYPE_NET, TYPE_RNG};
3333
use crate::resources::VmResources;
3434
use crate::snapshot::Persist;
3535
use crate::vstate::memory::GuestMemoryMmap;
36-
use crate::vstate::resources::ResourceAllocator;
3736
use crate::vstate::vm::{InterruptError, MsiVectorGroup};
3837
use crate::{EventManager, Vm};
3938

@@ -75,14 +74,14 @@ impl PciDevices {
7574

7675
// Currently we don't assign any IRQs to PCI devices. We will be using MSI-X interrupts
7776
// only.
78-
let pci_segment = PciSegment::new(0, &vm.common.resource_allocator, &[0u8; 32])?;
77+
let pci_segment = PciSegment::new(0, vm, &[0u8; 32])?;
7978
self.pci_segment = Some(pci_segment);
8079

8180
Ok(())
8281
}
8382

8483
fn register_bars_with_bus(
85-
resource_allocator: &ResourceAllocator,
84+
vm: &Vm,
8685
virtio_device: &Arc<Mutex<VirtioPciDevice>>,
8786
) -> Result<(), PciManagerError> {
8887
for bar in &virtio_device.lock().expect("Poisoned lock").bar_regions {
@@ -94,11 +93,8 @@ impl PciDevices {
9493
bar.size()
9594
);
9695
#[cfg(target_arch = "x86_64")]
97-
resource_allocator.pio_bus.insert(
98-
virtio_device.clone(),
99-
bar.addr(),
100-
bar.size(),
101-
)?;
96+
vm.pio_bus
97+
.insert(virtio_device.clone(), bar.addr(), bar.size())?;
10298
#[cfg(target_arch = "aarch64")]
10399
log::error!("pci: We do not support I/O region allocation")
104100
}
@@ -108,11 +104,9 @@ impl PciDevices {
108104
bar.addr(),
109105
bar.size()
110106
);
111-
resource_allocator.mmio_bus.insert(
112-
virtio_device.clone(),
113-
bar.addr(),
114-
bar.size(),
115-
)?;
107+
vm.common
108+
.mmio_bus
109+
.insert(virtio_device.clone(), bar.addr(), bar.size())?;
116110
}
117111
}
118112
}
@@ -168,7 +162,7 @@ impl PciDevices {
168162
self.virtio_devices
169163
.insert((device_type, id.clone()), virtio_device.clone());
170164

171-
Self::register_bars_with_bus(resource_allocator, &virtio_device)?;
165+
Self::register_bars_with_bus(vm, &virtio_device)?;
172166
virtio_device
173167
.lock()
174168
.expect("Poisoned lock")
@@ -213,7 +207,7 @@ impl PciDevices {
213207
self.virtio_devices
214208
.insert((device_type, device_id.to_string()), virtio_device.clone());
215209

216-
Self::register_bars_with_bus(&vm.common.resource_allocator, &virtio_device)?;
210+
Self::register_bars_with_bus(vm, &virtio_device)?;
217211
virtio_device
218212
.lock()
219213
.expect("Poisoned lock")

src/vmm/src/device_manager/persist.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -389,7 +389,7 @@ impl<'a> Persist<'a> for MMIODeviceManager {
389389
if state.type_ == DeviceType::Rtc {
390390
let rtc = Arc::new(Mutex::new(RTCDevice::new()));
391391
dev_manager.register_mmio_rtc(
392-
&constructor_args.vm.common.resource_allocator,
392+
constructor_args.vm,
393393
rtc,
394394
Some(state.device_info),
395395
)?;

src/vmm/src/devices/pci/pci_segment.rs

Lines changed: 28 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ use uuid::Uuid;
2121
use vm_allocator::AddressAllocator;
2222
use vm_device::{BusDeviceSync, BusError};
2323

24-
use crate::arch::{PCI_MMCONFIG_START, PCI_MMIO_CONFIG_SIZE_PER_SEGMENT};
24+
use crate::arch::{ArchVm as Vm, PCI_MMCONFIG_START, PCI_MMIO_CONFIG_SIZE_PER_SEGMENT};
2525
use crate::vstate::resources::ResourceAllocator;
2626

2727
pub struct PciSegment {
@@ -67,28 +67,21 @@ impl std::fmt::Debug for PciSegment {
6767
}
6868

6969
impl PciSegment {
70-
fn build(
71-
id: u16,
72-
resource_allocator: &Arc<ResourceAllocator>,
73-
pci_irq_slots: &[u8; 32],
74-
) -> Result<PciSegment, BusError> {
70+
fn build(id: u16, vm: &Arc<Vm>, pci_irq_slots: &[u8; 32]) -> Result<PciSegment, BusError> {
7571
let pci_root = PciRoot::new(None);
76-
let pci_bus = Arc::new(Mutex::new(PciBus::new(
77-
pci_root,
78-
resource_allocator.clone(),
79-
)));
72+
let pci_bus = Arc::new(Mutex::new(PciBus::new(pci_root, vm.clone())));
8073

8174
let pci_config_mmio = Arc::new(Mutex::new(PciConfigMmio::new(Arc::clone(&pci_bus))));
8275
let mmio_config_address = PCI_MMCONFIG_START + PCI_MMIO_CONFIG_SIZE_PER_SEGMENT * id as u64;
8376

84-
resource_allocator.mmio_bus.insert(
77+
vm.common.mmio_bus.insert(
8578
Arc::clone(&pci_config_mmio) as Arc<dyn BusDeviceSync>,
8679
mmio_config_address,
8780
PCI_MMIO_CONFIG_SIZE_PER_SEGMENT,
8881
)?;
8982

90-
let mem32_allocator = resource_allocator.mmio32_memory.clone();
91-
let mem64_allocator = resource_allocator.mmio64_memory.clone();
83+
let mem32_allocator = vm.common.resource_allocator.mmio32_memory.clone();
84+
let mem64_allocator = vm.common.resource_allocator.mmio64_memory.clone();
9285

9386
let start_of_mem32_area = mem32_allocator.lock().unwrap().base();
9487
let end_of_mem32_area = mem32_allocator.lock().unwrap().end();
@@ -119,13 +112,15 @@ impl PciSegment {
119112
#[cfg(target_arch = "x86_64")]
120113
pub(crate) fn new(
121114
id: u16,
122-
resource_allocator: &Arc<ResourceAllocator>,
115+
vm: &Arc<Vm>,
123116
pci_irq_slots: &[u8; 32],
124117
) -> Result<PciSegment, BusError> {
125-
let mut segment = Self::build(id, resource_allocator, pci_irq_slots)?;
118+
use crate::Vm;
119+
120+
let mut segment = Self::build(id, vm, pci_irq_slots)?;
126121
let pci_config_io = Arc::new(Mutex::new(PciConfigIo::new(Arc::clone(&segment.pci_bus))));
127122

128-
resource_allocator.pio_bus.insert(
123+
vm.pio_bus.insert(
129124
pci_config_io.clone(),
130125
PCI_CONFIG_IO_PORT,
131126
PCI_CONFIG_IO_PORT_SIZE,
@@ -151,10 +146,10 @@ impl PciSegment {
151146
#[cfg(target_arch = "aarch64")]
152147
pub(crate) fn new(
153148
id: u16,
154-
resource_allocator: &Arc<ResourceAllocator>,
149+
vm: &Arc<Vm>,
155150
pci_irq_slots: &[u8; 32],
156151
) -> Result<PciSegment, BusError> {
157-
let segment = Self::build(id, resource_allocator, pci_irq_slots)?;
152+
let segment = Self::build(id, vm, pci_irq_slots)?;
158153
info!(
159154
"pci: adding PCI segment: id={:#x}, PCI MMIO config address: {:#x}, mem32 area: \
160155
[{:#x}-{:#x}], mem64 area: [{:#x}-{:#x}]",
@@ -468,13 +463,14 @@ mod tests {
468463

469464
use super::*;
470465
use crate::arch;
466+
use crate::builder::tests::default_vmm;
471467
use crate::utils::u64_to_usize;
472468

473469
#[test]
474470
fn test_pci_segment_build() {
475-
let resource_allocator = Arc::new(ResourceAllocator::new().unwrap());
471+
let vmm = default_vmm();
476472
let pci_irq_slots = &[0u8; 32];
477-
let pci_segment = PciSegment::new(0, &resource_allocator, pci_irq_slots).unwrap();
473+
let pci_segment = PciSegment::new(0, &vmm.vm, pci_irq_slots).unwrap();
478474

479475
assert_eq!(pci_segment.id, 0);
480476
assert_eq!(
@@ -503,35 +499,34 @@ mod tests {
503499
#[cfg(target_arch = "x86_64")]
504500
#[test]
505501
fn test_io_bus() {
506-
let resource_allocator = Arc::new(ResourceAllocator::new().unwrap());
502+
let vmm = default_vmm();
507503
let pci_irq_slots = &[0u8; 32];
508-
let pci_segment = PciSegment::new(0, &resource_allocator, pci_irq_slots).unwrap();
504+
let pci_segment = PciSegment::new(0, &vmm.vm, pci_irq_slots).unwrap();
509505

510506
let mut data = [0u8; u64_to_usize(PCI_CONFIG_IO_PORT_SIZE)];
511-
resource_allocator
512-
.pio_bus
513-
.read(PCI_CONFIG_IO_PORT, &mut data)
514-
.unwrap();
507+
vmm.vm.pio_bus.read(PCI_CONFIG_IO_PORT, &mut data).unwrap();
515508

516-
resource_allocator
509+
vmm.vm
517510
.pio_bus
518511
.read(PCI_CONFIG_IO_PORT + PCI_CONFIG_IO_PORT_SIZE, &mut data)
519512
.unwrap_err();
520513
}
521514

522515
#[test]
523516
fn test_mmio_bus() {
524-
let resource_allocator = Arc::new(ResourceAllocator::new().unwrap());
517+
let vmm = default_vmm();
525518
let pci_irq_slots = &[0u8; 32];
526-
let pci_segment = PciSegment::new(0, &resource_allocator, pci_irq_slots).unwrap();
519+
let pci_segment = PciSegment::new(0, &vmm.vm, pci_irq_slots).unwrap();
527520

528521
let mut data = [0u8; u64_to_usize(PCI_MMIO_CONFIG_SIZE_PER_SEGMENT)];
529522

530-
resource_allocator
523+
vmm.vm
524+
.common
531525
.mmio_bus
532526
.read(pci_segment.mmio_config_address, &mut data)
533527
.unwrap();
534-
resource_allocator
528+
vmm.vm
529+
.common
535530
.mmio_bus
536531
.read(
537532
pci_segment.mmio_config_address + PCI_MMIO_CONFIG_SIZE_PER_SEGMENT,
@@ -542,9 +537,9 @@ mod tests {
542537

543538
#[test]
544539
fn test_next_device_bdf() {
545-
let resource_allocator = Arc::new(ResourceAllocator::new().unwrap());
540+
let vmm = default_vmm();
546541
let pci_irq_slots = &[0u8; 32];
547-
let pci_segment = PciSegment::new(0, &resource_allocator, pci_irq_slots).unwrap();
542+
let pci_segment = PciSegment::new(0, &vmm.vm, pci_irq_slots).unwrap();
548543

549544
// Start checking from device id 1, since 0 is allocated to the Root port.
550545
for dev_id in 1..32 {

src/vmm/src/lib.rs

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -373,10 +373,9 @@ impl Vmm {
373373
self.vcpus_handles.reserve(vcpu_count);
374374

375375
for mut vcpu in vcpus.drain(..) {
376-
vcpu.set_mmio_bus(self.vm.common.resource_allocator.mmio_bus.clone());
376+
vcpu.set_mmio_bus(self.vm.common.mmio_bus.clone());
377377
#[cfg(target_arch = "x86_64")]
378-
vcpu.kvm_vcpu
379-
.set_pio_bus(self.vm.common.resource_allocator.pio_bus.clone());
378+
vcpu.kvm_vcpu.set_pio_bus(self.vm.pio_bus.clone());
380379

381380
self.vcpus_handles
382381
.push(vcpu.start_threaded(vcpu_seccomp_filter.clone(), barrier.clone())?);

0 commit comments

Comments
 (0)