From 3d5a40dfa68e4717044a93cc07c51b072d98d38f Mon Sep 17 00:00:00 2001 From: Anatol Belski Date: Fri, 20 Mar 2026 20:30:53 +0100 Subject: [PATCH] vmm: device_manager: Wire up QcowDiskAsync with io_uring When io_uring is available and not disabled, open QCOW2 images with QcowDiskAsync for asynchronous reads. Falls back to QcowDiskSync otherwise. Signed-off-by: Anatol Belski --- vmm/src/device_manager.rs | 60 ++++++++++++++++++++++++++++++--------- 1 file changed, 46 insertions(+), 14 deletions(-) diff --git a/vmm/src/device_manager.rs b/vmm/src/device_manager.rs index 91d9509f3..9522be53d 100644 --- a/vmm/src/device_manager.rs +++ b/vmm/src/device_manager.rs @@ -35,6 +35,8 @@ use arch::{NumaNodes, layout}; use block::disk_file::DiskBackend; use block::error::BlockError; use block::fixed_vhd_sync::FixedVhdDiskSync; +#[cfg(feature = "io_uring")] +use block::qcow_async::QcowDiskAsync; use block::qcow_sync::QcowDiskSync; use block::raw_async_aio::RawFileDiskAio; use block::raw_sync::RawFileDiskSync; @@ -591,6 +593,10 @@ pub enum DeviceManagerError { #[error("Failed to create QcowDiskSync")] CreateQcowDiskSync(#[source] BlockError), + /// Failed to create QcowDiskAsync + #[error("Failed to create QcowDiskAsync")] + CreateQcowDiskAsync(#[source] BlockError), + /// Failed to create FixedVhdxDiskSync #[error("Failed to create FixedVhdxDiskSync")] CreateFixedVhdxDiskSync(#[source] BlockError), @@ -2801,20 +2807,46 @@ impl DeviceManager { } } ImageType::Qcow2 => { - info!("Using synchronous QCOW2 disk file"); - DiskBackend::Next(Box::new( - QcowDiskSync::new( - file, - disk_cfg.direct, - disk_cfg.backing_files, - disk_cfg.sparse, - ) - .map_err(|e| match &disk_cfg.path { - Some(p) => e.with_path(p), - None => e, - }) - .map_err(DeviceManagerError::CreateQcowDiskSync)?, - )) + if cfg!(feature = "io_uring") + && !disk_cfg.disable_io_uring + && self.io_uring_is_supported() + { + info!("Using asynchronous QCOW2 disk file (io_uring)"); + + #[cfg(not(feature = "io_uring"))] + unreachable!("Checked in if statement above"); + #[cfg(feature = "io_uring")] + { + DiskBackend::Next(Box::new( + QcowDiskAsync::new( + file, + disk_cfg.direct, + disk_cfg.backing_files, + disk_cfg.sparse, + ) + .map_err(|e| match &disk_cfg.path { + Some(p) => e.with_path(p), + None => e, + }) + .map_err(DeviceManagerError::CreateQcowDiskAsync)?, + )) + } + } else { + info!("Using synchronous QCOW2 disk file"); + DiskBackend::Next(Box::new( + QcowDiskSync::new( + file, + disk_cfg.direct, + disk_cfg.backing_files, + disk_cfg.sparse, + ) + .map_err(|e| match &disk_cfg.path { + Some(p) => e.with_path(p), + None => e, + }) + .map_err(DeviceManagerError::CreateQcowDiskSync)?, + )) + } } ImageType::Vhdx => { info!("Using synchronous VHDX disk file");