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

properly handle EOF in BufReader::peek #130042

Merged
merged 1 commit into from
Sep 15, 2024

Conversation

lolbinarycat
Copy link
Contributor

previously this would cause an infinite loop due to it being unable to read n bytes.

previously this would cause an infinite loop due to it being
unable to read `n` bytes.
@rustbot
Copy link
Collaborator

rustbot commented Sep 6, 2024

Thanks for the pull request, and welcome! The Rust team is excited to review your changes, and you should hear from @Amanieu (or someone else) some time within the next two weeks.

Please see the contribution instructions for more information. Namely, in order to ensure the minimum review times lag, PR authors and assigned reviewers should ensure that the review label (S-waiting-on-review and S-waiting-on-author) stays updated, invoking these commands when appropriate:

  • @rustbot author: the review is finished, PR author should check the comments and take action accordingly
  • @rustbot review: the author is ready for a review, this PR will be queued again in the reviewer's queue

@rustbot rustbot added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-libs Relevant to the library team, which will review and decide on the PR/issue. labels Sep 6, 2024
@workingjubilee
Copy link
Member

@lolbinarycat Can we get a test with the code that would cause the infinite loop?

@Amanieu
Copy link
Member

Amanieu commented Sep 6, 2024

I think a better algorithm would be to remove the loop and do this instead:

  • If enough bytes are already available in the buffer, return those immediately without doing any backshift.
  • Otherwise backshift the buffer and then perform a single read operation on the underlying reader.
  • If enough bytes were read to satisfy the peek, return those, otherwise return a shorter slice with the bytes that are available.

Always backshifting before reading will minimize the number of reads on the underlying reader, and we can avoid backshifting if enough bytes are already available in the buffer.

If the user really wants to issue multiple reads to the underlying reader then we should have a separate peek_exact method which does this.

@lolbinarycat lolbinarycat added the F-bufreader_peek `#![feature(bufreader_peek)]` label Sep 6, 2024
@lolbinarycat
Copy link
Contributor Author

@workingjubilee I actually added such a test to the end of the doctest, trying to peek once EOF has been reached would trigger the bug.

@Amanieu performing multiple reads is the entire purpose of this feature. if you don't care about robustness against short reads, you can just hackily use fill_buf. programs generally should not have their behavior be dependent on read boundaries.

@lolbinarycat
Copy link
Contributor Author

any status on moving this forward? either we should merge this fix, or mark bufreader_peek as an incomplete feature, because as it stands, any program using this is will hang as soon as it encounters EOF, and there is no possible workaround, unless you want to wrap every seek with alarm calls using unsafe ffi.

if we want to change the behavior or api of this feature, that should be discussed in a separate issue.

@Amanieu
Copy link
Member

Amanieu commented Sep 15, 2024

Sure, let's just fix this for now, we can discuss the API separately.

@bors r+

@bors
Copy link
Contributor

bors commented Sep 15, 2024

📌 Commit dfdbf63 has been approved by Amanieu

It is now in the queue for this repository.

@bors bors added S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Sep 15, 2024
Zalathar added a commit to Zalathar/rust that referenced this pull request Sep 15, 2024
…=Amanieu

properly handle EOF in BufReader::peek

previously this would cause an infinite loop due to it being unable to read `n` bytes.
/// `n` must be less than `capacity`.
/// `n` must be less than or equal to `capacity`.
///
/// the returned slice may be less than `n` bytes long if
Copy link
Contributor

@leo60228 leo60228 Sep 15, 2024

Choose a reason for hiding this comment

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

"the" should be capitalized, shouldn't it?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

yeah, nice catch. i plan on doing another pass at the documentation once the finer details of the behavior are worked out, possibly earlier.

however, this is a very minor typo, and i don't think it's worth blocking such a critical fix on such a minor typo.

bors added a commit to rust-lang-ci/rust that referenced this pull request Sep 15, 2024
Rollup of 6 pull requests

Successful merges:

 - rust-lang#130042 (properly handle EOF in BufReader::peek)
 - rust-lang#130061 (Add `NonNull` convenience methods to `Box` and `Vec`)
 - rust-lang#130202 (set `download-ci-llvm = true` by default on "library" and "tools" profiles)
 - rust-lang#130214 (MaybeUninit::zeroed: mention that padding is not zeroed)
 - rust-lang#130353 (Make some lint doctests compatible with `--stage=0`)
 - rust-lang#130370 (unstable-book: `trait_upcasting` example should not have `#![allow(incomplete_features)]`)

r? `@ghost`
`@rustbot` modify labels: rollup
bors added a commit to rust-lang-ci/rust that referenced this pull request Sep 15, 2024
Rollup of 6 pull requests

Successful merges:

 - rust-lang#130042 (properly handle EOF in BufReader::peek)
 - rust-lang#130061 (Add `NonNull` convenience methods to `Box` and `Vec`)
 - rust-lang#130202 (set `download-ci-llvm = true` by default on "library" and "tools" profiles)
 - rust-lang#130214 (MaybeUninit::zeroed: mention that padding is not zeroed)
 - rust-lang#130353 (Make some lint doctests compatible with `--stage=0`)
 - rust-lang#130370 (unstable-book: `trait_upcasting` example should not have `#![allow(incomplete_features)]`)

r? `@ghost`
`@rustbot` modify labels: rollup
@bors bors merged commit e02e6bf into rust-lang:master Sep 15, 2024
6 checks passed
@rustbot rustbot added this to the 1.83.0 milestone Sep 15, 2024
rust-timer added a commit to rust-lang-ci/rust that referenced this pull request Sep 15, 2024
Rollup merge of rust-lang#130042 - lolbinarycat:bufreaker_peek_eof, r=Amanieu

properly handle EOF in BufReader::peek

previously this would cause an infinite loop due to it being unable to read `n` bytes.
@bors
Copy link
Contributor

bors commented Sep 15, 2024

⌛ Testing commit dfdbf63 with merge bc486f3...

@workingjubilee
Copy link
Member

chill, bors.
@bors r-

@bors bors added S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. and removed S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. labels Sep 15, 2024
@workingjubilee
Copy link
Member

@bors r-

@workingjubilee
Copy link
Member

@bors retry

@bors bors removed the S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. label Sep 15, 2024
@bors bors added the S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. label Sep 15, 2024
@workingjubilee
Copy link
Member

@bors r-

@bors bors added S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. and removed S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. labels Sep 15, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
F-bufreader_peek `#![feature(bufreader_peek)]` S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. T-libs Relevant to the library team, which will review and decide on the PR/issue.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants