From c7fecf30e0f8f49698b75b1bbd2c6f9cd1002eca Mon Sep 17 00:00:00 2001 From: Colin Walters Date: Tue, 23 Jan 2024 19:44:50 -0500 Subject: [PATCH] install: Only switch to loopback after re-exec I noticed we were leaking a loopback device, and the reason is because the "re-exec self for selinux" dance. We should really try to move that re-exec way earlier because it's a big hazard for stuff like this right now. This is a simple fix though that just moves the switch to allocating the loopback device until after we've done the install prep (including that re-exec). Signed-off-by: Colin Walters --- lib/src/install.rs | 22 +++++++++++++++------- 1 file changed, 15 insertions(+), 7 deletions(-) diff --git a/lib/src/install.rs b/lib/src/install.rs index cb9416ca..be47ef09 100644 --- a/lib/src/install.rs +++ b/lib/src/install.rs @@ -1088,7 +1088,6 @@ pub(crate) async fn install_to_disk(opts: InstallToDiskOpts) -> Result<()> { .device .metadata() .with_context(|| format!("Querying {}", &block_opts.device))?; - let mut loopback = None; if opts.via_loopback { if !target_blockdev_meta.file_type().is_file() { anyhow::bail!( @@ -1096,9 +1095,6 @@ pub(crate) async fn install_to_disk(opts: InstallToDiskOpts) -> Result<()> { block_opts.device ); } - let loopback_dev = crate::blockdev::LoopbackDevice::new(block_opts.device.as_std_path())?; - block_opts.device = loopback_dev.path().into(); - loopback = Some(loopback_dev); } else { if !target_blockdev_meta.file_type().is_block_device() { anyhow::bail!("Not a block device: {}", block_opts.device); @@ -1107,10 +1103,22 @@ pub(crate) async fn install_to_disk(opts: InstallToDiskOpts) -> Result<()> { let state = prepare_install(opts.config_opts, opts.source_opts, opts.target_opts).await?; // This is all blocking stuff - let mut rootfs = { + let (mut rootfs, loopback) = { + let loopback_dev = if opts.via_loopback { + let loopback_dev = + crate::blockdev::LoopbackDevice::new(block_opts.device.as_std_path())?; + block_opts.device = loopback_dev.path().into(); + Some(loopback_dev) + } else { + None + }; + let state = state.clone(); - tokio::task::spawn_blocking(move || baseline::install_create_rootfs(&state, block_opts)) - .await?? + let rootfs = tokio::task::spawn_blocking(move || { + baseline::install_create_rootfs(&state, block_opts) + }) + .await??; + (rootfs, loopback_dev) }; install_to_filesystem_impl(&state, &mut rootfs).await?;