fix: handle write errors gracefully instead of panicking

Fixes #9769

Changed error.print().unwrap() to let _ = error.print() to prevent
panic when writing to /dev/full. Added regression test in test_cat.rs.
This commit is contained in:
Cả thế giới là Rust
2026-01-05 03:21:51 +00:00
parent 666c6df2c6
commit 9cc2e096d8
3 changed files with 35 additions and 1 deletions
+1
View File
@@ -182,6 +182,7 @@ LINESIZE
NAMESIZE
RTLD_NEXT
RTLD
SIGABRT
SIGINT
SIGKILL
SIGSTOP
+3 -1
View File
@@ -748,7 +748,9 @@ impl Error for ClapErrorWrapper {}
// This is abuse of the Display trait
impl Display for ClapErrorWrapper {
fn fmt(&self, _f: &mut Formatter<'_>) -> Result<(), std::fmt::Error> {
self.error.print().unwrap();
// Intentionally ignore the result - error.print() writes directly to stderr
// and we always return Ok(()) to satisfy Display's contract
let _ = self.error.print();
Ok(())
}
}
+31
View File
@@ -833,6 +833,37 @@ fn test_child_when_pipe_in() {
ts.ucmd().pipe_in("content").run().stdout_is("content");
}
/// Regression test for GitHub issue #9769
/// https://github.com/uutils/coreutils/issues/9769
///
/// Bug: Utilities panic when output is redirected to /dev/full
/// Location: src/uucore/src/lib/mods/error.rs:751 - `.unwrap()` causes panic
///
/// This test verifies that cat handles write errors to /dev/full gracefully
/// instead of panicking with exit code 134 (SIGABRT).
///
/// Expected behavior with current BUGGY code:
/// - Test WILL FAIL (cat panics with exit code 134)
///
/// Expected behavior after fix:
/// - Test SHOULD PASS (cat exits gracefully with error code 1)
// Regression test for issue #9769: graceful error handling when writing to /dev/full
#[test]
#[cfg(target_os = "linux")]
fn test_write_error_handling() {
use std::fs::File;
let dev_full =
File::create("/dev/full").expect("Failed to open /dev/full - test must run on Linux");
new_ucmd!()
.pipe_in("test content that should cause write error to /dev/full")
.set_stdout(dev_full)
.fails()
.code_is(1)
.stderr_contains("No space left on device");
}
#[test]
fn test_cat_eintr_handling() {
// Test that cat properly handles EINTR (ErrorKind::Interrupted) during I/O operations