Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

head: head_backwards for non-seekable files like /proc/* or fifos (named pipes) #5732

Merged

Conversation

cre4ture
Copy link
Contributor

@cre4ture cre4ture commented Dec 27, 2023

addresses issue #5703

  • fixed: head_backwards for byte count
  • fixed: head_backwards for line count
  • when reading from /sys/kernel/profiling: File is seekable but metadata of file provides wrong size information (4096). Apply GNU compatible special handling for small files.

Copy link

GNU testsuite comparison:

Skip an intermittent issue tests/tail/inotify-dir-recreate (fails in this run but passes in the 'main' branch)

Comment on lines 252 to 261
let n = match usize::try_from(n) {
Ok(value) => value,
Err(e) => {
show!(USimpleError::new(
1,
format!("{e}: number of bytes is too large")
));
return Ok(());
}
};
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can be simplify with something like

Suggested change
let n = match usize::try_from(n) {
Ok(value) => value,
Err(e) => {
show!(USimpleError::new(
1,
format!("{e}: number of bytes is too large")
));
return Ok(());
}
};
let n = usize::try_from(n).map_err(|e| {
show!(USimpleError::new(1, format!("{e}: number of bytes is too large")));
e
})?;

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I experimented with it. The problem: The proposed alternative is actually not 100% the same. It makes the function return with an Err(..) (which needs to be converted first). But originally it just prints the error and then returns with Ok().

I personally think this is a bit smelly anyway. But i moved this code just from a different location (cleanup commit will come soon).

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

additionally: I actually can't test this part of code. On 64bit machine usize and u64 is the same. Thus this convertion will only fail on 32 bit (or lower if this exists here)

separator: u8,
) -> std::io::Result<()> {
let n = match usize::try_from(n) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

as it seems to be the same, maybe create a function for this ?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ping ?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ok, i'll do some more experiments :-)

@cre4ture cre4ture changed the title implement head_backwards for non-seekable files like /proc/* or pipes implement head_backwards for non-seekable files like /proc/* or fifos (named pipes) Dec 27, 2023
Copy link

GNU testsuite comparison:

Skip an intermittent issue tests/tail/inotify-dir-recreate (fails in this run but passes in the 'main' branch)

@cre4ture cre4ture marked this pull request as ready for review December 27, 2023 20:13
@cre4ture
Copy link
Contributor Author

@sylvestre can you please check why android was failing? I guess its something with the infrastructure

@@ -243,63 +243,82 @@ fn read_n_lines(input: &mut impl std::io::BufRead, n: u64, separator: u8) -> std
Ok(())
}

fn read_but_last_n_bytes(input: &mut impl std::io::BufRead, n: usize) -> std::io::Result<()> {
fn checked_convert_to_usize_or_print_error(n: u64) -> Option<usize> {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

please rename this function to explain the goal, not the implementation

like
get_bytes()

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The function is used at two places. Once for bytes and once for lines. So we could call it 'get_number_of_bytes_or_lines'.

But to be honest, I do currently not understand why this should improve the readability. The only reason for this function to be called is that the downcast from u64 to usize might not be possible if we are on a 32 bit platform and the user wants us to print all but last with very large number.

Could you please elaborate your proposal a bit more?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I provided a new proposal. Let me know if your good with it.

Copy link

GNU testsuite comparison:

Skip an intermittent issue tests/tail/inotify-dir-recreate (fails in this run but passes in the 'main' branch)

…s_nonseekable_files

# Conflicts:
#	src/uu/head/src/head.rs
Copy link

GNU testsuite comparison:

Skipping an intermittent issue tests/tail/inotify-dir-recreate (passes in this run but fails in the 'main' branch)

@cre4ture cre4ture changed the title implement head_backwards for non-seekable files like /proc/* or fifos (named pipes) head: implement head_backwards for non-seekable files like /proc/* or fifos (named pipes) Dec 28, 2023
@cre4ture cre4ture changed the title head: implement head_backwards for non-seekable files like /proc/* or fifos (named pipes) head: head_backwards for non-seekable files like /proc/* or fifos (named pipes) Dec 28, 2023
@sylvestre
Copy link
Contributor

small different with upstream:
$ /usr/bin/head -c -1 /sys/kernel/profiling
0 (without \n)

$ ./target/debug/coreutils head -c -1 /sys/kernel/profiling
0\n

@cre4ture
Copy link
Contributor Author

small different with upstream: $ /usr/bin/head -c -1 /sys/kernel/profiling 0 (without \n)

$ ./target/debug/coreutils head -c -1 /sys/kernel/profiling 0\n

works now. How did you find this?

Copy link

GNU testsuite comparison:

Congrats! The gnu test tests/head/head-c is no longer failing!
Skipping an intermittent issue tests/tail/inotify-dir-recreate (passes in this run but fails in the 'main' branch)

Copy link

GNU testsuite comparison:

Congrats! The gnu test tests/head/head-c is no longer failing!

@sylvestre
Copy link
Contributor

GNU testsuite comparison:

Congrats! The gnu test tests/head/head-c is no longer failing!

excellent :)

@sylvestre
Copy link
Contributor

small different with upstream: $ /usr/bin/head -c -1 /sys/kernel/profiling 0 (without \n)
$ ./target/debug/coreutils head -c -1 /sys/kernel/profiling 0\n

works now. How did you find this?

this test tests/head/head-c :)

@sylvestre sylvestre merged commit 9b3cc54 into uutils:main Jan 4, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants