mirror of
https://github.com/cloud-hypervisor/cloud-hypervisor.git
synced 2026-08-05 02:19:16 +00:00
vmm: clear VFIO MMIO regions in DeviceManager::drop
DeviceManager and VfioPciDevice both hold Arc<MmapRegion> for each VFIO BAR mmap window. During VM shutdown, VfioPciDevice drops after DeviceManager::Drop::drop (via device_tree field drop). Without clearing DeviceManager's clones first, VfioPciDevice::unmap_mmio_regions decrements the Arc but does not reach zero, munmap never fires, the VFIO device file VMAs survive, and VFIO_GROUP_UNSET_CONTAINER returns EBUSY. Clear DeviceManager's mmio_regions in Drop::drop so VfioPciDevice is the sole Arc owner at drop time and ensure VFIO_GROUP_UNSET_CONTAINER ioctl success. Remove redundant .clone() on the mmio_regions() return value in the eject_device() hot-unplug path. Add detail comments Signed-off-by: Saravanan D <saravanand@crusoe.ai>
This commit is contained in:
committed by
Rob Bradford
parent
7294ca99cf
commit
5a14d0e2e0
@@ -4958,7 +4958,7 @@ impl DeviceManager {
|
||||
// rather than MmioRegion start addresses because move_bar()
|
||||
// updates the device's region addresses but not the
|
||||
// DeviceManager's cloned copies.
|
||||
let device_regions = vfio_pci_device.lock().unwrap().mmio_regions().clone();
|
||||
let device_regions = vfio_pci_device.lock().unwrap().mmio_regions();
|
||||
let mut mmio_regions = self.mmio_regions.lock().unwrap();
|
||||
for device_region in &device_regions {
|
||||
mmio_regions.retain(|x| !x.has_matching_slots(device_region));
|
||||
@@ -5865,6 +5865,11 @@ impl BusDevice for DeviceManager {
|
||||
|
||||
impl Drop for DeviceManager {
|
||||
fn drop(&mut self) {
|
||||
// Explicitly clear the regions owned by this device to ensure
|
||||
// that they are dropped and unmapped before the container is cleared.
|
||||
// See eject_device() for the device hot-unplug equivalent.
|
||||
self.mmio_regions.lock().unwrap().clear();
|
||||
|
||||
// Wake up the DeviceManager threads (mainly virtio device workers),
|
||||
// to avoid deadlock on waiting for paused/parked worker threads.
|
||||
if let Err(e) = self.resume() {
|
||||
|
||||
Reference in New Issue
Block a user