Skip to content

Fix underflow in core::str::Searcher::new #16590

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

Merged
merged 2 commits into from
Aug 19, 2014

Conversation

nham
Copy link
Contributor

@nham nham commented Aug 18, 2014

This incidentally fixes #16589, because it will cause MatchIndices to use NaiveSearcher instead of TwoWaySearcher, but I'm not sure #16589 should be closed until the underlying problem in TwoWaySearcher is found.

@nham nham changed the title Fix underflow in core::str::Searcher::new for haystacks of length < 20 Fix underflow in core::str::Searcher::new Aug 18, 2014
@alexcrichton
Copy link
Member

Could you add a test for this as well?

@Gankra
Copy link
Contributor

Gankra commented Aug 18, 2014

@alexcrichton this change only effects which internal algorithm is used to perform a search. If the underlying algorithms are correct (they're not), it should not effect the correctness, so in a sense this can't be tested.

@alexcrichton
Copy link
Member

This states that #16589 is fixed, so couldn't a test for that be added?

@Gankra
Copy link
Contributor

Gankra commented Aug 18, 2014

@alexcrichton sure, but it's more accurate to say the bug has been hidden by it.

"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxanana".contains("nana") should still fail.

@nham
Copy link
Contributor Author

nham commented Aug 19, 2014

@alexcrichton I meant that while this technically resolves #16589, the real problem is that TwoWaySearcher is broken, as @gankro mentioned. I've gone ahead and added a test though.

@asterite
Copy link

In the D programming language every now and then someone comes to the newsgroup saying "I have this strangest bug, this is working wrong", only to get the answer "you are comparing a signed int with an unsigned one". This happens because array lengths are also unsigned ints there.

Be prepared to have these bugs and get similar questions from people using Rust. In my opinion, it makes sense that the length of a vector or an array is unsigned (it can't be negative), but if you make it a signed integer it isn't a big drawback and you will never have these kinds of bugs.

C#'s Array.length is signed: http://msdn.microsoft.com/en-us/library/system.array.length(v=vs.110).aspx

Java's Array length (and other types) are also ints (well, I think they don't have unsigned types).

I never heard anyone running into these bugs in Python, Ruby, Javascript, etc., either.

This program has an unexpected answer:

fn main() {
  let a = [1, 2, 3];
  println!("{}", a.len() > -1);
}

(and, as a side note, this program crashes the compiler:)

fn main() {
  println!("{}", [].len() > -1);
}

Please, consider using unsigned ints as least as possible. Thanks :-)

@alexcrichton
Copy link
Member

@nham, tests such as this are normally added as unit tests, but the core tests are in the coretest library to get around bootstrapping concerns. Could you move the test to that library?

@nham
Copy link
Contributor Author

nham commented Aug 19, 2014

@alexcrichton Done.

bors added a commit that referenced this pull request Aug 19, 2014
This incidentally fixes #16589, because it will cause `MatchIndices` to use `NaiveSearcher` instead of `TwoWaySearcher`, but I'm not sure #16589 should be closed until the underlying problem in `TwoWaySearcher` is found.
@bors bors closed this Aug 19, 2014
@bors bors merged commit 3b0084e into rust-lang:master Aug 19, 2014
@pcwalton
Copy link
Contributor

It is correct to use unsigned types for array lengths. Changing array lengths to be signed is the wrong solution. The right solution is to just warn against things like > -1.

@asterite
Copy link

But in this issue the line was this:

needle.len() > haystack.len() - 20

I don't think the compiler can warn against that...

@imbaczek
Copy link

shouldn't integer overflow (either signed or unsigned) be trapped by a safe language which rust aims to be?

@asterite
Copy link

@imbaczek I thought the same. But maybe Rust only aims to be a memory-safe language, not a non bug-prone language.

@thestinger
Copy link
Contributor

@imbaczek: Rust aims to be competitive in performance with C and C++, and it wouldn't be if it branched on every integer operation. The complexity of the borrow checking and ownership don't make much sense if you have far bigger performance issues. It does expose intrinsics for efficient checked overflow and you could make checked types solely using those. In practice, not many people are going to use them. If you don't know the bounds it makes more sense to use a big integer.

@hatahet
Copy link
Contributor

hatahet commented Aug 24, 2014

This was discussed on /r/rust, and it was pointed out that this still contains a bug if needle.len() > UINT_MAX - 20.

@Gankra
Copy link
Contributor

Gankra commented Aug 24, 2014

@hatahet there is already a PR up for this issue: #16701

bors added a commit to rust-lang-ci/rust that referenced this pull request Feb 25, 2024
…stic-fix, r=Veykril

fix: Fix false positives for "unnecessary else" diagnostic

Completes rust-lang/rust-analyzer#16567 by `@ShoyuVanilla` (see rust-lang/rust-analyzer#16567 (comment))
Fixes rust-lang#16556
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.

"bananas".contains("nana") returns false
9 participants