mirror of
https://github.com/uutils/coreutils.git
synced 2025-07-07 13:35:00 +00:00
Merge pull request #8314 from bvinc/tail_zero
Some checks are pending
CICD / Style/cargo-deny (push) Waiting to run
CICD / MinRustV (push) Waiting to run
CICD / Dependencies (push) Waiting to run
CICD / Tests/BusyBox test suite (push) Blocked by required conditions
CICD / Tests/Toybox test suite (push) Blocked by required conditions
CICD / Code Coverage (push) Waiting to run
CICD / Separate Builds (push) Waiting to run
CICD / Test all features separately (push) Blocked by required conditions
CICD / Build/SELinux (push) Blocked by required conditions
CICD / Build (push) Blocked by required conditions
CICD / Style/deps (push) Waiting to run
CICD / Documentation/warnings (push) Waiting to run
CICD / Build/Makefile (push) Blocked by required conditions
CICD / Build/stable (push) Blocked by required conditions
CICD / Build/nightly (push) Blocked by required conditions
CICD / Binary sizes (push) Blocked by required conditions
GnuTests / Run GNU tests (push) Waiting to run
Android / Test builds (push) Waiting to run
Code Quality / Style/format (push) Waiting to run
Code Quality / Style/lint (push) Waiting to run
Code Quality / Style/spelling (push) Waiting to run
Code Quality / Style/toml (push) Waiting to run
Code Quality / Style/Python (push) Waiting to run
Code Quality / Pre-commit hooks (push) Waiting to run
FreeBSD / Style and Lint (push) Waiting to run
FreeBSD / Tests (push) Waiting to run
Some checks are pending
CICD / Style/cargo-deny (push) Waiting to run
CICD / MinRustV (push) Waiting to run
CICD / Dependencies (push) Waiting to run
CICD / Tests/BusyBox test suite (push) Blocked by required conditions
CICD / Tests/Toybox test suite (push) Blocked by required conditions
CICD / Code Coverage (push) Waiting to run
CICD / Separate Builds (push) Waiting to run
CICD / Test all features separately (push) Blocked by required conditions
CICD / Build/SELinux (push) Blocked by required conditions
CICD / Build (push) Blocked by required conditions
CICD / Style/deps (push) Waiting to run
CICD / Documentation/warnings (push) Waiting to run
CICD / Build/Makefile (push) Blocked by required conditions
CICD / Build/stable (push) Blocked by required conditions
CICD / Build/nightly (push) Blocked by required conditions
CICD / Binary sizes (push) Blocked by required conditions
GnuTests / Run GNU tests (push) Waiting to run
Android / Test builds (push) Waiting to run
Code Quality / Style/format (push) Waiting to run
Code Quality / Style/lint (push) Waiting to run
Code Quality / Style/spelling (push) Waiting to run
Code Quality / Style/toml (push) Waiting to run
Code Quality / Style/Python (push) Waiting to run
Code Quality / Pre-commit hooks (push) Waiting to run
FreeBSD / Style and Lint (push) Waiting to run
FreeBSD / Tests (push) Waiting to run
tail: fix tailing /dev/zero
This commit is contained in:
commit
b9a790b476
4 changed files with 33 additions and 23 deletions
|
@ -23,7 +23,7 @@ clap = { workspace = true }
|
|||
libc = { workspace = true }
|
||||
memchr = { workspace = true }
|
||||
notify = { workspace = true }
|
||||
uucore = { workspace = true, features = ["parser"] }
|
||||
uucore = { workspace = true, features = ["fs", "parser"] }
|
||||
same-file = { workspace = true }
|
||||
|
||||
[target.'cfg(windows)'.dependencies]
|
||||
|
|
|
@ -158,7 +158,6 @@ impl FileExtTail for File {
|
|||
pub trait MetadataExtTail {
|
||||
fn is_tailable(&self) -> bool;
|
||||
fn got_truncated(&self, other: &Metadata) -> UResult<bool>;
|
||||
fn get_block_size(&self) -> u64;
|
||||
fn file_id_eq(&self, other: &Metadata) -> bool;
|
||||
}
|
||||
|
||||
|
@ -180,17 +179,6 @@ impl MetadataExtTail for Metadata {
|
|||
Ok(other.len() < self.len() && other.modified()? != self.modified()?)
|
||||
}
|
||||
|
||||
fn get_block_size(&self) -> u64 {
|
||||
#[cfg(unix)]
|
||||
{
|
||||
self.blocks()
|
||||
}
|
||||
#[cfg(not(unix))]
|
||||
{
|
||||
self.len()
|
||||
}
|
||||
}
|
||||
|
||||
fn file_id_eq(&self, _other: &Metadata) -> bool {
|
||||
#[cfg(unix)]
|
||||
{
|
||||
|
|
|
@ -26,7 +26,7 @@ use args::{FilterMode, Settings, Signum, parse_args};
|
|||
use chunks::ReverseChunks;
|
||||
use follow::Observer;
|
||||
use memchr::{memchr_iter, memrchr_iter};
|
||||
use paths::{FileExtTail, HeaderPrinter, Input, InputKind, MetadataExtTail};
|
||||
use paths::{FileExtTail, HeaderPrinter, Input, InputKind};
|
||||
use same_file::Handle;
|
||||
use std::cmp::Ordering;
|
||||
use std::collections::HashMap;
|
||||
|
@ -169,14 +169,15 @@ fn tail_file(
|
|||
}
|
||||
observer.add_bad_path(path, input.display_name.as_str(), false)?;
|
||||
} else if input.is_tailable() {
|
||||
let metadata = path.metadata().ok();
|
||||
match File::open(path) {
|
||||
Ok(mut file) => {
|
||||
let st = file.metadata()?;
|
||||
let blksize_limit = uucore::fs::sane_blksize::sane_blksize_from_metadata(&st);
|
||||
header_printer.print_input(input);
|
||||
let mut reader;
|
||||
if !settings.presume_input_pipe
|
||||
&& file.is_seekable(if input.is_stdin() { offset } else { 0 })
|
||||
&& metadata.as_ref().unwrap().get_block_size() > 0
|
||||
&& (!st.is_file() || st.len() > blksize_limit)
|
||||
{
|
||||
bounded_tail(&mut file, settings);
|
||||
reader = BufReader::new(file);
|
||||
|
@ -448,6 +449,7 @@ fn backwards_thru_file(file: &mut File, num_delimiters: u64, delimiter: u8) {
|
|||
/// being a nice performance win for very large files.
|
||||
fn bounded_tail(file: &mut File, settings: &Settings) {
|
||||
debug_assert!(!settings.presume_input_pipe);
|
||||
let mut limit = None;
|
||||
|
||||
// Find the position in the file to start printing from.
|
||||
match &settings.mode {
|
||||
|
@ -462,9 +464,8 @@ fn bounded_tail(file: &mut File, settings: &Settings) {
|
|||
return;
|
||||
}
|
||||
FilterMode::Bytes(Signum::Negative(count)) => {
|
||||
let len = file.seek(SeekFrom::End(0)).unwrap();
|
||||
file.seek(SeekFrom::End(-((*count).min(len) as i64)))
|
||||
.unwrap();
|
||||
file.seek(SeekFrom::End(-(*count as i64))).unwrap();
|
||||
limit = Some(*count);
|
||||
}
|
||||
FilterMode::Bytes(Signum::Positive(count)) if count > &1 => {
|
||||
// GNU `tail` seems to index bytes and lines starting at 1, not
|
||||
|
@ -477,10 +478,7 @@ fn bounded_tail(file: &mut File, settings: &Settings) {
|
|||
_ => {}
|
||||
}
|
||||
|
||||
// Print the target section of the file.
|
||||
let stdout = stdout();
|
||||
let mut stdout = stdout.lock();
|
||||
io::copy(file, &mut stdout).unwrap();
|
||||
print_target_section(file, limit);
|
||||
}
|
||||
|
||||
fn unbounded_tail<T: Read>(reader: &mut BufReader<T>, settings: &Settings) -> UResult<()> {
|
||||
|
@ -547,6 +545,21 @@ fn unbounded_tail<T: Read>(reader: &mut BufReader<T>, settings: &Settings) -> UR
|
|||
Ok(())
|
||||
}
|
||||
|
||||
fn print_target_section<R>(file: &mut R, limit: Option<u64>)
|
||||
where
|
||||
R: Read + ?Sized,
|
||||
{
|
||||
// Print the target section of the file.
|
||||
let stdout = stdout();
|
||||
let mut stdout = stdout.lock();
|
||||
if let Some(limit) = limit {
|
||||
let mut reader = file.take(limit);
|
||||
io::copy(&mut reader, &mut stdout).unwrap();
|
||||
} else {
|
||||
io::copy(file, &mut stdout).unwrap();
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
|
||||
|
|
|
@ -4923,3 +4923,12 @@ fn test_failed_write_is_reported() {
|
|||
.fails()
|
||||
.stderr_is("tail: No space left on device\n");
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[cfg(target_os = "linux")]
|
||||
fn test_dev_zero() {
|
||||
new_ucmd!()
|
||||
.args(&["-c", "1", "/dev/zero"])
|
||||
.succeeds()
|
||||
.stdout_only("\0");
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue