diff options
| author | Kazu Hirata <kazu@google.com> | 2020-01-08 06:57:36 -0800 |
|---|---|---|
| committer | Kazu Hirata <kazu@google.com> | 2020-01-08 06:57:36 -0800 |
| commit | ead815924e6ebeaf02c31c37ebf7a560b5fdf67b (patch) | |
| tree | aff6e36937fef603deb76b190ff6d72c7ef1e88d /llvm/test/Transforms/JumpThreading | |
| parent | dac7b23cc3efbb4ccb6a9ea101f367f866f334e2 (diff) | |
| download | bcm5719-llvm-ead815924e6ebeaf02c31c37ebf7a560b5fdf67b.tar.gz bcm5719-llvm-ead815924e6ebeaf02c31c37ebf7a560b5fdf67b.zip | |
[JumpThreading] Thread jumps through two basic blocks
Summary:
This patch teaches JumpThreading.cpp to thread through two basic
blocks like:
bb3:
%var = phi i32* [ null, %bb1 ], [ @a, %bb2 ]
%tobool = icmp eq i32 %cond, 0
br i1 %tobool, label %bb4, label ...
bb4:
%cmp = icmp eq i32* %var, null
br i1 %cmp, label bb5, label bb6
by duplicating basic blocks like bb3 above. Once we duplicate bb3 as
bb3.dup and redirect edge bb2->bb3 to bb2->bb3.dup, we have:
bb3:
%var = phi i32* [ @a, %bb2 ]
%tobool = icmp eq i32 %cond, 0
br i1 %tobool, label %bb4, label ...
bb3.dup:
%var = phi i32* [ null, %bb1 ]
%tobool = icmp eq i32 %cond, 0
br i1 %tobool, label %bb4, label ...
bb4:
%cmp = icmp eq i32* %var, null
br i1 %cmp, label bb5, label bb6
Then the existing code in JumpThreading.cpp can thread edge
bb3.dup->bb4 through bb4 and eventually create bb3.dup->bb5.
Reviewers: wmi
Subscribers: hiraditya, jfb, llvm-commits
Tags: #llvm
Differential Revision: https://reviews.llvm.org/D70247
Diffstat (limited to 'llvm/test/Transforms/JumpThreading')
| -rw-r--r-- | llvm/test/Transforms/JumpThreading/thread-two-bbs1.ll | 59 | ||||
| -rw-r--r-- | llvm/test/Transforms/JumpThreading/thread-two-bbs2.ll | 56 |
2 files changed, 115 insertions, 0 deletions
diff --git a/llvm/test/Transforms/JumpThreading/thread-two-bbs1.ll b/llvm/test/Transforms/JumpThreading/thread-two-bbs1.ll new file mode 100644 index 00000000000..1b5f5cb14ae --- /dev/null +++ b/llvm/test/Transforms/JumpThreading/thread-two-bbs1.ll @@ -0,0 +1,59 @@ +; RUN: opt < %s -jump-threading -S -verify | FileCheck %s + +target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +@a = global i32 0, align 4 + +define void @foo(i32 %cond1, i32 %cond2) { +; CHECK-LABEL: @foo +; CHECK-LABEL: entry +entry: + %tobool = icmp eq i32 %cond1, 0 + br i1 %tobool, label %bb.cond2, label %bb.f1 + +bb.f1: + call void @f1() + br label %bb.cond2 +; Verify that we branch on cond2 without checking ptr. +; CHECK: call void @f1() +; CHECK-NEXT: icmp eq i32 %cond2, 0 +; CHECK-NEXT: label %bb.f4, label %bb.f2 + +bb.cond2: + %ptr = phi i32* [ null, %bb.f1 ], [ @a, %entry ] + %tobool1 = icmp eq i32 %cond2, 0 + br i1 %tobool1, label %bb.file, label %bb.f2 +; Verify that we branch on cond2 without checking ptr. +; CHECK: icmp eq i32 %cond2, 0 +; CHECK-NEXT: label %bb.f3, label %bb.f2 + +bb.f2: + call void @f2() + br label %exit + +; Verify that we eliminate this basic block. +; CHECK-NOT: bb.file: +bb.file: + %cmp = icmp eq i32* %ptr, null + br i1 %cmp, label %bb.f4, label %bb.f3 + +bb.f3: + call void @f3() + br label %exit + +bb.f4: + call void @f4() + br label %exit + +exit: + ret void +} + +declare void @f1() + +declare void @f2() + +declare void @f3() + +declare void @f4() diff --git a/llvm/test/Transforms/JumpThreading/thread-two-bbs2.ll b/llvm/test/Transforms/JumpThreading/thread-two-bbs2.ll new file mode 100644 index 00000000000..ebb7ce013eb --- /dev/null +++ b/llvm/test/Transforms/JumpThreading/thread-two-bbs2.ll @@ -0,0 +1,56 @@ +; RUN: opt < %s -jump-threading -S -verify | FileCheck %s + +target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128" +target triple = "x86_64-unknown-linux-gnu" + +define void @foo(i32 %cond1, i32 %cond2) { +; CHECK-LABEL: @foo +; CHECK-LABEL: entry +entry: + %tobool = icmp ne i32 %cond1, 0 + br i1 %tobool, label %bb.f1, label %bb.f2 + +bb.f1: + call void @f1() + br label %bb.cond2 +; Verify that we branch on cond2 without checking tobool again. +; CHECK: call void @f1() +; CHECK-NEXT: icmp eq i32 %cond2, 0 +; CHECK-NEXT: label %exit, label %bb.f3 + +bb.f2: + call void @f2() + br label %bb.cond2 +; Verify that we branch on cond2 without checking tobool again. +; CHECK: call void @f2() +; CHECK-NEXT: icmp eq i32 %cond2, 0 +; CHECK-NEXT: label %exit, label %bb.f4 + +bb.cond2: + %tobool1 = icmp eq i32 %cond2, 0 + br i1 %tobool1, label %exit, label %bb.cond1again + +; Verify that we eliminate this basic block. +; CHECK-NOT: bb.cond1again: +bb.cond1again: + br i1 %tobool, label %bb.f3, label %bb.f4 + +bb.f3: + call void @f3() + br label %exit + +bb.f4: + call void @f4() + br label %exit + +exit: + ret void +} + +declare void @f1() local_unnamed_addr + +declare void @f2() local_unnamed_addr + +declare void @f3() local_unnamed_addr + +declare void @f4() local_unnamed_addr |

