-
Notifications
You must be signed in to change notification settings - Fork 12.9k
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
.next().unwrap_unchecked()
on Iterator doesn't optimize as expected
#107681
Comments
It's not sufficient for the block to dominate, we also need the assume to post-dominate and there to be no implicit control flow. I think from the LLVM side, the better way to look at this is that the edge to the end block is dead because it would result in assume(false). One could interpret this is a degenerate jump threading optimization. |
This should fix rust-lang/rust#107681. Return undefined to a noundef return value is undefined. Example: ``` define noundef i32 @test_ret_noundef(i1 %cond) { entry: br i1 %cond, label %bb1, label %bb2 bb1: br label %bb2 bb2: %r = phi i32 [ undef, %entry ], [ 1, %bb1 ] ret i32 %r } ``` Reviewed By: nikic Differential Revision: https://reviews.llvm.org/D144319
This should fix rust-lang/rust#107681. Return undefined to a noundef return value is undefined. Example: ``` define noundef i32 @test_ret_noundef(i1 %cond) { entry: br i1 %cond, label %bb1, label %bb2 bb1: br label %bb2 bb2: %r = phi i32 [ undef, %entry ], [ 1, %bb1 ] ret i32 %r } ``` Differential Revision: https://reviews.llvm.org/D144319
This should fix rust-lang/rust#107681. Return undefined to a noundef return value is undefined. Example: ``` define noundef i32 @test_ret_noundef(i1 %cond) { entry: br i1 %cond, label %bb1, label %bb2 bb1: br label %bb2 bb2: %r = phi i32 [ undef, %entry ], [ 1, %bb1 ] ret i32 %r } ``` Reviewed By: nikic Differential Revision: https://reviews.llvm.org/D144319
This should fix rust-lang/rust#107681. Return undefined to a noundef return value is undefined. Example: ``` define noundef i32 @test_ret_noundef(i1 %cond) { entry: br i1 %cond, label %bb1, label %bb2 bb1: br label %bb2 bb2: %r = phi i32 [ undef, %entry ], [ 1, %bb1 ] ret i32 %r } ``` Differential Revision: https://reviews.llvm.org/D144319
This should fix rust-lang/rust#107681. Return undefined to a noundef return value is undefined. Example: ``` define noundef i32 @test_ret_noundef(i1 %cond) { entry: br i1 %cond, label %bb1, label %bb2 bb1: br label %bb2 bb2: %r = phi i32 [ undef, %entry ], [ 1, %bb1 ] ret i32 %r } ``` Reviewed By: nikic Differential Revision: https://reviews.llvm.org/D144319
This should fix rust-lang/rust#107681. Return undefined to a noundef return value is undefined. Example: ``` define noundef i32 @test_ret_noundef(i1 %cond) { entry: br i1 %cond, label %bb1, label %bb2 bb1: br label %bb2 bb2: %r = phi i32 [ undef, %entry ], [ 1, %bb1 ] ret i32 %r } ``` Reviewed By: nikic Differential Revision: https://reviews.llvm.org/D144319
Hi, I'm pretty new to rust, so please forgive me if this sounds ignorant, but how did you get the asm equivalent of your code? |
@Joymfl there are various ways to do that
|
@the8472 thanks! Just tried out |
Upstream patch: https://reviews.llvm.org/D144319. |
Upstream issue: llvm/llvm-project#60717 |
LLVM 19 no longer seems to solve this problem, and I suspect it has something to do with inline changes. Still keeping llvm-fixed-upstream, I'll look into that this week. |
Bisected to: #127113 |
@rustbot label +llvm-fixed-upstream |
Confirmed fixed by #127513, needs codegen test. |
We can finally close it. 🥲 |
Add a set of tests for LLVM 19 Close rust-lang#107681. Close rust-lang#118306. Close rust-lang#126585. r? compiler
Add a set of tests for LLVM 19 Close rust-lang#107681. Close rust-lang#118306. Close rust-lang#126585. r? compiler try-job: i686-msvc try-job: arm-android try-job: test-various
Add a set of tests for LLVM 19 Close rust-lang#107681. Close rust-lang#118306. Close rust-lang#126585. r? compiler try-job: i686-msvc try-job: arm-android try-job: test-various
Add a set of tests for LLVM 19 Close rust-lang#107681. Close rust-lang#118306. Close rust-lang#126585. r? compiler try-job: i686-msvc try-job: arm-android try-job: test-various
Add a set of tests for LLVM 19 Close rust-lang#107681. Close rust-lang#118306. Close rust-lang#126585. r? compiler try-job: i686-msvc try-job: arm-android try-job: test-various
Add a set of tests for LLVM 19 Close rust-lang#107681. Close rust-lang#118306. Close rust-lang#126585. r? compiler
Add a set of tests for LLVM 19 Close rust-lang#107681. Close rust-lang#118306. Close rust-lang#126585. r? compiler
I appreciate your perseverance here, @DianQK ! |
This should fix rust-lang/rust#107681. Return undefined to a noundef return value is undefined. Example: ``` define noundef i32 @test_ret_noundef(i1 %cond) { entry: br i1 %cond, label %bb1, label %bb2 bb1: br label %bb2 bb2: %r = phi i32 [ undef, %entry ], [ 1, %bb1 ] ret i32 %r } ``` Reviewed By: nikic Differential Revision: https://reviews.llvm.org/D144319
This should fix rust-lang/rust#107681. Return undefined to a noundef return value is undefined. Example: ``` define noundef i32 @test_ret_noundef(i1 %cond) { entry: br i1 %cond, label %bb1, label %bb2 bb1: br label %bb2 bb2: %r = phi i32 [ undef, %entry ], [ 1, %bb1 ] ret i32 %r } ``` Differential Revision: https://reviews.llvm.org/D144319
Update: per #107681 (comment), this will be fixed with LLVM 19
(Context: this is a minimized example of the behaviour I hit while working on https://github.com/rust-lang/rust/pull/107634/files#r1096624164)
I tried this code: https://rust.godbolt.org/z/EjWscs1e9
I expected to see this happen: the code would read and bump the pointer in the iterator without checking the end, something like
Instead, this happened: it still checks the iterator ending condition
Dunno where the problem is here -- could be LLVM, could be how the functions are written, could be how MIR handles things...
LLVM after optimizing:
Looks like CSE figured out that it's assuming the same thing as the
br
condition instart
, but nothing moved it up tostart
even though that block dominates the assume? If it had, then I think the the branch and compare might have properly disappeared?The text was updated successfully, but these errors were encountered: