1 ; RUN: opt < %s -inline -inline-threshold=20 -S | FileCheck %s 2 3 define internal i32 @callee1(i32 %A, i32 %B) { 4 %C = sdiv i32 %A, %B 5 ret i32 %C 6 } 7 8 define i32 @caller1() { 9 ; CHECK: define i32 @caller1 10 ; CHECK-NEXT: ret i32 3 11 12 %X = call i32 @callee1( i32 10, i32 3 ) 13 ret i32 %X 14 } 15 16 define i32 @caller2() { 17 ; Check that we can constant-prop through instructions after inlining callee21 18 ; to get constants in the inlined callsite to callee22. 19 ; FIXME: Currently, the threshold is fixed at 20 because we don't perform 20 ; *recursive* cost analysis to realize that the nested call site will definitely 21 ; inline and be cheap. We should eventually do that and lower the threshold here 22 ; to 1. 23 ; 24 ; CHECK: @caller2 25 ; CHECK-NOT: call void @callee2 26 ; CHECK: ret 27 28 %x = call i32 @callee21(i32 42, i32 48) 29 ret i32 %x 30 } 31 32 define i32 @callee21(i32 %x, i32 %y) { 33 %sub = sub i32 %y, %x 34 %result = call i32 @callee22(i32 %sub) 35 ret i32 %result 36 } 37 38 declare i8* @getptr() 39 40 define i32 @callee22(i32 %x) { 41 %icmp = icmp ugt i32 %x, 42 42 br i1 %icmp, label %bb.true, label %bb.false 43 bb.true: 44 ; This block musn't be counted in the inline cost. 45 %x1 = add i32 %x, 1 46 %x2 = add i32 %x1, 1 47 %x3 = add i32 %x2, 1 48 %x4 = add i32 %x3, 1 49 %x5 = add i32 %x4, 1 50 %x6 = add i32 %x5, 1 51 %x7 = add i32 %x6, 1 52 %x8 = add i32 %x7, 1 53 54 ret i32 %x8 55 bb.false: 56 ret i32 %x 57 } 58 59 define i32 @caller3() { 60 ; Check that even if the expensive path is hidden behind several basic blocks, 61 ; it doesn't count toward the inline cost when constant-prop proves those paths 62 ; dead. 63 ; 64 ; CHECK: @caller3 65 ; CHECK-NOT: call 66 ; CHECK: ret i32 6 67 68 entry: 69 %x = call i32 @callee3(i32 42, i32 48) 70 ret i32 %x 71 } 72 73 define i32 @callee3(i32 %x, i32 %y) { 74 %sub = sub i32 %y, %x 75 %icmp = icmp ugt i32 %sub, 42 76 br i1 %icmp, label %bb.true, label %bb.false 77 78 bb.true: 79 %icmp2 = icmp ult i32 %sub, 64 80 br i1 %icmp2, label %bb.true.true, label %bb.true.false 81 82 bb.true.true: 83 ; This block musn't be counted in the inline cost. 84 %x1 = add i32 %x, 1 85 %x2 = add i32 %x1, 1 86 %x3 = add i32 %x2, 1 87 %x4 = add i32 %x3, 1 88 %x5 = add i32 %x4, 1 89 %x6 = add i32 %x5, 1 90 %x7 = add i32 %x6, 1 91 %x8 = add i32 %x7, 1 92 br label %bb.merge 93 94 bb.true.false: 95 ; This block musn't be counted in the inline cost. 96 %y1 = add i32 %y, 1 97 %y2 = add i32 %y1, 1 98 %y3 = add i32 %y2, 1 99 %y4 = add i32 %y3, 1 100 %y5 = add i32 %y4, 1 101 %y6 = add i32 %y5, 1 102 %y7 = add i32 %y6, 1 103 %y8 = add i32 %y7, 1 104 br label %bb.merge 105 106 bb.merge: 107 %result = phi i32 [ %x8, %bb.true.true ], [ %y8, %bb.true.false ] 108 ret i32 %result 109 110 bb.false: 111 ret i32 %sub 112 } 113 114 115 define i32 @PR13412.main() { 116 ; This is a somewhat complicated three layer subprogram that was reported to 117 ; compute the wrong value for a branch due to assuming that an argument 118 ; mid-inline couldn't be equal to another pointer. 119 ; 120 ; After inlining, the branch should point directly to the exit block, not to 121 ; the intermediate block. 122 ; CHECK: @PR13412.main 123 ; CHECK: br i1 true, label %[[TRUE_DEST:.*]], label %[[FALSE_DEST:.*]] 124 ; CHECK: [[FALSE_DEST]]: 125 ; CHECK-NEXT: call void @PR13412.fail() 126 ; CHECK: [[TRUE_DEST]]: 127 ; CHECK-NEXT: ret i32 0 128 129 entry: 130 %i1 = alloca i64 131 store i64 0, i64* %i1 132 %arraydecay = bitcast i64* %i1 to i32* 133 %call = call i1 @PR13412.first(i32* %arraydecay, i32* %arraydecay) 134 br i1 %call, label %cond.end, label %cond.false 135 136 cond.false: 137 call void @PR13412.fail() 138 br label %cond.end 139 140 cond.end: 141 ret i32 0 142 } 143 144 define internal i1 @PR13412.first(i32* %a, i32* %b) { 145 entry: 146 %call = call i32* @PR13412.second(i32* %a, i32* %b) 147 %cmp = icmp eq i32* %call, %b 148 ret i1 %cmp 149 } 150 151 declare void @PR13412.fail() 152 153 define internal i32* @PR13412.second(i32* %a, i32* %b) { 154 entry: 155 %sub.ptr.lhs.cast = ptrtoint i32* %b to i64 156 %sub.ptr.rhs.cast = ptrtoint i32* %a to i64 157 %sub.ptr.sub = sub i64 %sub.ptr.lhs.cast, %sub.ptr.rhs.cast 158 %sub.ptr.div = ashr exact i64 %sub.ptr.sub, 2 159 %cmp = icmp ugt i64 %sub.ptr.div, 1 160 br i1 %cmp, label %if.then, label %if.end3 161 162 if.then: 163 %0 = load i32* %a 164 %1 = load i32* %b 165 %cmp1 = icmp eq i32 %0, %1 166 br i1 %cmp1, label %return, label %if.end3 167 168 if.end3: 169 br label %return 170 171 return: 172 %retval.0 = phi i32* [ %b, %if.end3 ], [ %a, %if.then ] 173 ret i32* %retval.0 174 } 175