-
Notifications
You must be signed in to change notification settings - Fork 12.6k
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
[JumpThreading] Missing optimization: thread over a nearly empty basicblock #76609
Comments
Hi, I find this one interesting. Can you mention a good starting point? |
@elhewaty , I once worked on similar things in SimplifyCFG and JumpThreading pass (#67275). A possible solution is to relax the non-empty phis constraint at llvm-project/llvm/lib/Transforms/Utils/Local.cpp Line 1017 in a02a0e8
, and then handle the empty basicblock without phi correctly. |
@XChy why can't the branch in |
@elhewaty , the phi in |
This missed optimization opportunity also exists in CPython/_ctypes/_ctypes.c. |
) Fixes #76609 This patch does: - relax the phis constraint in `CanRedirectPredsOfEmptyBBToSucc` - guarantee the BB has multiple different predecessors to redirect, so that we can handle the case without phis in BB. Without this change and phi constraint, we may redirect the CommonPred. The motivation is consistent with JumpThreading. We always want the branch to jump more direct to the destination, without passing the middle block. In this way, we can expose more other optimization opportunities. An obivous example proposed by @dtcxzyw is like: ```llvm define i32 @test(...) { entry: br i1 %c, label %do.end, label %if.then if.then: ; preds = %entry %call2 = call i32 @dummy() %tobool3.not = icmp eq i32 %call2, 0 br i1 %tobool3.not, label %do.end, label %return do.end: ; preds = %entry, %if.then br label %return return: ; preds = %if.then, %do.end %retval.0 = phi i32 [ 0, %do.end ], [ %call2, %if.then ] ret i32 %retval.0 } ``` `entry` can directly jump to return, without passing `do.end`, and then the if-else pattern can be simplified further: ```llvm define i32 @test(...) { entry: br i1 %c, label %return, label %if.then if.then: ; preds = %entry %call2 = call i32 @dummy() br label %return return: ; preds = %if.then %retval.0 = phi i32 [ 0, %entry ], [ %call2, %if.then ] ret i32 %retval.0 } ```
Alive2 proof: https://alive2.llvm.org/ce/z/Lv9e4r
Description:
can be folded to:
The conditional branch in BB
entry
can thread directly through nearly empty BBelse
toreturn
.Real-world motivation
This snippet of IR is derived from auto-generated qemu/xxx/qapi-visit-dump.c (after inline and O3 pipeline).
The example above is a reduced version. If you're interested in the original suboptimal IR and optimal IR, contact me to get it(Too big to upload here).
Let me know if you can confirm that it's an optimization opportunity, thanks.
The text was updated successfully, but these errors were encountered: