Skip to content

Commit d3e8d36

Browse files
Johan-Liebert1cgwalters
authored andcommitted
composefs/state: Use atomic writes for origin and staged deployment files
Signed-off-by: Johan-Liebert1 <[email protected]>
1 parent 7a10221 commit d3e8d36

File tree

2 files changed

+27
-11
lines changed

2 files changed

+27
-11
lines changed

crates/lib/src/install.rs

Lines changed: 21 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2063,7 +2063,8 @@ fn setup_composefs_boot(root_setup: &RootSetup, state: &State, image_id: &str) -
20632063
}
20642064

20652065
pub(crate) const COMPOSEFS_TRANSIENT_STATE_DIR: &str = "/run/composefs";
2066-
pub(crate) const COMPOSEFS_STAGED_DEPLOYMENT_PATH: &str = "/run/composefs/staged-deployment";
2066+
/// File created in /run/composefs to record a staged-deployment
2067+
pub(crate) const COMPOSEFS_STAGED_DEPLOYMENT_FNAME: &str = "staged-deployment";
20672068
/// Relative to /sysroot
20682069
pub(crate) const STATE_DIR_RELATIVE: &str = "state/deploy";
20692070

@@ -2105,21 +2106,32 @@ pub(crate) fn write_composefs_state(
21052106
.section(ORIGIN_KEY_BOOT)
21062107
.item(ORIGIN_KEY_BOOT_TYPE, boot_type);
21072108

2108-
let mut origin_file =
2109-
std::fs::File::create(state_path.join(format!("{}.origin", deployment_id.to_hex())))
2110-
.context("Failed to open .origin file")?;
2109+
let state_dir = cap_std::fs::Dir::open_ambient_dir(&state_path, cap_std::ambient_authority())
2110+
.context("Opening state dir")?;
21112111

2112-
origin_file
2113-
.write(config.to_string().as_bytes())
2112+
state_dir
2113+
.atomic_write(
2114+
format!("{}.origin", deployment_id.to_hex()),
2115+
config.to_string().as_bytes(),
2116+
)
21142117
.context("Falied to write to .origin file")?;
21152118

21162119
if staged {
21172120
std::fs::create_dir_all(COMPOSEFS_TRANSIENT_STATE_DIR)
21182121
.with_context(|| format!("Creating {COMPOSEFS_TRANSIENT_STATE_DIR}"))?;
21192122

2120-
let buf = deployment_id.to_hex();
2121-
std::fs::write(COMPOSEFS_STAGED_DEPLOYMENT_PATH, buf)
2122-
.with_context(|| format!("Writing {COMPOSEFS_STAGED_DEPLOYMENT_PATH}"))?;
2123+
let staged_depl_dir = cap_std::fs::Dir::open_ambient_dir(
2124+
COMPOSEFS_TRANSIENT_STATE_DIR,
2125+
cap_std::ambient_authority(),
2126+
)
2127+
.with_context(|| format!("Opening {COMPOSEFS_TRANSIENT_STATE_DIR}"))?;
2128+
2129+
staged_depl_dir
2130+
.atomic_write(
2131+
COMPOSEFS_STAGED_DEPLOYMENT_FNAME,
2132+
deployment_id.to_hex().as_bytes(),
2133+
)
2134+
.with_context(|| format!("Writing to {COMPOSEFS_STAGED_DEPLOYMENT_FNAME}"))?;
21232135
}
21242136

21252137
Ok(())

crates/lib/src/status.rs

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,9 @@ use crate::deploy::get_sorted_uki_boot_entries;
2929
use crate::install::BootType;
3030
use crate::install::ORIGIN_KEY_BOOT;
3131
use crate::install::ORIGIN_KEY_BOOT_TYPE;
32-
use crate::install::{COMPOSEFS_STAGED_DEPLOYMENT_PATH, STATE_DIR_RELATIVE};
32+
use crate::install::{
33+
COMPOSEFS_STAGED_DEPLOYMENT_FNAME, COMPOSEFS_TRANSIENT_STATE_DIR, STATE_DIR_RELATIVE,
34+
};
3335
use crate::spec::ImageStatus;
3436
use crate::spec::{BootEntry, BootOrder, Host, HostSpec, HostStatus, HostType};
3537
use crate::spec::{ImageReference, ImageSignature};
@@ -428,7 +430,9 @@ pub(crate) async fn composefs_deployment_status() -> Result<Host> {
428430

429431
let mut host = Host::new(host_spec);
430432

431-
let staged_deployment_id = match std::fs::File::open(COMPOSEFS_STAGED_DEPLOYMENT_PATH) {
433+
let staged_deployment_id = match std::fs::File::open(format!(
434+
"{COMPOSEFS_TRANSIENT_STATE_DIR}/{COMPOSEFS_STAGED_DEPLOYMENT_FNAME}"
435+
)) {
432436
Ok(mut f) => {
433437
let mut s = String::new();
434438
f.read_to_string(&mut s)?;

0 commit comments

Comments
 (0)