Hmbown/CodeWhale · error · anyhow::Error
xAI OAuth private basename must be one UTF-8 path component
Error message
xAI OAuth private basename must be one UTF-8 path component
What it means
Enforced by validate_private_basename before every raw openat/renameat/unlinkat (open_at, remove_raw, rename_raw, open_windows_file): the name must be exactly one Normal UTF-8 path component with no separators and not `.`/`..`. This guarantees the *at() calls cannot escape the pinned credentials directory. Public entry points funnel input through validate_owned_auth_name first, so hitting this means an in-crate caller passed a compound or non-UTF-8 name.
Source
Thrown at crates/config/src/xai_credentials.rs:440
if store.remove_raw(&target)? {
removed += 1;
}
}
Ok(removed)
}
}
fn validate_owned_auth_name(name: &str) -> Result<()> {
anyhow::ensure!(
name == LEGACY_XAI_OAUTH_FILE_NAME || is_valid_xai_oauth_generation(name),
"invalid Codewhale-owned xAI OAuth basename"
);
Ok(())
}
fn validate_private_basename(name: &str) -> Result<()> {
let path = Path::new(name);
anyhow::ensure!(
path.components().count() == 1
&& matches!(path.components().next(), Some(Component::Normal(_)))
&& path.file_name().and_then(|value| value.to_str()) == Some(name),
"xAI OAuth private basename must be one UTF-8 path component"
);
Ok(())
}
#[cfg(unix)]
fn open_owned_credentials_directory(directory: &Path) -> Result<XaiOAuthCredentialStore> {
use std::os::fd::FromRawFd as _;
use std::os::unix::fs::{MetadataExt as _, PermissionsExt as _};
anyhow::ensure!(
directory.is_absolute(),
"xAI OAuth credentials directory must be absolute"
);
// SAFETY: the literal root path contains no interior NUL and the returnedView on GitHub (pinned to 8880682c63)
Solutions
- Pass a single basename (no '/', '\\', '.', or '..') to internal store helpers
- Route new public entry points through validate_owned_auth_name and keep validate_private_basename on the private raw layer
- In tests, build names with the same helper functions the production code uses
Defensive patterns
Strategy: validation
Validate before calling
fn is_single_component(name: &str) -> bool {
let p = std::path::Path::new(name);
p.components().count() == 1
&& matches!(p.components().next(), Some(std::path::Component::Normal(_)))
&& p.file_name().and_then(|n| n.to_str()) == Some(name)
} Type guard
fn is_private_basename(name: &str) -> bool {
!name.is_empty()
&& !name.contains(['/', '\\', '\u{0}'])
&& name != "."
&& name != ".."
&& std::path::Path::new(name).file_name().and_then(|n| n.to_str()) == Some(name)
} Prevention
- Inside the crate, always funnel new public entry points through validate_owned_auth_name
- Keep raw *at()-style helpers private and prefix their inputs with the basename check
- In tests, generate names with the same helpers production code uses
When it happens
Trigger: Calling the private rename_raw/remove_raw/open_at helpers with names like "dir/xai-auth.json", "..", ".", or a non-UTF-8 OsStr name; only reachable from code inside the codewhale-config crate or its unit tests.
Common situations: Contributors extending the store (new lifecycle files, tombstones) passing full paths instead of basenames; refactors that bypass validate_owned_auth_name; fuzz tests feeding path-shaped strings into internal helpers.
Related errors
- invalid Codewhale-owned xAI OAuth basename
- xAI OAuth credentials directory must be absolute
- Codewhale credentials directory cannot be a volume root
- Codewhale credentials path must be a directory
- Codewhale credentials directory must be owned by the current
AI-assisted analysis of Hmbown/CodeWhale@8880682c63 (2026-08-16).
Data as JSON: /api/errors/cda98eb44b89f19a.
Report an issue: GitHub.