1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
2; RUN: opt < %s -unroll-runtime-other-exit-predictable=false -loop-unroll -unroll-runtime=true -verify-dom-info -verify-loop-info -instcombine -S | FileCheck %s
3; RUN: opt < %s -unroll-runtime-other-exit-predictable=false -loop-unroll -unroll-runtime=true -verify-dom-info -unroll-runtime-multi-exit=false -verify-loop-info -S | FileCheck %s -check-prefix=NOUNROLL
4
5; this tests when unrolling multiple exit loop occurs by default (i.e. without specifying -unroll-runtime-multi-exit)
6
7; the second exit block is a deopt block. The loop has one exiting block other than the latch.
8define i32 @test1(i32* nocapture %a, i64 %n) {
9;
10; CHECK-LABEL: @test1(
11; CHECK-NEXT:  entry:
12; CHECK-NEXT:    [[TMP0:%.*]] = add i64 [[N:%.*]], -1
13; CHECK-NEXT:    [[XTRAITER:%.*]] = and i64 [[N]], 7
14; CHECK-NEXT:    [[TMP1:%.*]] = icmp ult i64 [[TMP0]], 7
15; CHECK-NEXT:    br i1 [[TMP1]], label [[LATCHEXIT_UNR_LCSSA:%.*]], label [[ENTRY_NEW:%.*]]
16; CHECK:       entry.new:
17; CHECK-NEXT:    [[UNROLL_ITER:%.*]] = and i64 [[N]], -8
18; CHECK-NEXT:    br label [[HEADER:%.*]]
19; CHECK:       header:
20; CHECK-NEXT:    [[INDVARS_IV:%.*]] = phi i64 [ 0, [[ENTRY_NEW]] ], [ [[INDVARS_IV_NEXT_7:%.*]], [[LATCH_7:%.*]] ]
21; CHECK-NEXT:    [[SUM_02:%.*]] = phi i32 [ 0, [[ENTRY_NEW]] ], [ [[ADD_7:%.*]], [[LATCH_7]] ]
22; CHECK-NEXT:    [[NITER:%.*]] = phi i64 [ 0, [[ENTRY_NEW]] ], [ [[NITER_NEXT_7:%.*]], [[LATCH_7]] ]
23; CHECK-NEXT:    br label [[FOR_EXITING_BLOCK:%.*]]
24; CHECK:       for.exiting_block:
25; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i64 [[N]], 42
26; CHECK-NEXT:    br i1 [[CMP]], label [[OTHEREXIT_LOOPEXIT:%.*]], label [[LATCH:%.*]]
27; CHECK:       latch:
28; CHECK-NEXT:    [[ARRAYIDX:%.*]] = getelementptr inbounds i32, i32* [[A:%.*]], i64 [[INDVARS_IV]]
29; CHECK-NEXT:    [[TMP2:%.*]] = load i32, i32* [[ARRAYIDX]], align 4
30; CHECK-NEXT:    [[ADD:%.*]] = add nsw i32 [[TMP2]], [[SUM_02]]
31; CHECK-NEXT:    [[INDVARS_IV_NEXT:%.*]] = or i64 [[INDVARS_IV]], 1
32; CHECK-NEXT:    br label [[FOR_EXITING_BLOCK_1:%.*]]
33; CHECK:       for.exiting_block.1:
34; CHECK-NEXT:    [[CMP_1:%.*]] = icmp eq i64 [[N]], 42
35; CHECK-NEXT:    br i1 [[CMP_1]], label [[OTHEREXIT_LOOPEXIT]], label [[LATCH_1:%.*]]
36; CHECK:       latch.1:
37; CHECK-NEXT:    [[ARRAYIDX_1:%.*]] = getelementptr inbounds i32, i32* [[A]], i64 [[INDVARS_IV_NEXT]]
38; CHECK-NEXT:    [[TMP3:%.*]] = load i32, i32* [[ARRAYIDX_1]], align 4
39; CHECK-NEXT:    [[ADD_1:%.*]] = add nsw i32 [[TMP3]], [[ADD]]
40; CHECK-NEXT:    [[INDVARS_IV_NEXT_1:%.*]] = or i64 [[INDVARS_IV]], 2
41; CHECK-NEXT:    br label [[FOR_EXITING_BLOCK_2:%.*]]
42; CHECK:       for.exiting_block.2:
43; CHECK-NEXT:    [[CMP_2:%.*]] = icmp eq i64 [[N]], 42
44; CHECK-NEXT:    br i1 [[CMP_2]], label [[OTHEREXIT_LOOPEXIT]], label [[LATCH_2:%.*]]
45; CHECK:       latch.2:
46; CHECK-NEXT:    [[ARRAYIDX_2:%.*]] = getelementptr inbounds i32, i32* [[A]], i64 [[INDVARS_IV_NEXT_1]]
47; CHECK-NEXT:    [[TMP4:%.*]] = load i32, i32* [[ARRAYIDX_2]], align 4
48; CHECK-NEXT:    [[ADD_2:%.*]] = add nsw i32 [[TMP4]], [[ADD_1]]
49; CHECK-NEXT:    [[INDVARS_IV_NEXT_2:%.*]] = or i64 [[INDVARS_IV]], 3
50; CHECK-NEXT:    br label [[FOR_EXITING_BLOCK_3:%.*]]
51; CHECK:       for.exiting_block.3:
52; CHECK-NEXT:    [[CMP_3:%.*]] = icmp eq i64 [[N]], 42
53; CHECK-NEXT:    br i1 [[CMP_3]], label [[OTHEREXIT_LOOPEXIT]], label [[LATCH_3:%.*]]
54; CHECK:       latch.3:
55; CHECK-NEXT:    [[ARRAYIDX_3:%.*]] = getelementptr inbounds i32, i32* [[A]], i64 [[INDVARS_IV_NEXT_2]]
56; CHECK-NEXT:    [[TMP5:%.*]] = load i32, i32* [[ARRAYIDX_3]], align 4
57; CHECK-NEXT:    [[ADD_3:%.*]] = add nsw i32 [[TMP5]], [[ADD_2]]
58; CHECK-NEXT:    [[INDVARS_IV_NEXT_3:%.*]] = or i64 [[INDVARS_IV]], 4
59; CHECK-NEXT:    br label [[FOR_EXITING_BLOCK_4:%.*]]
60; CHECK:       for.exiting_block.4:
61; CHECK-NEXT:    [[CMP_4:%.*]] = icmp eq i64 [[N]], 42
62; CHECK-NEXT:    br i1 [[CMP_4]], label [[OTHEREXIT_LOOPEXIT]], label [[LATCH_4:%.*]]
63; CHECK:       latch.4:
64; CHECK-NEXT:    [[ARRAYIDX_4:%.*]] = getelementptr inbounds i32, i32* [[A]], i64 [[INDVARS_IV_NEXT_3]]
65; CHECK-NEXT:    [[TMP6:%.*]] = load i32, i32* [[ARRAYIDX_4]], align 4
66; CHECK-NEXT:    [[ADD_4:%.*]] = add nsw i32 [[TMP6]], [[ADD_3]]
67; CHECK-NEXT:    [[INDVARS_IV_NEXT_4:%.*]] = or i64 [[INDVARS_IV]], 5
68; CHECK-NEXT:    br label [[FOR_EXITING_BLOCK_5:%.*]]
69; CHECK:       for.exiting_block.5:
70; CHECK-NEXT:    [[CMP_5:%.*]] = icmp eq i64 [[N]], 42
71; CHECK-NEXT:    br i1 [[CMP_5]], label [[OTHEREXIT_LOOPEXIT]], label [[LATCH_5:%.*]]
72; CHECK:       latch.5:
73; CHECK-NEXT:    [[ARRAYIDX_5:%.*]] = getelementptr inbounds i32, i32* [[A]], i64 [[INDVARS_IV_NEXT_4]]
74; CHECK-NEXT:    [[TMP7:%.*]] = load i32, i32* [[ARRAYIDX_5]], align 4
75; CHECK-NEXT:    [[ADD_5:%.*]] = add nsw i32 [[TMP7]], [[ADD_4]]
76; CHECK-NEXT:    [[INDVARS_IV_NEXT_5:%.*]] = or i64 [[INDVARS_IV]], 6
77; CHECK-NEXT:    br label [[FOR_EXITING_BLOCK_6:%.*]]
78; CHECK:       for.exiting_block.6:
79; CHECK-NEXT:    [[CMP_6:%.*]] = icmp eq i64 [[N]], 42
80; CHECK-NEXT:    br i1 [[CMP_6]], label [[OTHEREXIT_LOOPEXIT]], label [[LATCH_6:%.*]]
81; CHECK:       latch.6:
82; CHECK-NEXT:    [[ARRAYIDX_6:%.*]] = getelementptr inbounds i32, i32* [[A]], i64 [[INDVARS_IV_NEXT_5]]
83; CHECK-NEXT:    [[TMP8:%.*]] = load i32, i32* [[ARRAYIDX_6]], align 4
84; CHECK-NEXT:    [[ADD_6:%.*]] = add nsw i32 [[TMP8]], [[ADD_5]]
85; CHECK-NEXT:    [[INDVARS_IV_NEXT_6:%.*]] = or i64 [[INDVARS_IV]], 7
86; CHECK-NEXT:    br label [[FOR_EXITING_BLOCK_7:%.*]]
87; CHECK:       for.exiting_block.7:
88; CHECK-NEXT:    [[CMP_7:%.*]] = icmp eq i64 [[N]], 42
89; CHECK-NEXT:    br i1 [[CMP_7]], label [[OTHEREXIT_LOOPEXIT]], label [[LATCH_7]]
90; CHECK:       latch.7:
91; CHECK-NEXT:    [[ARRAYIDX_7:%.*]] = getelementptr inbounds i32, i32* [[A]], i64 [[INDVARS_IV_NEXT_6]]
92; CHECK-NEXT:    [[TMP9:%.*]] = load i32, i32* [[ARRAYIDX_7]], align 4
93; CHECK-NEXT:    [[ADD_7]] = add nsw i32 [[TMP9]], [[ADD_6]]
94; CHECK-NEXT:    [[INDVARS_IV_NEXT_7]] = add i64 [[INDVARS_IV]], 8
95; CHECK-NEXT:    [[NITER_NEXT_7]] = add i64 [[NITER]], 8
96; CHECK-NEXT:    [[NITER_NCMP_7:%.*]] = icmp eq i64 [[NITER_NEXT_7]], [[UNROLL_ITER]]
97; CHECK-NEXT:    br i1 [[NITER_NCMP_7]], label [[LATCHEXIT_UNR_LCSSA_LOOPEXIT:%.*]], label [[HEADER]]
98; CHECK:       latchexit.unr-lcssa.loopexit:
99; CHECK-NEXT:    br label [[LATCHEXIT_UNR_LCSSA]]
100; CHECK:       latchexit.unr-lcssa:
101; CHECK-NEXT:    [[SUM_0_LCSSA_PH:%.*]] = phi i32 [ undef, [[ENTRY:%.*]] ], [ [[ADD_7]], [[LATCHEXIT_UNR_LCSSA_LOOPEXIT]] ]
102; CHECK-NEXT:    [[INDVARS_IV_UNR:%.*]] = phi i64 [ 0, [[ENTRY]] ], [ [[INDVARS_IV_NEXT_7]], [[LATCHEXIT_UNR_LCSSA_LOOPEXIT]] ]
103; CHECK-NEXT:    [[SUM_02_UNR:%.*]] = phi i32 [ 0, [[ENTRY]] ], [ [[ADD_7]], [[LATCHEXIT_UNR_LCSSA_LOOPEXIT]] ]
104; CHECK-NEXT:    [[LCMP_MOD_NOT:%.*]] = icmp eq i64 [[XTRAITER]], 0
105; CHECK-NEXT:    br i1 [[LCMP_MOD_NOT]], label [[LATCHEXIT:%.*]], label [[HEADER_EPIL_PREHEADER:%.*]]
106; CHECK:       header.epil.preheader:
107; CHECK-NEXT:    br label [[HEADER_EPIL:%.*]]
108; CHECK:       header.epil:
109; CHECK-NEXT:    [[INDVARS_IV_EPIL:%.*]] = phi i64 [ [[INDVARS_IV_NEXT_EPIL:%.*]], [[LATCH_EPIL:%.*]] ], [ [[INDVARS_IV_UNR]], [[HEADER_EPIL_PREHEADER]] ]
110; CHECK-NEXT:    [[SUM_02_EPIL:%.*]] = phi i32 [ [[ADD_EPIL:%.*]], [[LATCH_EPIL]] ], [ [[SUM_02_UNR]], [[HEADER_EPIL_PREHEADER]] ]
111; CHECK-NEXT:    [[EPIL_ITER:%.*]] = phi i64 [ [[EPIL_ITER_NEXT:%.*]], [[LATCH_EPIL]] ], [ 0, [[HEADER_EPIL_PREHEADER]] ]
112; CHECK-NEXT:    br label [[FOR_EXITING_BLOCK_EPIL:%.*]]
113; CHECK:       for.exiting_block.epil:
114; CHECK-NEXT:    [[CMP_EPIL:%.*]] = icmp eq i64 [[N]], 42
115; CHECK-NEXT:    br i1 [[CMP_EPIL]], label [[OTHEREXIT_LOOPEXIT3:%.*]], label [[LATCH_EPIL]]
116; CHECK:       latch.epil:
117; CHECK-NEXT:    [[ARRAYIDX_EPIL:%.*]] = getelementptr inbounds i32, i32* [[A]], i64 [[INDVARS_IV_EPIL]]
118; CHECK-NEXT:    [[TMP10:%.*]] = load i32, i32* [[ARRAYIDX_EPIL]], align 4
119; CHECK-NEXT:    [[ADD_EPIL]] = add nsw i32 [[TMP10]], [[SUM_02_EPIL]]
120; CHECK-NEXT:    [[INDVARS_IV_NEXT_EPIL]] = add i64 [[INDVARS_IV_EPIL]], 1
121; CHECK-NEXT:    [[EPIL_ITER_NEXT]] = add i64 [[EPIL_ITER]], 1
122; CHECK-NEXT:    [[EPIL_ITER_CMP_NOT:%.*]] = icmp eq i64 [[EPIL_ITER_NEXT]], [[XTRAITER]]
123; CHECK-NEXT:    br i1 [[EPIL_ITER_CMP_NOT]], label [[LATCHEXIT_EPILOG_LCSSA:%.*]], label [[HEADER_EPIL]], !llvm.loop [[LOOP0:![0-9]+]]
124; CHECK:       latchexit.epilog-lcssa:
125; CHECK-NEXT:    br label [[LATCHEXIT]]
126; CHECK:       latchexit:
127; CHECK-NEXT:    [[SUM_0_LCSSA:%.*]] = phi i32 [ [[SUM_0_LCSSA_PH]], [[LATCHEXIT_UNR_LCSSA]] ], [ [[ADD_EPIL]], [[LATCHEXIT_EPILOG_LCSSA]] ]
128; CHECK-NEXT:    ret i32 [[SUM_0_LCSSA]]
129; CHECK:       otherexit.loopexit:
130; CHECK-NEXT:    [[SUM_02_LCSSA_PH:%.*]] = phi i32 [ [[SUM_02]], [[FOR_EXITING_BLOCK]] ], [ [[ADD]], [[FOR_EXITING_BLOCK_1]] ], [ [[ADD_1]], [[FOR_EXITING_BLOCK_2]] ], [ [[ADD_2]], [[FOR_EXITING_BLOCK_3]] ], [ [[ADD_3]], [[FOR_EXITING_BLOCK_4]] ], [ [[ADD_4]], [[FOR_EXITING_BLOCK_5]] ], [ [[ADD_5]], [[FOR_EXITING_BLOCK_6]] ], [ [[ADD_6]], [[FOR_EXITING_BLOCK_7]] ]
131; CHECK-NEXT:    br label [[OTHEREXIT:%.*]]
132; CHECK:       otherexit.loopexit3:
133; CHECK-NEXT:    br label [[OTHEREXIT]]
134; CHECK:       otherexit:
135; CHECK-NEXT:    [[SUM_02_LCSSA:%.*]] = phi i32 [ [[SUM_02_LCSSA_PH]], [[OTHEREXIT_LOOPEXIT]] ], [ [[SUM_02_EPIL]], [[OTHEREXIT_LOOPEXIT3]] ]
136; CHECK-NEXT:    [[RVAL:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"(i32 [[SUM_02_LCSSA]]) ]
137; CHECK-NEXT:    ret i32 [[RVAL]]
138;
139; NOUNROLL-LABEL: @test1(
140; NOUNROLL-NEXT:  entry:
141; NOUNROLL-NEXT:    br label [[HEADER:%.*]]
142; NOUNROLL:       header:
143; NOUNROLL-NEXT:    [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], [[LATCH:%.*]] ], [ 0, [[ENTRY:%.*]] ]
144; NOUNROLL-NEXT:    [[SUM_02:%.*]] = phi i32 [ [[ADD:%.*]], [[LATCH]] ], [ 0, [[ENTRY]] ]
145; NOUNROLL-NEXT:    br label [[FOR_EXITING_BLOCK:%.*]]
146; NOUNROLL:       for.exiting_block:
147; NOUNROLL-NEXT:    [[CMP:%.*]] = icmp eq i64 [[N:%.*]], 42
148; NOUNROLL-NEXT:    br i1 [[CMP]], label [[OTHEREXIT:%.*]], label [[LATCH]]
149; NOUNROLL:       latch:
150; NOUNROLL-NEXT:    [[ARRAYIDX:%.*]] = getelementptr inbounds i32, i32* [[A:%.*]], i64 [[INDVARS_IV]]
151; NOUNROLL-NEXT:    [[TMP0:%.*]] = load i32, i32* [[ARRAYIDX]], align 4
152; NOUNROLL-NEXT:    [[ADD]] = add nsw i32 [[TMP0]], [[SUM_02]]
153; NOUNROLL-NEXT:    [[INDVARS_IV_NEXT]] = add i64 [[INDVARS_IV]], 1
154; NOUNROLL-NEXT:    [[EXITCOND:%.*]] = icmp eq i64 [[INDVARS_IV_NEXT]], [[N]]
155; NOUNROLL-NEXT:    br i1 [[EXITCOND]], label [[LATCHEXIT:%.*]], label [[HEADER]]
156; NOUNROLL:       latchexit:
157; NOUNROLL-NEXT:    [[SUM_0_LCSSA:%.*]] = phi i32 [ [[ADD]], [[LATCH]] ]
158; NOUNROLL-NEXT:    ret i32 [[SUM_0_LCSSA]]
159; NOUNROLL:       otherexit:
160; NOUNROLL-NEXT:    [[SUM_02_LCSSA:%.*]] = phi i32 [ [[SUM_02]], [[FOR_EXITING_BLOCK]] ]
161; NOUNROLL-NEXT:    [[RVAL:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"(i32 [[SUM_02_LCSSA]]) ]
162; NOUNROLL-NEXT:    ret i32 [[RVAL]]
163;
164entry:
165  br label %header
166
167header:
168  %indvars.iv = phi i64 [ %indvars.iv.next, %latch ], [ 0, %entry ]
169  %sum.02 = phi i32 [ %add, %latch ], [ 0, %entry ]
170  br label %for.exiting_block
171
172for.exiting_block:
173  %cmp = icmp eq i64 %n, 42
174  br i1 %cmp, label %otherexit, label %latch
175
176latch:
177  %arrayidx = getelementptr inbounds i32, i32* %a, i64 %indvars.iv
178  %0 = load i32, i32* %arrayidx, align 4
179  %add = add nsw i32 %0, %sum.02
180  %indvars.iv.next = add i64 %indvars.iv, 1
181  %exitcond = icmp eq i64 %indvars.iv.next, %n
182  br i1 %exitcond, label %latchexit, label %header
183
184latchexit:                                          ; preds = %latch
185  %sum.0.lcssa = phi i32 [ %add, %latch ]
186  ret i32 %sum.0.lcssa
187
188otherexit:
189  %rval = call i32(...) @llvm.experimental.deoptimize.i32() [ "deopt"(i32 %sum.02) ]
190  ret i32 %rval
191}
192
193; the exit block is not a deopt block.
194define i32 @test2(i32* nocapture %a, i64 %n) {
195;
196; CHECK-LABEL: @test2(
197; CHECK-NEXT:  entry:
198; CHECK-NEXT:    br label [[HEADER:%.*]]
199; CHECK:       header:
200; CHECK-NEXT:    [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], [[LATCH:%.*]] ], [ 0, [[ENTRY:%.*]] ]
201; CHECK-NEXT:    [[SUM_02:%.*]] = phi i32 [ [[ADD:%.*]], [[LATCH]] ], [ 0, [[ENTRY]] ]
202; CHECK-NEXT:    br label [[FOR_EXITING_BLOCK:%.*]]
203; CHECK:       for.exiting_block:
204; CHECK-NEXT:    [[CMP:%.*]] = icmp eq i64 [[N:%.*]], 42
205; CHECK-NEXT:    br i1 [[CMP]], label [[OTHEREXIT:%.*]], label [[LATCH]]
206; CHECK:       latch:
207; CHECK-NEXT:    [[ARRAYIDX:%.*]] = getelementptr inbounds i32, i32* [[A:%.*]], i64 [[INDVARS_IV]]
208; CHECK-NEXT:    [[TMP0:%.*]] = load i32, i32* [[ARRAYIDX]], align 4
209; CHECK-NEXT:    [[ADD]] = add nsw i32 [[TMP0]], [[SUM_02]]
210; CHECK-NEXT:    [[INDVARS_IV_NEXT]] = add i64 [[INDVARS_IV]], 1
211; CHECK-NEXT:    [[EXITCOND:%.*]] = icmp eq i64 [[INDVARS_IV_NEXT]], [[N]]
212; CHECK-NEXT:    br i1 [[EXITCOND]], label [[LATCHEXIT:%.*]], label [[HEADER]]
213; CHECK:       latchexit:
214; CHECK-NEXT:    ret i32 [[ADD]]
215; CHECK:       otherexit:
216; CHECK-NEXT:    ret i32 [[SUM_02]]
217;
218; NOUNROLL-LABEL: @test2(
219; NOUNROLL-NEXT:  entry:
220; NOUNROLL-NEXT:    br label [[HEADER:%.*]]
221; NOUNROLL:       header:
222; NOUNROLL-NEXT:    [[INDVARS_IV:%.*]] = phi i64 [ [[INDVARS_IV_NEXT:%.*]], [[LATCH:%.*]] ], [ 0, [[ENTRY:%.*]] ]
223; NOUNROLL-NEXT:    [[SUM_02:%.*]] = phi i32 [ [[ADD:%.*]], [[LATCH]] ], [ 0, [[ENTRY]] ]
224; NOUNROLL-NEXT:    br label [[FOR_EXITING_BLOCK:%.*]]
225; NOUNROLL:       for.exiting_block:
226; NOUNROLL-NEXT:    [[CMP:%.*]] = icmp eq i64 [[N:%.*]], 42
227; NOUNROLL-NEXT:    br i1 [[CMP]], label [[OTHEREXIT:%.*]], label [[LATCH]]
228; NOUNROLL:       latch:
229; NOUNROLL-NEXT:    [[ARRAYIDX:%.*]] = getelementptr inbounds i32, i32* [[A:%.*]], i64 [[INDVARS_IV]]
230; NOUNROLL-NEXT:    [[TMP0:%.*]] = load i32, i32* [[ARRAYIDX]], align 4
231; NOUNROLL-NEXT:    [[ADD]] = add nsw i32 [[TMP0]], [[SUM_02]]
232; NOUNROLL-NEXT:    [[INDVARS_IV_NEXT]] = add i64 [[INDVARS_IV]], 1
233; NOUNROLL-NEXT:    [[EXITCOND:%.*]] = icmp eq i64 [[INDVARS_IV_NEXT]], [[N]]
234; NOUNROLL-NEXT:    br i1 [[EXITCOND]], label [[LATCHEXIT:%.*]], label [[HEADER]]
235; NOUNROLL:       latchexit:
236; NOUNROLL-NEXT:    [[SUM_0_LCSSA:%.*]] = phi i32 [ [[ADD]], [[LATCH]] ]
237; NOUNROLL-NEXT:    ret i32 [[SUM_0_LCSSA]]
238; NOUNROLL:       otherexit:
239; NOUNROLL-NEXT:    [[RVAL:%.*]] = phi i32 [ [[SUM_02]], [[FOR_EXITING_BLOCK]] ]
240; NOUNROLL-NEXT:    ret i32 [[RVAL]]
241;
242entry:
243  br label %header
244
245header:
246  %indvars.iv = phi i64 [ %indvars.iv.next, %latch ], [ 0, %entry ]
247  %sum.02 = phi i32 [ %add, %latch ], [ 0, %entry ]
248  br label %for.exiting_block
249
250for.exiting_block:
251  %cmp = icmp eq i64 %n, 42
252  br i1 %cmp, label %otherexit, label %latch
253
254latch:
255  %arrayidx = getelementptr inbounds i32, i32* %a, i64 %indvars.iv
256  %0 = load i32, i32* %arrayidx, align 4
257  %add = add nsw i32 %0, %sum.02
258  %indvars.iv.next = add i64 %indvars.iv, 1
259  %exitcond = icmp eq i64 %indvars.iv.next, %n
260  br i1 %exitcond, label %latchexit, label %header
261
262latchexit:                                          ; preds = %latch
263  %sum.0.lcssa = phi i32 [ %add, %latch ]
264  ret i32 %sum.0.lcssa
265
266otherexit:
267  %rval = phi i32 [%sum.02, %for.exiting_block ]
268  ret i32 %rval
269}
270declare i32 @llvm.experimental.deoptimize.i32(...)
271