yes: remove cfg & move ownership of buffer to fn exec

This commit is contained in:
oech3
2026-04-30 22:01:53 +09:00
committed by Daniel Hofstetter
parent 6b75bae3ce
commit 3e3daaa347
+11 -13
View File
@@ -27,16 +27,9 @@ pub fn uumain(args: impl uucore::Args) -> UResult<()> {
let matches = uucore::clap_localization::handle_clap_result(uu_app(), args)?;
#[allow(clippy::unwrap_used, reason = "clap provides 'y' by default")]
let mut buffer = args_into_buffer(matches.get_many::<OsString>("STRING").unwrap())?;
#[cfg(any(target_os = "linux", target_os = "android"))]
let aligned_before_growing = PAGE_SIZE.is_multiple_of(buffer.len());
let buffer = args_into_buffer(matches.get_many::<OsString>("STRING").unwrap())?;
prepare_buffer(&mut buffer);
#[cfg(any(target_os = "linux", target_os = "android"))]
let res = exec(&buffer, aligned_before_growing);
#[cfg(not(any(target_os = "linux", target_os = "android")))]
let res = exec(&buffer);
match res {
match exec(buffer) {
Ok(()) => Ok(()),
// On Windows, silently handle broken pipe since there's no SIGPIPE
#[cfg(windows)]
@@ -98,7 +91,7 @@ fn args_into_buffer<'a>(i: impl Iterator<Item = &'a OsString>) -> UResult<Vec<u8
/// Assumes buf holds a single output line forged from the command line arguments, copies it
/// repeatedly until the buffer holds as many copies as it can
fn prepare_buffer(buf: &mut Vec<u8>) {
fn repeat_content_to_capacity(buf: &mut Vec<u8>) {
let line_len = buf.len();
debug_assert!(line_len > 0, "buffer is not empty since we have newline");
let target_size = line_len * (buf.capacity() / line_len); // 0 if line_len is already large enough
@@ -111,7 +104,9 @@ fn prepare_buffer(buf: &mut Vec<u8>) {
}
#[cfg(not(any(target_os = "linux", target_os = "android")))]
pub fn exec(bytes: &[u8]) -> io::Result<()> {
pub fn exec(mut bytes: Vec<u8>) -> io::Result<()> {
repeat_content_to_capacity(&mut bytes);
let bytes = bytes.as_slice();
let mut stdout = io::stdout().lock();
loop {
stdout.write_all(bytes)?;
@@ -119,8 +114,11 @@ pub fn exec(bytes: &[u8]) -> io::Result<()> {
}
#[cfg(any(target_os = "linux", target_os = "android"))]
pub fn exec(bytes: &[u8], aligned: bool) -> io::Result<()> {
pub fn exec(mut bytes: Vec<u8>) -> io::Result<()> {
use uucore::pipes::{pipe, splice, tee};
let aligned = PAGE_SIZE.is_multiple_of(bytes.len());
repeat_content_to_capacity(&mut bytes);
let bytes = bytes.as_slice();
let mut stdout = io::stdout(); // no need to lock with zero-copy
// don't show any error from fast-path and fallback to write for proper message
if let Ok((p_read, mut p_write)) = pipe()
@@ -182,7 +180,7 @@ mod tests {
for (line, final_len) in tests {
let mut v = Vec::with_capacity(BUF_SIZE);
v.extend(std::iter::repeat_n(b'a', line));
prepare_buffer(&mut v);
repeat_content_to_capacity(&mut v);
assert_eq!(v.len(), final_len);
}
}