diff --git a/Cargo.lock b/Cargo.lock index a69e3e3f86..308af027ee 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -232,6 +232,15 @@ dependencies = [ "tracing-subscriber", ] +[[package]] +name = "bootc-kernel-cmdline" +version = "0.0.0" +source = "git+https://github.com/containers/bootc?rev=b76d75d6024bd0aa0f270ff181807aff4209f9c9#b76d75d6024bd0aa0f270ff181807aff4209f9c9" +dependencies = [ + "anyhow", + "serde", +] + [[package]] name = "bstr" version = "1.12.0" @@ -1581,7 +1590,7 @@ dependencies = [ "libc", "percent-encoding", "pin-project-lite", - "socket2 0.6.0", + "socket2 0.5.10", "system-configuration 0.6.1", "tokio", "tower-service", @@ -2843,6 +2852,7 @@ dependencies = [ "anyhow", "binread", "bitflags 2.9.1", + "bootc-kernel-cmdline", "camino", "cap-primitives", "cap-std", @@ -3965,7 +3975,7 @@ version = "0.1.9" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "cf221c93e13a30d793f7645a0e7762c55d169dbb0a49671918a2319d289b10bb" dependencies = [ - "windows-sys 0.59.0", + "windows-sys 0.48.0", ] [[package]] diff --git a/Cargo.toml b/Cargo.toml index 40d6e311e7..bda73b5e8d 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -74,6 +74,7 @@ once_cell = "1.21.3" os-release = "0.1.0" # We pull this one from git, as the project is no longer published as an external crate. ostree-ext = { git = "https://github.com/containers/bootc", rev = "b76d75d6024bd0aa0f270ff181807aff4209f9c9" } +bootc-kernel-cmdline = { git = "https://github.com/containers/bootc", rev = "b76d75d6024bd0aa0f270ff181807aff4209f9c9" } pastey = "0.1.1" phf = { version = "0.12", features = ["macros"] } rand = "0.9.1" diff --git a/rpmostree-cxxrs.cxx b/rpmostree-cxxrs.cxx index 6092ec6302..9c5282ee05 100644 --- a/rpmostree-cxxrs.cxx +++ b/rpmostree-cxxrs.cxx @@ -3029,6 +3029,9 @@ extern "C" void rpmostreecxx$cxxbridge1$cache_branch_to_nevra (::rust::Str nevra, ::rust::String *return$) noexcept; + void rpmostreecxx$cxxbridge1$kargs_delete (::rust::Str kargs, ::rust::Str to_delete, + ::rust::String *return$) noexcept; + ::std::uint32_t rpmostreecxx$cxxbridge1$CxxGObjectArray$length (::rpmostreecxx::CxxGObjectArray &self) noexcept { @@ -6232,6 +6235,14 @@ cache_branch_to_nevra (::rust::Str nevra) noexcept rpmostreecxx$cxxbridge1$cache_branch_to_nevra (nevra, &return$.value); return ::std::move (return$.value); } + +::rust::String +kargs_delete (::rust::Str kargs, ::rust::Str to_delete) noexcept +{ + ::rust::MaybeUninit<::rust::String> return$; + rpmostreecxx$cxxbridge1$kargs_delete (kargs, to_delete, &return$.value); + return ::std::move (return$.value); +} } // namespace rpmostreecxx extern "C" diff --git a/rpmostree-cxxrs.h b/rpmostree-cxxrs.h index fadec30166..2f57375034 100644 --- a/rpmostree-cxxrs.h +++ b/rpmostree-cxxrs.h @@ -2134,4 +2134,6 @@ ::rpmostreecxx::GKeyFile *treefile_to_origin (::rpmostreecxx::Treefile const &tf void origin_validate_roundtrip (::rpmostreecxx::GKeyFile const &kf) noexcept; ::rust::String cache_branch_to_nevra (::rust::Str nevra) noexcept; + +::rust::String kargs_delete (::rust::Str kargs, ::rust::Str to_delete) noexcept; } // namespace rpmostreecxx diff --git a/rust/src/kargs.rs b/rust/src/kargs.rs new file mode 100644 index 0000000000..92c1c931af --- /dev/null +++ b/rust/src/kargs.rs @@ -0,0 +1,19 @@ +/* + * SPDX-License-Identifier: Apache-2.0 OR MIT + */ + +use bootc_kernel_cmdline::utf8::{Cmdline, Parameter}; + +pub fn kargs_delete(kargs: &str, to_delete: &str) -> String { + let mut cmdline = Cmdline::from(kargs.to_string()); + let to_delete_param = match Parameter::parse(to_delete) { + Some(p) => p, + None => return String::new(), + }; + + if cmdline.remove_exact(&to_delete_param) { + cmdline.to_string() + } else { + String::new() + } +} diff --git a/rust/src/lib.rs b/rust/src/lib.rs index 31383677a8..79d257ea76 100644 --- a/rust/src/lib.rs +++ b/rust/src/lib.rs @@ -20,6 +20,8 @@ mod cmdutils; mod cxxrsutil; mod ffiutil; pub(crate) mod ffiwrappers; +mod kargs; +pub use crate::kargs::kargs_delete; mod reexec; pub(crate) use cxxrsutil::*; use ffi::BubblewrapMutability; @@ -835,6 +837,10 @@ pub mod ffi { fn cache_branch_to_nevra(nevra: &str) -> String; } + extern "Rust" { + fn kargs_delete(kargs: &str, to_delete: &str) -> String; + } + unsafe extern "C++" { include!("rpmostree-cxxrsutil.hpp"); #[allow(missing_debug_implementations)] diff --git a/src/daemon/rpmostreed-transaction-types.cxx b/src/daemon/rpmostreed-transaction-types.cxx index e2002b284d..540c6c7c1f 100644 --- a/src/daemon/rpmostreed-transaction-types.cxx +++ b/src/daemon/rpmostreed-transaction-types.cxx @@ -2762,12 +2762,19 @@ kernel_arg_apply_patching (KernelArgTransaction *self, RpmOstreeSysrootUpgrader g_auto (GStrv) existing_kargs_strv = ostree_kernel_args_to_strv (existing_kargs); gboolean changed = FALSE; - /* Delete all the entries included in the kernel args */ + g_auto (GStrv) kargs_strv = ostree_kernel_args_to_strv (kargs); + g_autofree char *kargs_str = g_strjoinv (" ", kargs_strv); + for (char **iter = self->kernel_args_deleted; iter && *iter; iter++) { const char *arg = *iter; - if (!ostree_kernel_args_delete (kargs, arg, error)) - return FALSE; + auto result = rpmostreecxx::kargs_delete (kargs_str, arg); + if (result.empty ()) + { + g_set_error (error, G_IO_ERROR, G_IO_ERROR_NOT_FOUND, "No karg '%s' found", arg); + return FALSE; + } + kargs_str = g_strdup (result.c_str ()); changed = TRUE; } @@ -2788,8 +2795,8 @@ kernel_arg_apply_patching (KernelArgTransaction *self, RpmOstreeSysrootUpgrader for (char **iter = append_if_missing; iter && *iter; iter++) { const char *arg = *iter; - g_auto (GStrv) kargs_strv = ostree_kernel_args_to_strv (kargs); - if (!g_strv_contains (kargs_strv, arg)) + g_auto (GStrv) current_kargs_strv = ostree_kernel_args_to_strv (kargs); + if (!g_strv_contains (current_kargs_strv, arg)) { ostree_kernel_args_append (kargs, arg); changed = TRUE; @@ -2799,14 +2806,22 @@ kernel_arg_apply_patching (KernelArgTransaction *self, RpmOstreeSysrootUpgrader for (char **iter = delete_if_present; iter && *iter; iter++) { const char *arg = *iter; - if (g_strv_contains (existing_kargs_strv, arg)) + auto result = rpmostreecxx::kargs_delete (kargs_str, arg); + if (!result.empty ()) { - if (!ostree_kernel_args_delete (kargs, arg, error)) - return FALSE; + kargs_str = g_strdup (result.c_str ()); changed = TRUE; } } + if (changed) + { + g_autoptr (OstreeKernelArgs) new_kargs = ostree_kernel_args_from_string (kargs_str); + g_auto (GStrv) new_strv = ostree_kernel_args_to_strv (new_kargs); + for (char **iter = new_strv; iter && *iter; iter++) + ostree_kernel_args_append (kargs, *iter); + } + if (!kernel_arg_apply (self, upgrader, kargs, changed, cancellable, error)) return FALSE;