diff --git a/hive-priv/src/main.rs b/hive-priv/src/main.rs index aae7b5b0..cdeac79b 100644 --- a/hive-priv/src/main.rs +++ b/hive-priv/src/main.rs @@ -2183,10 +2183,12 @@ async fn set_subvolume_quota( Ok((String::new(), String::new())) } -/// Validate a single argument destined for `forgejo admin`. Rejects -/// null bytes and newlines (which could corrupt the subprocess args list -/// or log output). Shell metacharacters are harmless since the command -/// is spawned directly (no shell), but we reject them defensively. +/// Validate a single argument destined for `forgejo admin`. Rejects null +/// bytes, newlines and carriage returns (which could corrupt the +/// subprocess args list or log output). +/// +/// Shell metacharacters are **not** rejected, and do not need to be: the +/// command is spawned directly, with no shell to interpret them. fn validate_forge_admin_arg(arg: &str) -> Result<()> { if arg.bytes().any(|b| b == 0 || b == b'\n' || b == b'\r') { bail!("forge admin arg {arg:?} contains null byte or newline"); @@ -2765,8 +2767,13 @@ fn validate_name_chars(name: &str) -> Result<()> { } /// Validate a bind-mount path: must be absolute, non-empty, and contain -/// no newlines, null bytes, or double-quotes (which would break the -/// `EXTRA_NSPAWN_FLAGS="..."` conf line format). +/// no newlines, null bytes, double-quotes, or colons. +/// +/// The first three would break the `EXTRA_NSPAWN_FLAGS="..."` conf line +/// format. The colon is the one that matters most and had been left out +/// of this list: `--bind=SRC:DST` is colon-separated, so a path carrying +/// one does not corrupt the line — it silently becomes a *different +/// mount* than the caller asked for. fn validate_bind_path(path: &str) -> Result<()> { if path.is_empty() || !path.starts_with('/')