pci: vfio: Fix potential mmap leaks from the mmio regions

We can return prematurely from 'map_mmio_regions()' (e.g. when a mmap call
failed for vfio or 'create_user_memory_region()' failed for vfio-user)
without updating the 'MmioRegion::user_memory_regions' with the
information of previous successful mmaps, which in turn would cause mmap
leaks particularly for the case of hotplug where the 'vmm' thread will
keep running. To fix the issue, let's keep 'MmioRegion::user_memory_regions'
updated right after successful mmap calls.

Fixes: #4068

Signed-off-by: Bo Chen <chen.bo@intel.com>
This commit is contained in:
Bo Chen 2022-05-05 15:57:48 -07:00 committed by Sebastien Boeuf
parent 42c19e14c5
commit 06f57abdf9
2 changed files with 4 additions and 10 deletions

View File

@ -1200,7 +1200,6 @@ impl VfioPciDevice {
self.common.interrupt.msix.as_ref(),
)?;
let mut user_memory_regions = Vec::new();
for area in sparse_areas.iter() {
let host_addr = unsafe {
libc::mmap(
@ -1230,6 +1229,8 @@ impl VfioPciDevice {
host_addr: host_addr as u64,
};
region.user_memory_regions.push(user_memory_region);
let mem_region = vm.make_user_memory_region(
user_memory_region.slot,
user_memory_region.start,
@ -1241,11 +1242,7 @@ impl VfioPciDevice {
vm.create_user_memory_region(mem_region)
.map_err(VfioPciError::CreateUserMemoryRegion)?;
user_memory_regions.push(user_memory_region);
}
region.user_memory_regions = user_memory_regions;
}
}

View File

@ -173,7 +173,6 @@ impl VfioUserPciDevice {
sparse_areas
};
let mut user_memory_regions = Vec::new();
for s in mmaps.iter() {
let host_addr = unsafe {
libc::mmap(
@ -202,6 +201,8 @@ impl VfioUserPciDevice {
host_addr: host_addr as u64,
};
mmio_region.user_memory_regions.push(user_memory_region);
let mem_region = vm.make_user_memory_region(
user_memory_region.slot,
user_memory_region.start,
@ -213,11 +214,7 @@ impl VfioUserPciDevice {
vm.create_user_memory_region(mem_region)
.map_err(VfioUserPciDeviceError::MapRegionGuest)?;
user_memory_regions.push(user_memory_region);
}
mmio_region.user_memory_regions = user_memory_regions;
}
}