1; RUN: llc < %s -asm-verbose=false | FileCheck %s 2 3; Test the CFG stackifier pass. 4 5target datalayout = "e-p:32:32-i64:64-n32:64-S128" 6target triple = "wasm32-unknown-unknown" 7 8declare void @something() 9 10; Test that loops are made contiguous, even in the presence of split backedges. 11 12; CHECK-LABEL: test0 13; CHECK: (loop 14; CHECK: (add 15; CHECK: (brif 16; CHECK: (call 17; CHECK: (br $BB0_1) 18; CHECK: (return) 19define void @test0(i32 %n) { 20entry: 21 br label %header 22 23header: 24 %i = phi i32 [ 0, %entry ], [ %i.next, %back ] 25 %i.next = add i32 %i, 1 26 27 %c = icmp slt i32 %i.next, %n 28 br i1 %c, label %back, label %exit 29 30exit: 31 ret void 32 33back: 34 call void @something() 35 br label %header 36} 37 38; Same as test0, but the branch condition is reversed. 39 40; CHECK-LABEL: test1 41; CHECK: (loop 42; CHECK: (add 43; CHECK: (brif 44; CHECK: (call 45; CHECK: (br $BB1_1) 46; CHECK: (return) 47define void @test1(i32 %n) { 48entry: 49 br label %header 50 51header: 52 %i = phi i32 [ 0, %entry ], [ %i.next, %back ] 53 %i.next = add i32 %i, 1 54 55 %c = icmp sge i32 %i.next, %n 56 br i1 %c, label %exit, label %back 57 58exit: 59 ret void 60 61back: 62 call void @something() 63 br label %header 64} 65 66; Test that a simple loop is handled as expected. 67 68; CHECK-LABEL: test2 69; CHECK: (block $BB2_2) 70; CHECK: (brif $BB2_2 {{.*}}) 71; CHECK: BB2_1: 72; CHECK: (brif $BB2_1 @14) 73; CHECK: BB2_2: 74; CHECK: (return) 75define void @test2(double* nocapture %p, i32 %n) { 76entry: 77 %cmp.4 = icmp sgt i32 %n, 0 78 br i1 %cmp.4, label %for.body.preheader, label %for.end 79 80for.body.preheader: 81 br label %for.body 82 83for.body: 84 %i.05 = phi i32 [ %inc, %for.body ], [ 0, %for.body.preheader ] 85 %arrayidx = getelementptr inbounds double, double* %p, i32 %i.05 86 %0 = load double, double* %arrayidx, align 8 87 %mul = fmul double %0, 3.200000e+00 88 store double %mul, double* %arrayidx, align 8 89 %inc = add nuw nsw i32 %i.05, 1 90 %exitcond = icmp eq i32 %inc, %n 91 br i1 %exitcond, label %for.end.loopexit, label %for.body 92 93for.end.loopexit: 94 br label %for.end 95 96for.end: 97 ret void 98} 99 100; CHECK-LABEL: doublediamond 101; CHECK: (block $BB3_5) 102; CHECK: (block $BB3_4) 103; CHECK: (block $BB3_2) 104; CHECK: (brif $BB3_2 @4) 105; CHECK: (br $BB3_5) 106; CHECK: BB3_2: 107; CHECK: (brif $BB3_4 @7) 108; CHECK: (br $BB3_5) 109; CHECK: BB3_4: 110; CHECK: BB3_5: 111; CHECK: (return @3) 112define i32 @doublediamond(i32 %a, i32 %b, i32* %p) { 113entry: 114 %c = icmp eq i32 %a, 0 115 %d = icmp eq i32 %b, 0 116 store volatile i32 0, i32* %p 117 br i1 %c, label %true, label %false 118true: 119 store volatile i32 1, i32* %p 120 br label %exit 121false: 122 store volatile i32 2, i32* %p 123 br i1 %d, label %ft, label %ff 124ft: 125 store volatile i32 3, i32* %p 126 br label %exit 127ff: 128 store volatile i32 4, i32* %p 129 br label %exit 130exit: 131 store volatile i32 5, i32* %p 132 ret i32 0 133} 134 135; CHECK-LABEL: triangle 136; CHECK: (block $BB4_2) 137; CHECK: (brif $BB4_2 @3) 138; CHECK: BB4_2: 139; CHECK: (return @2) 140define i32 @triangle(i32* %p, i32 %a) { 141entry: 142 %c = icmp eq i32 %a, 0 143 store volatile i32 0, i32* %p 144 br i1 %c, label %true, label %exit 145true: 146 store volatile i32 1, i32* %p 147 br label %exit 148exit: 149 store volatile i32 2, i32* %p 150 ret i32 0 151} 152 153; CHECK-LABEL: diamond 154; CHECK: (block $BB5_3) 155; CHECK: (block $BB5_2) 156; CHECK: (brif $BB5_2 @3) 157; CHECK: (br $BB5_3) 158; CHECK: BB5_2: 159; CHECK: BB5_3: 160; CHECK: (return @2) 161define i32 @diamond(i32* %p, i32 %a) { 162entry: 163 %c = icmp eq i32 %a, 0 164 store volatile i32 0, i32* %p 165 br i1 %c, label %true, label %false 166true: 167 store volatile i32 1, i32* %p 168 br label %exit 169false: 170 store volatile i32 2, i32* %p 171 br label %exit 172exit: 173 store volatile i32 3, i32* %p 174 ret i32 0 175} 176 177; CHECK-LABEL: single_block 178; CHECK-NOT: br 179; CHECK: (return @1) 180define i32 @single_block(i32* %p) { 181entry: 182 store volatile i32 0, i32* %p 183 ret i32 0 184} 185 186; CHECK-LABEL: minimal_loop 187; CHECK-NOT: br 188; CHECK: BB7_1: 189; CHECK: (store_i32 @0 @2) 190; CHECK: (br $BB7_1) 191define i32 @minimal_loop(i32* %p) { 192entry: 193 store volatile i32 0, i32* %p 194 br label %loop 195loop: 196 store volatile i32 1, i32* %p 197 br label %loop 198} 199 200; CHECK-LABEL: simple_loop 201; CHECK-NOT: br 202; CHECK: BB8_1: 203; CHECK: (loop $BB8_1) 204; CHECK: (brif $BB8_1 @4) 205; CHECK: (return @2) 206define i32 @simple_loop(i32* %p, i32 %a) { 207entry: 208 %c = icmp eq i32 %a, 0 209 store volatile i32 0, i32* %p 210 br label %loop 211loop: 212 store volatile i32 1, i32* %p 213 br i1 %c, label %loop, label %exit 214exit: 215 store volatile i32 2, i32* %p 216 ret i32 0 217} 218 219; CHECK-LABEL: doubletriangle 220; CHECK: (block $BB9_4) 221; CHECK: (block $BB9_3) 222; CHECK: (brif $BB9_4 @4) 223; CHECK: (brif $BB9_3 @7) 224; CHECK: BB9_3: 225; CHECK: BB9_4: 226; CHECK: (return @3) 227define i32 @doubletriangle(i32 %a, i32 %b, i32* %p) { 228entry: 229 %c = icmp eq i32 %a, 0 230 %d = icmp eq i32 %b, 0 231 store volatile i32 0, i32* %p 232 br i1 %c, label %true, label %exit 233true: 234 store volatile i32 2, i32* %p 235 br i1 %d, label %tt, label %tf 236tt: 237 store volatile i32 3, i32* %p 238 br label %tf 239tf: 240 store volatile i32 4, i32* %p 241 br label %exit 242exit: 243 store volatile i32 5, i32* %p 244 ret i32 0 245} 246 247; CHECK-LABEL: ifelse_earlyexits 248; CHECK: (block $BB10_4) 249; CHECK: (block $BB10_2) 250; CHECK: (brif $BB10_2 @4) 251; CHECK: (br $BB10_4) 252; CHECK: BB10_2: 253; CHECK: (brif $BB10_4 @7) 254; CHECK: BB10_4: 255; CHECK: (return @3) 256define i32 @ifelse_earlyexits(i32 %a, i32 %b, i32* %p) { 257entry: 258 %c = icmp eq i32 %a, 0 259 %d = icmp eq i32 %b, 0 260 store volatile i32 0, i32* %p 261 br i1 %c, label %true, label %false 262true: 263 store volatile i32 1, i32* %p 264 br label %exit 265false: 266 store volatile i32 2, i32* %p 267 br i1 %d, label %ft, label %exit 268ft: 269 store volatile i32 3, i32* %p 270 br label %exit 271exit: 272 store volatile i32 4, i32* %p 273 ret i32 0 274} 275