Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 9 additions & 4 deletions src/uu/cat/src/cat.rs
Original file line number Diff line number Diff line change
Expand Up @@ -496,11 +496,16 @@
// If we're not on Linux or Android, or the splice() call failed,
// fall back on slower writing.
let mut buf = [0; 1024 * 64];
while let Ok(n) = handle.reader.read(&mut buf) {
if n == 0 {
break;
loop {
match handle.reader.read(&mut buf) {
Ok(n) => {
if n == 0 {
break;
}
stdout_lock.write_all(&buf[..n])?;
}
Err(e) => return Err(e.into()),

Check warning on line 507 in src/uu/cat/src/cat.rs

View check run for this annotation

Codecov / codecov/patch

src/uu/cat/src/cat.rs#L507

Added line #L507 was not covered by tests
}
stdout_lock.write_all(&buf[..n])?;
}

// If the splice() call failed and there has been some data written to
Expand Down
20 changes: 20 additions & 0 deletions tests/by-util/test_cat.rs
Original file line number Diff line number Diff line change
Expand Up @@ -713,6 +713,26 @@ fn test_u_ignored() {
}
}

#[test]
#[cfg(unix)]
fn test_write_fast_read_error() {
use std::os::unix::fs::PermissionsExt;

let (at, mut ucmd) = at_and_ucmd!();

// Create a file with content
at.write("foo", "content");

// Remove read permissions to cause a read error
let file_path = at.plus_as_string("foo");
let mut perms = std::fs::metadata(&file_path).unwrap().permissions();
perms.set_mode(0o000); // No permissions
std::fs::set_permissions(&file_path, perms).unwrap();

// Test that cat fails with permission denied
ucmd.arg("foo").fails().stderr_contains("Permission denied");
}

#[test]
#[cfg(target_os = "linux")]
fn test_appending_same_input_output() {
Expand Down
Loading