1; RUN: opt -S -jump-threading %s | FileCheck %s 2 3; Value of predicate known on all inputs (trivial case) 4; Note: InstCombine/EarlyCSE would also get this case 5define void @test(i8* %p, i8** %addr) { 6; CHECK-LABEL: @test 7entry: 8 %cmp0 = icmp eq i8* %p, null 9 br i1 %cmp0, label %exit, label %loop 10loop: 11; CHECK-LABEL: loop: 12; CHECK-NEXT: phi 13; CHECK-NEXT: br label %loop 14 %p1 = phi i8* [%p, %entry], [%p1, %loop] 15 %cmp1 = icmp eq i8* %p1, null 16 br i1 %cmp1, label %exit, label %loop 17exit: 18 ret void 19} 20 21; Value of predicate known on all inputs (non-trivial) 22define void @test2(i8* %p) { 23; CHECK-LABEL: @test2 24entry: 25 %cmp0 = icmp eq i8* %p, null 26 br i1 %cmp0, label %exit, label %loop 27loop: 28 %p1 = phi i8* [%p, %entry], [%p2, %backedge] 29 %cmp1 = icmp eq i8* %p1, null 30 br i1 %cmp1, label %exit, label %backedge 31backedge: 32; CHECK-LABEL: backedge: 33; CHECK-NEXT: phi 34; CHECK-NEXT: bitcast 35; CHECK-NEXT: load 36; CHECK-NEXT: cmp 37; CHECK-NEXT: br 38; CHECK-DAG: label %backedge 39 %addr = bitcast i8* %p1 to i8** 40 %p2 = load i8*, i8** %addr 41 %cmp2 = icmp eq i8* %p2, null 42 br i1 %cmp2, label %exit, label %loop 43exit: 44 ret void 45} 46 47; If the inputs don't branch the same way, we can't rewrite 48; Well, we could unroll this loop exactly twice, but that's 49; a different transform. 50define void @test_mixed(i8* %p) { 51; CHECK-LABEL: @test_mixed 52entry: 53 %cmp0 = icmp eq i8* %p, null 54 br i1 %cmp0, label %exit, label %loop 55loop: 56; CHECK-LABEL: loop: 57; CHECK-NEXT: phi 58; CHECK-NEXT: %cmp1 = icmp 59; CHECK-NEXT: br i1 %cmp1 60 %p1 = phi i8* [%p, %entry], [%p1, %loop] 61 %cmp1 = icmp ne i8* %p1, null 62 br i1 %cmp1, label %exit, label %loop 63exit: 64 ret void 65} 66 67; The eq predicate is always true if we go through the path from 68; L1 to L3, no matter the phi result %t5 is on the lhs or rhs of 69; the predicate. 70declare void @goo() 71declare void @hoo() 72 73define void @test3(i32 %m, i32** %t1) { 74L1: 75 %t0 = add i32 %m, 7 76 %t2 = load i32*, i32** %t1, align 8 77; CHECK-LABEL: @test3 78; CHECK: %t3 = icmp eq i32* %t2, null 79; CHECK: br i1 %t3, label %[[LABEL2:.*]], label %[[LABEL1:.*]] 80 81 %t3 = icmp eq i32* %t2, null 82 br i1 %t3, label %L3, label %L2 83 84; CHECK: [[LABEL1]]: 85; CHECK-NEXT: %t4 = load i32, i32* %t2, align 4 86L2: 87 %t4 = load i32, i32* %t2, align 4 88 br label %L3 89 90L3: 91 %t5 = phi i32 [ %t0, %L1 ], [ %t4, %L2 ] 92 %t6 = icmp eq i32 %t0, %t5 93 br i1 %t6, label %L4, label %L5 94 95; CHECK: [[LABEL2]]: 96; CHECK-NEXT: call void @goo() 97L4: 98 call void @goo() 99 ret void 100 101L5: 102 call void @hoo() 103 ret void 104} 105