xref: /llvm-project/llvm/test/Transforms/SimplifyCFG/wc-widen-block.ll (revision 8979ae42769e529b0f6fce3268492ffb49bd54b9)
1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
2; RUN: opt -passes=simplifycfg -simplifycfg-require-and-preserve-domtree=1 -S < %s | FileCheck %s
3
4define i32 @basic(i1 %cond_0, ptr %p) {
5; CHECK-LABEL: @basic(
6; CHECK-NEXT:  entry:
7; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
8; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND:%.*]] = and i1 [[COND_0:%.*]], [[WIDENABLE_COND]]
9; CHECK-NEXT:    br i1 [[EXIPLICIT_GUARD_COND]], label [[GUARDED:%.*]], label [[DEOPT:%.*]], !prof [[PROF0:![0-9]+]]
10; CHECK:       deopt:
11; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
12; CHECK-NEXT:    ret i32 [[DEOPTRET]]
13; CHECK:       guarded:
14; CHECK-NEXT:    [[V:%.*]] = load i32, ptr [[P:%.*]], align 4
15; CHECK-NEXT:    [[COND_1:%.*]] = icmp eq i32 [[V]], 0
16; CHECK-NEXT:    br i1 [[COND_1]], label [[RETURN:%.*]], label [[DEOPT]], !prof [[PROF0]]
17; CHECK:       return:
18; CHECK-NEXT:    ret i32 0
19;
20entry:
21  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
22  %exiplicit_guard_cond = and i1 %cond_0, %widenable_cond
23  br i1 %exiplicit_guard_cond, label %guarded, label %deopt, !prof !0
24
25deopt:
26  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
27  ret i32 %deoptret
28
29guarded:
30  %v = load i32, ptr %p
31  %cond_1 = icmp eq i32 %v, 0
32  br i1 %cond_1, label %return, label %deopt2, !prof !0
33
34deopt2:
35  %deoptret2 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
36  ret i32 %deoptret2
37
38return:
39  ret i32 0
40}
41
42define i32 @mergeable(i1 %cond_0, i1 %cond_1) {
43; CHECK-LABEL: @mergeable(
44; CHECK-NEXT:  entry:
45; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
46; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND:%.*]] = and i1 [[COND_0:%.*]], [[WIDENABLE_COND]]
47; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND_NOT:%.*]] = xor i1 [[EXIPLICIT_GUARD_COND]], true
48; CHECK-NEXT:    [[COND_1_NOT:%.*]] = xor i1 [[COND_1:%.*]], true
49; CHECK-NEXT:    [[BRMERGE:%.*]] = select i1 [[EXIPLICIT_GUARD_COND_NOT]], i1 true, i1 [[COND_1_NOT]]
50; CHECK-NEXT:    br i1 [[BRMERGE]], label [[DEOPT:%.*]], label [[RETURN:%.*]], !prof [[PROF1:![0-9]+]]
51; CHECK:       deopt:
52; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
53; CHECK-NEXT:    ret i32 [[DEOPTRET]]
54; CHECK:       return:
55; CHECK-NEXT:    ret i32 0
56;
57entry:
58  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
59  %exiplicit_guard_cond = and i1 %cond_0, %widenable_cond
60  br i1 %exiplicit_guard_cond, label %guarded, label %deopt, !prof !0
61
62deopt:
63  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
64  ret i32 %deoptret
65
66guarded:
67  br i1 %cond_1, label %return, label %deopt2, !prof !0
68
69deopt2:
70  %deoptret2 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
71  ret i32 %deoptret2
72
73return:
74  ret i32 0
75}
76
77define i32 @basic_swapped_branch(i1 %cond_0, ptr %p) {
78; CHECK-LABEL: @basic_swapped_branch(
79; CHECK-NEXT:  entry:
80; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
81; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND:%.*]] = and i1 [[COND_0:%.*]], [[WIDENABLE_COND]]
82; CHECK-NEXT:    br i1 [[EXIPLICIT_GUARD_COND]], label [[GUARDED:%.*]], label [[DEOPT:%.*]], !prof [[PROF0]]
83; CHECK:       deopt:
84; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
85; CHECK-NEXT:    ret i32 [[DEOPTRET]]
86; CHECK:       guarded:
87; CHECK-NEXT:    [[V:%.*]] = load i32, ptr [[P:%.*]], align 4
88; CHECK-NEXT:    [[COND_1:%.*]] = icmp eq i32 [[V]], 0
89; CHECK-NEXT:    br i1 [[COND_1]], label [[DEOPT]], label [[RETURN:%.*]], !prof [[PROF0]]
90; CHECK:       return:
91; CHECK-NEXT:    ret i32 0
92;
93entry:
94  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
95  %exiplicit_guard_cond = and i1 %cond_0, %widenable_cond
96  br i1 %exiplicit_guard_cond, label %guarded, label %deopt, !prof !0
97
98deopt:
99  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
100  ret i32 %deoptret
101
102guarded:
103  %v = load i32, ptr %p
104  %cond_1 = icmp eq i32 %v, 0
105  br i1 %cond_1, label %deopt2, label %return, !prof !0
106
107deopt2:
108  %deoptret2 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
109  ret i32 %deoptret2
110
111return:
112  ret i32 0
113}
114
115define i32 @todo_sink_side_effect(i1 %cond_0, i1 %cond_1) {
116; CHECK-LABEL: @todo_sink_side_effect(
117; CHECK-NEXT:  entry:
118; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
119; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND:%.*]] = and i1 [[COND_0:%.*]], [[WIDENABLE_COND]]
120; CHECK-NEXT:    br i1 [[EXIPLICIT_GUARD_COND]], label [[GUARDED:%.*]], label [[DEOPT:%.*]], !prof [[PROF0]]
121; CHECK:       deopt:
122; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
123; CHECK-NEXT:    ret i32 [[DEOPTRET]]
124; CHECK:       guarded:
125; CHECK-NEXT:    call void @unknown()
126; CHECK-NEXT:    br i1 [[COND_1:%.*]], label [[RETURN:%.*]], label [[DEOPT2:%.*]], !prof [[PROF0]]
127; CHECK:       deopt2:
128; CHECK-NEXT:    [[DEOPTRET2:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
129; CHECK-NEXT:    ret i32 [[DEOPTRET2]]
130; CHECK:       return:
131; CHECK-NEXT:    ret i32 0
132;
133entry:
134  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
135  %exiplicit_guard_cond = and i1 %cond_0, %widenable_cond
136  br i1 %exiplicit_guard_cond, label %guarded, label %deopt, !prof !0
137
138deopt:
139  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
140  ret i32 %deoptret
141
142guarded:
143  call void @unknown()
144  br i1 %cond_1, label %return, label %deopt2, !prof !0
145
146deopt2:
147  %deoptret2 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
148  ret i32 %deoptret2
149
150return:
151  ret i32 0
152}
153
154define i32 @neg_unsinkable_side_effect(i1 %cond_0) {
155; CHECK-LABEL: @neg_unsinkable_side_effect(
156; CHECK-NEXT:  entry:
157; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
158; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND:%.*]] = and i1 [[COND_0:%.*]], [[WIDENABLE_COND]]
159; CHECK-NEXT:    br i1 [[EXIPLICIT_GUARD_COND]], label [[GUARDED:%.*]], label [[DEOPT:%.*]], !prof [[PROF0]]
160; CHECK:       deopt:
161; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
162; CHECK-NEXT:    ret i32 [[DEOPTRET]]
163; CHECK:       guarded:
164; CHECK-NEXT:    [[V:%.*]] = call i32 @unknown_i32()
165; CHECK-NEXT:    [[COND_1:%.*]] = icmp eq i32 [[V]], 0
166; CHECK-NEXT:    br i1 [[COND_1]], label [[RETURN:%.*]], label [[DEOPT2:%.*]], !prof [[PROF0]]
167; CHECK:       deopt2:
168; CHECK-NEXT:    [[DEOPTRET2:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
169; CHECK-NEXT:    ret i32 [[DEOPTRET2]]
170; CHECK:       return:
171; CHECK-NEXT:    ret i32 0
172;
173entry:
174  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
175  %exiplicit_guard_cond = and i1 %cond_0, %widenable_cond
176  br i1 %exiplicit_guard_cond, label %guarded, label %deopt, !prof !0
177
178deopt:
179  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
180  ret i32 %deoptret
181
182guarded:
183  %v = call i32 @unknown_i32()
184  %cond_1 = icmp eq i32 %v, 0
185  br i1 %cond_1, label %return, label %deopt2, !prof !0
186
187deopt2:
188  %deoptret2 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
189  ret i32 %deoptret2
190
191return:
192  ret i32 0
193}
194
195
196define i32 @neg_inf_loop(i1 %cond_0, i1 %cond_1) {
197; CHECK-LABEL: @neg_inf_loop(
198; CHECK-NEXT:  entry:
199; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
200; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND:%.*]] = and i1 [[COND_0:%.*]], [[WIDENABLE_COND]]
201; CHECK-NEXT:    br i1 [[EXIPLICIT_GUARD_COND]], label [[GUARDED:%.*]], label [[DEOPT:%.*]], !prof [[PROF0]]
202; CHECK:       deopt:
203; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
204; CHECK-NEXT:    ret i32 [[DEOPTRET]]
205; CHECK:       guarded:
206; CHECK-NEXT:    call void @unknown()
207; CHECK-NEXT:    br i1 [[COND_1:%.*]], label [[RETURN:%.*]], label [[DEOPT]], !prof [[PROF0]]
208; CHECK:       return:
209; CHECK-NEXT:    ret i32 0
210;
211entry:
212  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
213  %exiplicit_guard_cond = and i1 %cond_0, %widenable_cond
214  br i1 %exiplicit_guard_cond, label %guarded, label %deopt, !prof !0
215
216deopt:
217  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
218  ret i32 %deoptret
219
220guarded:
221  call void @unknown()
222  br i1 %cond_1, label %return, label %deopt, !prof !0
223
224return:
225  ret i32 0
226}
227
228
229define i32 @todo_phi(i1 %cond_0, i1 %cond_1) {
230; CHECK-LABEL: @todo_phi(
231; CHECK-NEXT:  entry:
232; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
233; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND:%.*]] = and i1 [[COND_0:%.*]], [[WIDENABLE_COND]]
234; CHECK-NEXT:    br i1 [[EXIPLICIT_GUARD_COND]], label [[GUARDED:%.*]], label [[DEOPT:%.*]], !prof [[PROF0]]
235; CHECK:       deopt:
236; CHECK-NEXT:    [[PHI:%.*]] = phi i32 [ 0, [[ENTRY:%.*]] ]
237; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"(i32 [[PHI]]) ]
238; CHECK-NEXT:    ret i32 [[DEOPTRET]]
239; CHECK:       guarded:
240; CHECK-NEXT:    br i1 [[COND_1:%.*]], label [[RETURN:%.*]], label [[DEOPT2:%.*]], !prof [[PROF0]]
241; CHECK:       deopt2:
242; CHECK-NEXT:    [[DEOPTRET2:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
243; CHECK-NEXT:    ret i32 [[DEOPTRET2]]
244; CHECK:       return:
245; CHECK-NEXT:    ret i32 0
246;
247entry:
248  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
249  %exiplicit_guard_cond = and i1 %cond_0, %widenable_cond
250  br i1 %exiplicit_guard_cond, label %guarded, label %deopt, !prof !0
251
252deopt:
253  %phi = phi i32 [0, %entry]
254  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"(i32 %phi) ]
255  ret i32 %deoptret
256
257guarded:
258  br i1 %cond_1, label %return, label %deopt2, !prof !0
259
260deopt2:
261  %deoptret2 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
262  ret i32 %deoptret2
263
264return:
265  ret i32 0
266}
267
268
269define i32 @neg_loop(i1 %cond_0, i1 %cond_1) {
270; CHECK-LABEL: @neg_loop(
271; CHECK-NEXT:  entry:
272; CHECK-NEXT:    br label [[GUARDED:%.*]]
273; CHECK:       loop:
274; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
275; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND:%.*]] = and i1 [[COND_0:%.*]], [[WIDENABLE_COND]]
276; CHECK-NEXT:    br i1 [[EXIPLICIT_GUARD_COND]], label [[GUARDED]], label [[DEOPT:%.*]], !prof [[PROF0]]
277; CHECK:       deopt:
278; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
279; CHECK-NEXT:    ret i32 [[DEOPTRET]]
280; CHECK:       guarded:
281; CHECK-NEXT:    call void @unknown()
282; CHECK-NEXT:    br i1 [[COND_1:%.*]], label [[LOOP:%.*]], label [[DEOPT2:%.*]], !prof [[PROF0]]
283; CHECK:       deopt2:
284; CHECK-NEXT:    [[DEOPTRET2:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
285; CHECK-NEXT:    ret i32 [[DEOPTRET2]]
286;
287entry:
288  br label %guarded
289
290loop:
291  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
292  %exiplicit_guard_cond = and i1 %cond_0, %widenable_cond
293  br i1 %exiplicit_guard_cond, label %guarded, label %deopt, !prof !0
294
295deopt:
296  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
297  ret i32 %deoptret
298
299guarded:
300  call void @unknown()
301  br i1 %cond_1, label %loop, label %deopt2, !prof !0
302
303deopt2:
304  %deoptret2 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
305  ret i32 %deoptret2
306}
307
308; This one is subtle - We can't widen only one branch use of the
309; widenable condition as two branches are correlated.  We'd have to
310; widen them *both*.
311define i32 @neg_correlated(i1 %cond_0, i1 %cond_1, ptr %p) {
312; CHECK-LABEL: @neg_correlated(
313; CHECK-NEXT:  entry:
314; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
315; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND:%.*]] = and i1 [[COND_0:%.*]], [[WIDENABLE_COND]]
316; CHECK-NEXT:    br i1 [[EXIPLICIT_GUARD_COND]], label [[GUARDED:%.*]], label [[DEOPT:%.*]], !prof [[PROF0]]
317; CHECK:       deopt:
318; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
319; CHECK-NEXT:    ret i32 [[DEOPTRET]]
320; CHECK:       guarded:
321; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND2:%.*]] = and i1 [[COND_1:%.*]], [[WIDENABLE_COND]]
322; CHECK-NEXT:    br i1 [[EXIPLICIT_GUARD_COND2]], label [[GUARDED2:%.*]], label [[DEOPT2:%.*]], !prof [[PROF0]]
323; CHECK:       deopt2:
324; CHECK-NEXT:    [[DEOPTRET2:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
325; CHECK-NEXT:    ret i32 [[DEOPTRET2]]
326; CHECK:       guarded2:
327; CHECK-NEXT:    [[V:%.*]] = load i32, ptr [[P:%.*]], align 4
328; CHECK-NEXT:    [[COND_2:%.*]] = icmp eq i32 [[V]], 0
329; CHECK-NEXT:    br i1 [[COND_2]], label [[RETURN:%.*]], label [[DEOPT3:%.*]], !prof [[PROF0]]
330; CHECK:       deopt3:
331; CHECK-NEXT:    [[DEOPTRET3:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
332; CHECK-NEXT:    ret i32 [[DEOPTRET3]]
333; CHECK:       return:
334; CHECK-NEXT:    ret i32 0
335;
336entry:
337  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
338  %exiplicit_guard_cond = and i1 %cond_0, %widenable_cond
339  br i1 %exiplicit_guard_cond, label %guarded, label %deopt, !prof !0
340
341deopt:
342  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
343  ret i32 %deoptret
344
345guarded:
346  %exiplicit_guard_cond2 = and i1 %cond_1, %widenable_cond
347  br i1 %exiplicit_guard_cond2, label %guarded2, label %deopt2, !prof !0
348
349deopt2:
350  %deoptret2 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
351  ret i32 %deoptret2
352
353guarded2:
354  %v = load i32, ptr %p
355  %cond_2 = icmp eq i32 %v, 0
356  br i1 %cond_2, label %return, label %deopt3, !prof !0
357
358deopt3:
359  %deoptret3 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
360  ret i32 %deoptret3
361
362return:
363  ret i32 0
364}
365
366define i32 @trivial_wb(i1 %cond_0, ptr %p) {
367; CHECK-LABEL: @trivial_wb(
368; CHECK-NEXT:  entry:
369; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
370; CHECK-NEXT:    br i1 [[WIDENABLE_COND]], label [[GUARDED:%.*]], label [[DEOPT:%.*]], !prof [[PROF0]]
371; CHECK:       deopt:
372; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
373; CHECK-NEXT:    ret i32 [[DEOPTRET]]
374; CHECK:       guarded:
375; CHECK-NEXT:    [[V:%.*]] = load i32, ptr [[P:%.*]], align 4
376; CHECK-NEXT:    [[COND_1:%.*]] = icmp eq i32 [[V]], 0
377; CHECK-NEXT:    br i1 [[COND_1]], label [[RETURN:%.*]], label [[DEOPT]], !prof [[PROF0]]
378; CHECK:       return:
379; CHECK-NEXT:    ret i32 0
380;
381entry:
382  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
383  br i1 %widenable_cond, label %guarded, label %deopt, !prof !0
384
385deopt:
386  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
387  ret i32 %deoptret
388
389guarded:
390  %v = load i32, ptr %p
391  %cond_1 = icmp eq i32 %v, 0
392  br i1 %cond_1, label %return, label %deopt2, !prof !0
393
394deopt2:
395  %deoptret2 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
396  ret i32 %deoptret2
397
398return:
399  ret i32 0
400}
401
402
403define i32 @swapped_wb(i1 %cond_0, ptr %p) {
404; CHECK-LABEL: @swapped_wb(
405; CHECK-NEXT:  entry:
406; CHECK-NEXT:    [[WIDENABLE_COND:%.*]] = call i1 @llvm.experimental.widenable.condition()
407; CHECK-NEXT:    [[EXIPLICIT_GUARD_COND:%.*]] = and i1 [[WIDENABLE_COND]], [[COND_0:%.*]]
408; CHECK-NEXT:    br i1 [[EXIPLICIT_GUARD_COND]], label [[GUARDED:%.*]], label [[DEOPT:%.*]], !prof [[PROF0]]
409; CHECK:       deopt:
410; CHECK-NEXT:    [[DEOPTRET:%.*]] = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
411; CHECK-NEXT:    ret i32 [[DEOPTRET]]
412; CHECK:       guarded:
413; CHECK-NEXT:    [[V:%.*]] = load i32, ptr [[P:%.*]], align 4
414; CHECK-NEXT:    [[COND_1:%.*]] = icmp eq i32 [[V]], 0
415; CHECK-NEXT:    br i1 [[COND_1]], label [[RETURN:%.*]], label [[DEOPT]], !prof [[PROF0]]
416; CHECK:       return:
417; CHECK-NEXT:    ret i32 0
418;
419entry:
420  %widenable_cond = call i1 @llvm.experimental.widenable.condition()
421  %exiplicit_guard_cond = and i1 %widenable_cond, %cond_0
422  br i1 %exiplicit_guard_cond, label %guarded, label %deopt, !prof !0
423
424deopt:
425  %deoptret = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
426  ret i32 %deoptret
427
428guarded:
429  %v = load i32, ptr %p
430  %cond_1 = icmp eq i32 %v, 0
431  br i1 %cond_1, label %return, label %deopt2, !prof !0
432
433deopt2:
434  %deoptret2 = call i32 (...) @llvm.experimental.deoptimize.i32() [ "deopt"() ]
435  ret i32 %deoptret2
436
437return:
438  ret i32 0
439}
440
441
442
443
444declare void @unknown()
445declare i32 @unknown_i32()
446
447declare i1 @llvm.experimental.widenable.condition()
448declare i32 @llvm.experimental.deoptimize.i32(...)
449
450!0 = !{!"branch_weights", i32 1048576, i32 1}
451!1 = !{i32 1, i32 -2147483648}
452