[llvm] 8eb2f86 - [CodeGenPrepare] Fold br(freeze(icmp x, const)) to br(icmp(freeze x, const))

Philip Reames via llvm-commits llvm-commits at lists.llvm.org
Wed Mar 11 12:49:10 PDT 2020


The title on this should have been updated before submission as the 
requirement for a branch was relaxed.  Here's a more appropriate title.

[CodeGenPrepare] Fold freeze(icmp x, const) to icmp(freeze x, const)

On 3/11/20 11:16 AM, Juneyoung Lee via llvm-commits wrote:
> Author: Juneyoung Lee
> Date: 2020-03-12T03:16:15+09:00
> New Revision: 8eb2f865c3034934231b1fb3471960191a6f754f
>
> URL: https://github.com/llvm/llvm-project/commit/8eb2f865c3034934231b1fb3471960191a6f754f
> DIFF: https://github.com/llvm/llvm-project/commit/8eb2f865c3034934231b1fb3471960191a6f754f.diff
>
> LOG: [CodeGenPrepare] Fold br(freeze(icmp x, const)) to br(icmp(freeze x, const))
>
> Summary:
> This patch helps CodeGenPrepare move freeze into the icmp when it is used by branch.
> It reenables generation of efficient conditional jumps.
>
> This is only done when at least one of icmp's operands is constant to prevent the transformation from increasing # of freeze instructions.
>
> Performance degradation of MultiSource/Benchmarks/Ptrdist/yacr2/yacr2.test is resolved with this patch.
>
> Checked with Alive2
>
> Reviewers: reames, fhahn, nlopes
>
> Reviewed By: reames
>
> Subscribers: jdoerfert, hiraditya, llvm-commits
>
> Tags: #llvm
>
> Differential Revision: https://reviews.llvm.org/D75859
>
> Added:
>      llvm/test/Transforms/CodeGenPrepare/X86/freeze-icmp.ll
>
> Modified:
>      llvm/lib/CodeGen/CodeGenPrepare.cpp
>
> Removed:
>      
>
>
> ################################################################################
> diff  --git a/llvm/lib/CodeGen/CodeGenPrepare.cpp b/llvm/lib/CodeGen/CodeGenPrepare.cpp
> index 052316f34bb6..262036499b30 100644
> --- a/llvm/lib/CodeGen/CodeGenPrepare.cpp
> +++ b/llvm/lib/CodeGen/CodeGenPrepare.cpp
> @@ -7191,6 +7191,26 @@ bool CodeGenPrepare::optimizeInst(Instruction *I, bool &ModifiedDT) {
>       return false;
>     }
>   
> +  if (FreezeInst *FI = dyn_cast<FreezeInst>(I)) {
> +    // br(freeze(icmp a, const)) -> br(icmp (freeze a), const)
> +    // This helps generate efficient conditional jumps.
> +    if (ICmpInst *II = dyn_cast<ICmpInst>(FI->getOperand(0))) {
> +      auto Op0 = II->getOperand(0), Op1 = II->getOperand(1);
> +      bool Const0 = isa<ConstantInt>(Op0), Const1 = isa<ConstantInt>(Op1);
> +      if (II->hasOneUse() && (Const0 || Const1)) {
> +        if (!Const0 || !Const1) {
> +          auto *F = new FreezeInst(Const0 ? Op1 : Op0, "", II);
> +          F->takeName(FI);
> +          II->setOperand(Const0 ? 1 : 0, F);
> +        }
> +        FI->replaceAllUsesWith(II);
> +        FI->eraseFromParent();
> +        return true;
> +      }
> +    }
> +    return false;
> +  }
> +
>     if (tryToSinkFreeOperands(I))
>       return true;
>   
>
> diff  --git a/llvm/test/Transforms/CodeGenPrepare/X86/freeze-icmp.ll b/llvm/test/Transforms/CodeGenPrepare/X86/freeze-icmp.ll
> new file mode 100644
> index 000000000000..e4febc15c03e
> --- /dev/null
> +++ b/llvm/test/Transforms/CodeGenPrepare/X86/freeze-icmp.ll
> @@ -0,0 +1,75 @@
> +; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
> +; RUN: opt -S -codegenprepare < %s | FileCheck %s
> +
> +target triple = "x86_64-unknown-linux-gnu"
> +
> +define void @f1(i32 %a) {
> +; CHECK-LABEL: @f1(
> +; CHECK-NEXT:    [[FR1:%.*]] = freeze i32 [[A:%.*]]
> +; CHECK-NEXT:    [[C:%.*]] = icmp eq i32 [[FR1]], 0
> +; CHECK-NEXT:    br i1 [[C]], label [[A:%.*]], label [[B:%.*]]
> +; CHECK:       A:
> +; CHECK-NEXT:    call void @g1()
> +; CHECK-NEXT:    ret void
> +; CHECK:       B:
> +; CHECK-NEXT:    call void @g2()
> +; CHECK-NEXT:    ret void
> +;
> +  %c = icmp eq i32 %a, 0
> +  %fr = freeze i1 %c
> +  br i1 %fr, label %A, label %B
> +A:
> +  call void @g1()
> +  ret void
> +B:
> +  call void @g2()
> +  ret void
> +}
> +
> +define void @f2(i32 %a) {
> +; CHECK-LABEL: @f2(
> +; CHECK-NEXT:    [[FR1:%.*]] = freeze i32 [[A:%.*]]
> +; CHECK-NEXT:    [[C:%.*]] = icmp eq i32 0, [[FR1]]
> +; CHECK-NEXT:    br i1 [[C]], label [[A:%.*]], label [[B:%.*]]
> +; CHECK:       A:
> +; CHECK-NEXT:    call void @g1()
> +; CHECK-NEXT:    ret void
> +; CHECK:       B:
> +; CHECK-NEXT:    call void @g2()
> +; CHECK-NEXT:    ret void
> +;
> +  %c = icmp eq i32 0, %a
> +  %fr = freeze i1 %c
> +  br i1 %fr, label %A, label %B
> +A:
> +  call void @g1()
> +  ret void
> +B:
> +  call void @g2()
> +  ret void
> +}
> +
> +define void @f3(i32 %a) {
> +; CHECK-LABEL: @f3(
> +; CHECK-NEXT:    [[C:%.*]] = icmp eq i32 0, 1
> +; CHECK-NEXT:    br i1 [[C]], label [[A:%.*]], label [[B:%.*]]
> +; CHECK:       A:
> +; CHECK-NEXT:    call void @g1()
> +; CHECK-NEXT:    ret void
> +; CHECK:       B:
> +; CHECK-NEXT:    call void @g2()
> +; CHECK-NEXT:    ret void
> +;
> +  %c = icmp eq i32 0, 1
> +  %fr = freeze i1 %c
> +  br i1 %fr, label %A, label %B
> +A:
> +  call void @g1()
> +  ret void
> +B:
> +  call void @g2()
> +  ret void
> +}
> +
> +declare void @g1()
> +declare void @g2()
>
>
>          
> _______________________________________________
> llvm-commits mailing list
> llvm-commits at lists.llvm.org
> https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits


More information about the llvm-commits mailing list