-
Notifications
You must be signed in to change notification settings - Fork 13k
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
Bounds check that should not be eliminated is #54214
Comments
I've had a similar problem (with overflow checks instead of bounds checks) in #38136, and I suspect that this issue has the same cause: LLVM noticing (thanks to LTO) that an out of bounds index would lead to an infinite side-effect-free loop, which it considers UB (#28728) and consequently takes as justification to remove the bounds check entirely. |
Hmm… At the same time, somehow I couldn't reproduce with a single crate (where it does keep the overflow check). So maybe there's something a bit more deep than that? Anyway, notifying #28728 of the issue, given no one seemed to have mentioned |
Minified reproducer: #![no_std]
#[no_mangle]
pub extern fn bar(x: &[u8; 255], y: u8) -> u8 {
x[y as usize]
}
#[panic_handler]
fn on_panic_loop(_unused: &core::panic::PanicInfo) -> ! {
loop {}
}
Compile with |
NB: |
Just coming back here, I think this should be tagged I-unsound, given it's generating unsafe code with only safe code. Especially now that |
Actually nevermind, this really is a duplicate of #28728 anyway, so I guess I can close it. |
Originally tested with
rustc 1.29.0-nightly (e94df4acb 2018-07-31)
. Also reproduced (for amd64, wasm didn't compile) withrustc 1.30.0-nightly (90d36fb59 2018-09-13)
andrustc 1.28.0-nightly (b907d9665 2018-06-13)
. The details below will concern therustc 1.29.0-nightly (e94df4acb 2018-07-31)
.This issue appears to reproduce only with two crates and optimizations turned on. It may be an upstream LLVM issue, given I'm not sure whether
--emit=llvm-ir
already includes some LLVM-made optimizations or not. Basically, the issue is not there in--emit=mir
, but is there in--emit=llvm-ir
.With the following code in crate
stuff
:And the following code into the main crate (that has
stuff
as a dependency):With this in the main Cargo.toml:
Then the following commands:
Both show code that has no bounds check:
However, I would think a bounds check is required here, in case
len
is actually returned as 0, as the index to 0 would otherwise read into uninitialized memory (that should be safely hidden behind theData
interface)Do I miss something obvious?
The bounds check appears to disappear between MIR and LLVM IR:
becomes
The text was updated successfully, but these errors were encountered: