Skip to content

Commit 7d942d3

Browse files
committed
feat: Add loader-entries set-options-for-source for source-tracked kargs
Add a new `bootc loader-entries set-options-for-source` command that manages kernel arguments from independent sources (e.g. TuneD, admin) by tracking ownership via `x-options-source-<name>` extension keys in BLS config files. This solves the problem of karg accumulation on bootc systems with transient /etc, where tools like TuneD lose their state files on reboot and can't track which kargs they previously set. The command stages a new deployment with the updated kargs and source keys. The kargs diff is computed by removing the old source's args and adding the new ones, preserving all untracked options. Source keys survive the staging roundtrip via ostree's `bootconfig-extra` serialization (ostree >= 2026.1, version check present but commented out until release). Staged deployment handling: - No staged deployment: stages based on the booted commit - Staged deployment exists (e.g. from `bootc upgrade`): replaces it using the staged commit and origin, preserving pending upgrades while layering the source kargs change on top Example usage: bootc loader-entries set-options-for-source --source tuned \ --options "isolcpus=1-3 nohz_full=1-3" See: ostreedev/ostree#3570 See: bootc-dev#899 Assisted-by: OpenCode (Claude claude-opus-4-6)
1 parent d8785c6 commit 7d942d3

File tree

3 files changed

+506
-0
lines changed

3 files changed

+506
-0
lines changed

crates/lib/src/cli.rs

Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -715,6 +715,54 @@ pub(crate) enum InternalsOpts {
715715
},
716716
}
717717

718+
/// Options for the `set-options-for-source` subcommand.
719+
#[derive(Debug, Parser, PartialEq, Eq)]
720+
pub(crate) struct SetOptionsForSourceOpts {
721+
/// The name of the source that owns these kernel arguments.
722+
///
723+
/// Must contain only alphanumeric characters, hyphens, or underscores.
724+
/// Examples: "tuned", "admin", "bootc-kargs-d"
725+
#[clap(long)]
726+
pub(crate) source: String,
727+
728+
/// The kernel arguments to set for this source.
729+
///
730+
/// If not provided, the source is removed and its options are
731+
/// dropped from the merged `options` line.
732+
#[clap(long)]
733+
pub(crate) options: Option<String>,
734+
}
735+
736+
/// Operations on Boot Loader Specification (BLS) entries.
737+
///
738+
/// These commands support managing kernel arguments from multiple independent
739+
/// sources (e.g., TuneD, admin, bootc kargs.d) by tracking argument ownership
740+
/// via `x-options-source-<name>` extension keys in BLS config files.
741+
///
742+
/// See <https://github.com/ostreedev/ostree/pull/3570>
743+
#[derive(Debug, clap::Subcommand, PartialEq, Eq)]
744+
pub(crate) enum LoaderEntriesOpts {
745+
/// Set or update the kernel arguments owned by a specific source.
746+
///
747+
/// Each source's arguments are tracked via `x-options-source-<name>`
748+
/// keys in BLS config files. The `options` line is recomputed as the
749+
/// merge of all tracked sources plus any untracked (pre-existing) options.
750+
///
751+
/// This stages a new deployment with the updated kernel arguments.
752+
///
753+
/// ## Examples
754+
///
755+
/// Add TuneD kernel arguments:
756+
/// bootc loader-entries set-options-for-source --source tuned --options "isolcpus=1-3 nohz_full=1-3"
757+
///
758+
/// Update TuneD kernel arguments:
759+
/// bootc loader-entries set-options-for-source --source tuned --options "isolcpus=0-7"
760+
///
761+
/// Remove TuneD kernel arguments:
762+
/// bootc loader-entries set-options-for-source --source tuned
763+
SetOptionsForSource(SetOptionsForSourceOpts),
764+
}
765+
718766
#[derive(Debug, clap::Subcommand, PartialEq, Eq)]
719767
pub(crate) enum StateOpts {
720768
/// Remove all ostree deployments from this system
@@ -820,6 +868,11 @@ pub(crate) enum Opt {
820868
/// Stability: This interface may change in the future.
821869
#[clap(subcommand, hide = true)]
822870
Image(ImageOpts),
871+
/// Operations on Boot Loader Specification (BLS) entries.
872+
///
873+
/// Manage kernel arguments from multiple independent sources.
874+
#[clap(subcommand)]
875+
LoaderEntries(LoaderEntriesOpts),
823876
/// Execute the given command in the host mount namespace
824877
#[clap(hide = true)]
825878
ExecInHostMountNamespace {
@@ -1864,6 +1917,19 @@ async fn run_from_opt(opt: Opt) -> Result<()> {
18641917
crate::install::install_finalize(&root_path).await
18651918
}
18661919
},
1920+
Opt::LoaderEntries(opts) => match opts {
1921+
LoaderEntriesOpts::SetOptionsForSource(opts) => {
1922+
prepare_for_write()?;
1923+
let storage = get_storage().await?;
1924+
let sysroot = storage.get_ostree()?;
1925+
crate::loader_entries::set_options_for_source_staged(
1926+
sysroot,
1927+
&opts.source,
1928+
opts.options.as_deref(),
1929+
)?;
1930+
Ok(())
1931+
}
1932+
},
18671933
Opt::ExecInHostMountNamespace { args } => {
18681934
crate::install::exec_in_host_mountns(args.as_slice())
18691935
}

crates/lib/src/lib.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,7 @@ pub(crate) mod journal;
8282
mod k8sapitypes;
8383
mod kernel;
8484
mod lints;
85+
mod loader_entries;
8586
mod lsm;
8687
pub(crate) mod metadata;
8788
mod parsers;

0 commit comments

Comments
 (0)