mirror of
https://github.com/RGBCube/uutils-coreutils
synced 2025-09-15 19:36:16 +00:00
cat: Do not assume complete writes
This commit is contained in:
parent
c1079e0b1c
commit
d002810a47
1 changed files with 13 additions and 11 deletions
|
@ -44,21 +44,23 @@ pub(super) fn write_fast_using_splice<R: FdReadable>(
|
|||
}
|
||||
}
|
||||
|
||||
/// Caller must ensure that `num_bytes <= BUF_SIZE`, otherwise this function
|
||||
/// will panic. The way we use this function in `write_fast_using_splice`
|
||||
/// above is safe because `splice` is set to write at most `BUF_SIZE` to the
|
||||
/// pipe.
|
||||
#[inline]
|
||||
/// Move exactly `num_bytes` bytes from `read_fd` to `write_fd`.
|
||||
///
|
||||
/// Panics if not enough bytes can be read.
|
||||
fn copy_exact(read_fd: RawFd, write_fd: RawFd, num_bytes: usize) -> nix::Result<()> {
|
||||
let mut left = num_bytes;
|
||||
let mut buf = [0; BUF_SIZE];
|
||||
loop {
|
||||
let read = unistd::read(read_fd, &mut buf[..left])?;
|
||||
let written = unistd::write(write_fd, &buf[..read])?;
|
||||
left -= written;
|
||||
if left == 0 {
|
||||
break;
|
||||
while left > 0 {
|
||||
let read = unistd::read(read_fd, &mut buf)?;
|
||||
assert_ne!(read, 0, "unexpected end of pipe");
|
||||
let mut written = 0;
|
||||
while written < read {
|
||||
match unistd::write(write_fd, &buf[written..read])? {
|
||||
0 => panic!(),
|
||||
n => written += n,
|
||||
}
|
||||
}
|
||||
left -= read;
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue