Jul 7, 2026·7 min read·28 visits
The Rust-based uutils coreutils implementation fails to trigger backup mode when only the --suffix parameter is specified, causing utilities like cp, mv, and ln to silently delete and overwrite existing target files without producing the expected safety backup.
A behavioral mismatch vulnerability (CWE-701) in the Rust-based uutils coreutils implementation of common command-line utilities allows silent data loss. When the --suffix argument is executed without explicit backup flags, the uucore library fails to enter backup mode, silently overwriting target files instead of creating preserving copies as expected under GNU standards.
The uutils coreutils project is a modern Rust re-implementation of the classic GNU coreutils software suite. It is designed to act as a secure, fast, and drop-in alternative for POSIX/GNU utility binaries across diverse server, desktop, and embedded platforms. A critical component of this ecosystem is the shared library crate known as uucore, which houses unified command-line argument processing, file system logic, and compatibility layers for tools including cp, mv, ln, and install.
Within GNU coreutils, specifying the -S or --suffix option implicitly informs the utility that a backup operation must be performed, defaulting the backup methodology to the 'existing' scheme if no other type is specified. This design ensures that target files are systematically preserved under a modified suffix name during replacement, relocation, or linkage events. In uutils coreutils, however, a critical mismatch exists because the presence of the --suffix flag alone is ignored by the backup control parser, defaulting the execution state to no-backup.
This behavior maps directly to CWE-701: Behavioral Mismatch, where a software application's internal implementation diverges from its documented reference design in a manner that compromises system expectations. By failing to align with standard GNU behavior, the toolkit introduces unexpected system actions. Users executing scripts containing custom suffix declarations will find their target files truncated or replaced without any preserving copies created.
The root cause of this flaw lies in the parser design found in the module src/uucore/src/lib/features/backup_control.rs. The function determine_backup_mode is tasked with evaluating arguments parsed by the clap crate and mapping them to a safe-state state-machine representation known as BackupMode. This enum can take values such as None, Simple, Numbered, or Existing.
Prior to the patch, determine_backup_mode only queried whether the explicit backup arguments were set in the clap match structure. The logic examined matches.contains_id(arguments::OPT_BACKUP) and matches.get_flag(arguments::OPT_BACKUP_NO_ARG). Because the parser lacked any matching check for the suffix identifier arguments::OPT_SUFFIX, any CLI call passing only --suffix would trigger the catch-all else block, returning BackupMode::None.
Subsequently, during the file-writing phase, the system queries get_backup_path to locate the target path where the existing file should be safely renamed. When this function receives BackupMode::None, it immediately returns None, skipping all backup copy mechanisms. The binary then proceeds with the destructive path creation step, truncating and overwriting the pre-existing target file in place. This design failure exemplifies CWE-459: Incomplete Cleanup / State Handling, as the application fails to initialize the target preservation states.
To understand the implementation flaw, examine the vulnerable implementation of the argument parsing state-machine in uucore:
pub fn determine_backup_mode(matches: &ArgMatches) -> UResult<BackupMode> {
if matches.contains_id(arguments::OPT_BACKUP) {
// Code evaluates explicitly set backup parameters
// ...
} else if matches.get_flag(arguments::OPT_BACKUP_NO_ARG) {
// ...
} else {
// No backup option was parsed, fallback directly to None
Ok(BackupMode::None)
}
}When BackupMode::None is propagated to the file management layer, the backup target path generator resolves the path to None and aborts safety initialization:
pub fn get_backup_path(
backup_mode: BackupMode,
backup_path: &Path,
suffix: &str,
) -> Option<PathBuf> {
match backup_mode {
BackupMode::None => None, // Safely returns None, bypasses backup file generation
BackupMode::Simple => Some(simple_backup_path(backup_path, suffix)),
BackupMode::Numbered => Some(numbered_backup_path(backup_path)),
BackupMode::Existing => Some(existing_backup_path(backup_path, suffix)),
}
}The patch resolved this by inserting an additional conditional arm before falling back to None. This arm queries whether OPT_SUFFIX is present, evaluating environmental overrides before establishing a default backup scheme:
} else if matches.contains_id(arguments::OPT_SUFFIX) {
// Suffix option triggers backup mode even when --backup is omitted.
// Default behavior falls back to "existing" unless overridden via VERSION_CONTROL env.
if let Ok(method) = env::var("VERSION_CONTROL") {
match_method(&method, "$VERSION_CONTROL")
} else {
Ok(BackupMode::Existing)
}
} else {
Ok(BackupMode::None)
}This remediation successfully bridges the compatibility gap, aligning the logic paths with standard POSIX patterns.
An attacker with the ability to inject files or manipulate target destinations in system automation frameworks can weaponize this behavioral mismatch. Because standard scripts rely on --suffix for safety wrappers, executing these scripts under uutils coreutils leads to silent state corruption. No privilege escalation occurs directly, but target data is irrecoverably destroyed.
To demonstrate this behavior in a shell environment, initialize a target file containing dummy configuration data and run the vulnerable copy tool:
# 1. Initialize destination file with sensitive contents
echo "important_original_data" > /tmp/test_dest
# 2. Attempt a copy using uutils cp with suffix only
coreutils cp --suffix=.bak /etc/hostname /tmp/test_dest
# 3. Analyze the directory
ls -la /tmp/test_dest*On a vulnerable deployment, only /tmp/test_dest is present, containing the contents of /etc/hostname. The safety file /tmp/test_dest.bak was never created, resulting in the permanent destruction of important_original_data without warning. The process exits with code 0, masking the loss from automated monitors.
A similar vector targets link replacement pipelines where symbolic links are forced over production settings:
# Initialize production reference
echo "critical_target_file" > /tmp/test_ln_dest
echo "some_source" > /tmp/test_ln_src
# Force link replacement with suffix
coreutils ln -f --suffix=.bak /tmp/test_ln_src /tmp/test_ln_destThe target file /tmp/test_ln_dest is overwritten with the symbolic link, and no safety backup file /tmp/test_ln_dest.bak is generated, permanently deleting the file system's original configuration pointer.
The security impact of GHSA-FQF6-GXHH-2XHW is categorized primarily as high integrity destruction and resource loss. Standard deployments utilizing Rust-native environments under the assumption of drop-in compatibility are subject to sudden configuration corruption. This vulnerability holds a CVSS v3.1 score of 6.6 with the vector string CVSS:3.1/AV:L/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:H.
The high rating on Integrity and Availability stems from the permanent nature of the data deletion. In automated scenarios like continuous integration pipelines, database rotation setups, or script-driven configuration loaders, failures do not cause command errors. Because the core utilities exit with zero status, orchestration platforms like Kubernetes or Ansible assume a successful safe rotation, leaving deployments functionally crippled but seemingly healthy.
In target environments, an attacker who can trigger administrative cleanup scripts can strategically manipulate destination files. Because the safety copy is bypassed, critical runtime variables, security policies, or operational databases can be permanently modified. This provides a direct path for denial-of-service, diagnostic logging erasure, and system disruption campaigns.
To address this vulnerability, system administrators and developers must upgrade uutils coreutils to a release containing Pull Request #9741 or compile the suite from upstream sources updated after December 20, 2025. Software distributions packing uutils should patch their respective package definitions immediately to prevent silent failure states.
For systems where immediate upgrades of the binary suite are impossible due to technical debt, change management constraints, or air-gapped target environments, administrators must deploy script-level workarounds. This involves altering all instances of target commands within shell pipelines to explicitly pass the backup flag in conjunction with the suffix parameter:
# Vulnerable configuration pattern
mv --suffix=.bak source target
# Secure configuration pattern (workaround)
mv --backup --suffix=.bak source targetAdditionally, validation checks must be added to verify file existence and backup state presence inside cron tasks. Security teams should scan orchestration scripts to locate any raw dependencies on suffix-based preservation patterns, ensuring that the necessary logic flags are present to bypass the flawed code paths.
CVSS:3.1/AV:L/AC:L/PR:N/UI:R/S:U/C:N/I:H/A:H| Product | Affected Versions | Fixed Version |
|---|---|---|
uutils coreutils uutils | <= 0.0.28 | 0.0.29 / PR 9741 |
| Attribute | Detail |
|---|---|
| CWE ID | CWE-701: Behavioral Mismatch / CWE-459: Incomplete Cleanup |
| Attack Vector | Local (L) |
| CVSS v3.1 Score | 6.6 (Medium) |
| EPSS Score | Not Applicable (No registered CVE) |
| Impact | High Integrity Destruction and File Resource Deletion |
| Exploit Status | Proof of Concept (PoC) available and verified |
| KEV Status | Not Listed |
The product's behavior deviates significantly from its expected specification or equivalent system, resulting in unexpected outcomes.
A vulnerability in vLLM prior to 0.30.0 allows an authenticated multi-tenant attacker to infer execution history and prompt structures of other tenants. The multi-turn Responses API ('Harmony' path) fails to propagate the 'cache_salt' parameter during tool-call continuation steps, storing sensitive prompt prefixes in the global, unsalted cache space.
A state desynchronization (cache drift) vulnerability exists in the multimodal Inter-Process Communication (IPC) Least Recently Used (LRU) caches of vLLM. When a multimodal request fails validation after its media hash has been registered on the frontend but before the payload is committed to the backend engine core, the frontend and backend caches drift out of lockstep. A subsequent request reusing the same media triggers an assertion failure in the backend engine core, resulting in a complete denial of service.
CVE-2026-105750 is a medium-severity local file disclosure vulnerability affecting the Docling and Docling-Slim libraries. When processing HTML documents using the optional Playwright rendering backend, the application fail to validate and restrict request URIs using the file:// scheme. This permits an attacker supplying a crafted HTML file to access, render, and exfiltrate local system files.
CVE-2026-102598 is a security bypass and Denial of Service (DoS) vulnerability in the Werkzeug WSGI web application library. In versions prior to 3.1.9, the library's safe_join function fails to sanitize Windows reserved device names containing an empty NTFS Alternate Data Stream (ADS) marker (such as NUL:). This allows remote, unauthenticated attackers to trigger indefinite thread-blocking operations on Windows hosts, resulting in application-wide resource exhaustion.
A vulnerability in @graphql-tools/executor-legacy-ws prior to version 1.1.35 hardcodes the TLS rejectUnauthorized setting to false for outgoing secure WebSocket (wss://) connections. This defect allows unauthenticated remote attackers to perform Adversary-in-the-Middle (MitM) attacks, capturing or tampering with sensitive connection payloads and subscription data.
CVE-2026-103918 is a medium-severity vulnerability within the @orpc/zod smart coercion plugin in oRPC. Prior to version 1.14.10, the package fails to sanitize untrusted input keys when performing pre-validation type coercion, allowing prototype injection on the returned request object and Denial of Service.