xref: /llvm-project/llvm/test/Transforms/SCCP/with.overflow.ll (revision 106ed59fe962e0443d2f59a81fa6f52875ced5c0)
1c412a2edSNikita Popov; NOTE: Assertions have been autogenerated by utils/update_test_checks.py
2*106ed59fSRoman Lebedev; RUN: opt -S -passes=sccp < %s | FileCheck %s
3c412a2edSNikita Popov
4c412a2edSNikita Popovdeclare { i8, i1 } @llvm.uadd.with.overflow.i8(i8, i8)
5c412a2edSNikita Popovdeclare { i8, i1 } @llvm.usub.with.overflow.i8(i8, i8)
6c412a2edSNikita Popovdeclare { i8, i1 } @llvm.umul.with.overflow.i8(i8, i8)
7c412a2edSNikita Popovdeclare { i8, i1 } @llvm.sadd.with.overflow.i8(i8, i8)
8c412a2edSNikita Popovdeclare { i8, i1 } @llvm.ssub.with.overflow.i8(i8, i8)
9c412a2edSNikita Popovdeclare { i8, i1 } @llvm.smul.with.overflow.i8(i8, i8)
10c412a2edSNikita Popovdeclare { <2 x i8>, <2 x i1> } @llvm.uadd.with.overflow.v2i8(<2 x i8>, <2 x i8>)
11c412a2edSNikita Popovdeclare void @use.i1(i1)
12c412a2edSNikita Popov
13c412a2edSNikita Popovdefine void @unsigned_overflow(ptr %p) {
14c412a2edSNikita Popov; CHECK-LABEL: @unsigned_overflow(
15c412a2edSNikita Popov; CHECK-NEXT:    [[V0_100:%.*]] = load i8, ptr [[P:%.*]], align 1, !range [[RNG0:![0-9]+]]
16c412a2edSNikita Popov; CHECK-NEXT:    [[V0_155:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG1:![0-9]+]]
17c412a2edSNikita Popov; CHECK-NEXT:    [[V0_156:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG2:![0-9]+]]
18c412a2edSNikita Popov; CHECK-NEXT:    [[V100_255:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG3:![0-9]+]]
19c412a2edSNikita Popov; CHECK-NEXT:    [[V99_255:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG4:![0-9]+]]
20c412a2edSNikita Popov; CHECK-NEXT:    [[V1_2:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG5:![0-9]+]]
21c412a2edSNikita Popov; CHECK-NEXT:    [[V1_3:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG6:![0-9]+]]
22c412a2edSNikita Popov; CHECK-NEXT:    [[WO1:%.*]] = call { i8, i1 } @llvm.uadd.with.overflow.i8(i8 [[V0_100]], i8 [[V0_155]])
23f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 false)
24c412a2edSNikita Popov; CHECK-NEXT:    [[WO2:%.*]] = call { i8, i1 } @llvm.uadd.with.overflow.i8(i8 [[V0_100]], i8 [[V0_156]])
25c412a2edSNikita Popov; CHECK-NEXT:    [[OV2:%.*]] = extractvalue { i8, i1 } [[WO2]], 1
26c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[OV2]])
27c412a2edSNikita Popov; CHECK-NEXT:    [[WO3:%.*]] = call { i8, i1 } @llvm.usub.with.overflow.i8(i8 [[V100_255]], i8 [[V0_100]])
28f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 false)
29c412a2edSNikita Popov; CHECK-NEXT:    [[WO4:%.*]] = call { i8, i1 } @llvm.usub.with.overflow.i8(i8 [[V99_255]], i8 [[V0_100]])
30c412a2edSNikita Popov; CHECK-NEXT:    [[OV4:%.*]] = extractvalue { i8, i1 } [[WO4]], 1
31c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[OV4]])
32c412a2edSNikita Popov; CHECK-NEXT:    [[WO5:%.*]] = call { i8, i1 } @llvm.umul.with.overflow.i8(i8 [[V0_100]], i8 [[V1_2]])
33f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 false)
34c412a2edSNikita Popov; CHECK-NEXT:    [[WO6:%.*]] = call { i8, i1 } @llvm.umul.with.overflow.i8(i8 [[V0_100]], i8 [[V1_3]])
35c412a2edSNikita Popov; CHECK-NEXT:    [[OV6:%.*]] = extractvalue { i8, i1 } [[WO6]], 1
36c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[OV6]])
37c412a2edSNikita Popov; CHECK-NEXT:    ret void
38c412a2edSNikita Popov;
39c412a2edSNikita Popov  %v0_100 = load i8, ptr %p, !range !{i8 0, i8 101}
40c412a2edSNikita Popov  %v0_155 = load i8, ptr %p, !range !{i8 0, i8 156}
41c412a2edSNikita Popov  %v0_156 = load i8, ptr %p, !range !{i8 0, i8 157}
42c412a2edSNikita Popov  %v100_255 = load i8, ptr %p, !range !{i8 100, i8 0}
43c412a2edSNikita Popov  %v99_255 = load i8, ptr %p, !range !{i8 99, i8 0}
44c412a2edSNikita Popov  %v1_2 = load i8, ptr %p, !range !{i8 1, i8 3}
45c412a2edSNikita Popov  %v1_3 = load i8, ptr %p, !range !{i8 1, i8 4}
46c412a2edSNikita Popov
47c412a2edSNikita Popov  %wo1 = call { i8, i1 } @llvm.uadd.with.overflow.i8(i8 %v0_100, i8 %v0_155)
48c412a2edSNikita Popov  %ov1 = extractvalue { i8, i1 } %wo1, 1
49c412a2edSNikita Popov  call void @use.i1(i1 %ov1)
50c412a2edSNikita Popov
51c412a2edSNikita Popov  %wo2 = call { i8, i1 } @llvm.uadd.with.overflow.i8(i8 %v0_100, i8 %v0_156)
52c412a2edSNikita Popov  %ov2 = extractvalue { i8, i1 } %wo2, 1
53c412a2edSNikita Popov  call void @use.i1(i1 %ov2)
54c412a2edSNikita Popov
55c412a2edSNikita Popov  %wo3 = call { i8, i1 } @llvm.usub.with.overflow.i8(i8 %v100_255, i8 %v0_100)
56c412a2edSNikita Popov  %ov3 = extractvalue { i8, i1 } %wo3, 1
57c412a2edSNikita Popov  call void @use.i1(i1 %ov3)
58c412a2edSNikita Popov
59c412a2edSNikita Popov  %wo4 = call { i8, i1 } @llvm.usub.with.overflow.i8(i8 %v99_255, i8 %v0_100)
60c412a2edSNikita Popov  %ov4 = extractvalue { i8, i1 } %wo4, 1
61c412a2edSNikita Popov  call void @use.i1(i1 %ov4)
62c412a2edSNikita Popov
63c412a2edSNikita Popov  %wo5 = call { i8, i1 } @llvm.umul.with.overflow.i8(i8 %v0_100, i8 %v1_2)
64c412a2edSNikita Popov  %ov5 = extractvalue { i8, i1 } %wo5, 1
65c412a2edSNikita Popov  call void @use.i1(i1 %ov5)
66c412a2edSNikita Popov
67c412a2edSNikita Popov  %wo6 = call { i8, i1 } @llvm.umul.with.overflow.i8(i8 %v0_100, i8 %v1_3)
68c412a2edSNikita Popov  %ov6 = extractvalue { i8, i1 } %wo6, 1
69c412a2edSNikita Popov  call void @use.i1(i1 %ov6)
70c412a2edSNikita Popov  ret void
71c412a2edSNikita Popov}
72c412a2edSNikita Popov
73c412a2edSNikita Popovdefine void @signed_overflow(ptr %p) {
74c412a2edSNikita Popov; CHECK-LABEL: @signed_overflow(
75c412a2edSNikita Popov; CHECK-NEXT:    [[V0_100:%.*]] = load i8, ptr [[P:%.*]], align 1, !range [[RNG0]]
76c412a2edSNikita Popov; CHECK-NEXT:    [[V0_27:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG7:![0-9]+]]
77c412a2edSNikita Popov; CHECK-NEXT:    [[V0_28:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG8:![0-9]+]]
78c412a2edSNikita Popov; CHECK-NEXT:    [[VM27_0:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG9:![0-9]+]]
79c412a2edSNikita Popov; CHECK-NEXT:    [[VM28_0:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG10:![0-9]+]]
80c412a2edSNikita Popov; CHECK-NEXT:    [[V1_4:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG11:![0-9]+]]
81c412a2edSNikita Popov; CHECK-NEXT:    [[V1_5:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG12:![0-9]+]]
82c412a2edSNikita Popov; CHECK-NEXT:    [[WO1:%.*]] = call { i8, i1 } @llvm.sadd.with.overflow.i8(i8 [[V0_100]], i8 [[V0_27]])
83f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 false)
84c412a2edSNikita Popov; CHECK-NEXT:    [[WO2:%.*]] = call { i8, i1 } @llvm.sadd.with.overflow.i8(i8 [[V0_100]], i8 [[V0_28]])
85c412a2edSNikita Popov; CHECK-NEXT:    [[OV2:%.*]] = extractvalue { i8, i1 } [[WO2]], 1
86c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[OV2]])
87c412a2edSNikita Popov; CHECK-NEXT:    [[WO3:%.*]] = call { i8, i1 } @llvm.ssub.with.overflow.i8(i8 [[V0_100]], i8 [[VM27_0]])
88f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 false)
89c412a2edSNikita Popov; CHECK-NEXT:    [[WO4:%.*]] = call { i8, i1 } @llvm.ssub.with.overflow.i8(i8 [[V0_100]], i8 [[VM28_0]])
90c412a2edSNikita Popov; CHECK-NEXT:    [[OV4:%.*]] = extractvalue { i8, i1 } [[WO4]], 1
91c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[OV4]])
92c412a2edSNikita Popov; CHECK-NEXT:    [[WO5:%.*]] = call { i8, i1 } @llvm.smul.with.overflow.i8(i8 [[V0_27]], i8 [[V1_4]])
93f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 false)
94c412a2edSNikita Popov; CHECK-NEXT:    [[WO6:%.*]] = call { i8, i1 } @llvm.smul.with.overflow.i8(i8 [[V0_27]], i8 [[V1_5]])
95c412a2edSNikita Popov; CHECK-NEXT:    [[OV6:%.*]] = extractvalue { i8, i1 } [[WO6]], 1
96c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[OV6]])
97c412a2edSNikita Popov; CHECK-NEXT:    ret void
98c412a2edSNikita Popov;
99c412a2edSNikita Popov  %v0_100 = load i8, ptr %p, !range !{i8 0, i8 101}
100c412a2edSNikita Popov  %v0_27 = load i8, ptr %p, !range !{i8 0, i8 28}
101c412a2edSNikita Popov  %v0_28 = load i8, ptr %p, !range !{i8 0, i8 29}
102c412a2edSNikita Popov  %vm27_0 = load i8, ptr %p, !range !{i8 -27, i8 0}
103c412a2edSNikita Popov  %vm28_0 = load i8, ptr %p, !range !{i8 -28, i8 0}
104c412a2edSNikita Popov  %v1_4 = load i8, ptr %p, !range !{i8 1, i8 5}
105c412a2edSNikita Popov  %v1_5 = load i8, ptr %p, !range !{i8 1, i8 6}
106c412a2edSNikita Popov
107c412a2edSNikita Popov  %wo1 = call { i8, i1 } @llvm.sadd.with.overflow.i8(i8 %v0_100, i8 %v0_27)
108c412a2edSNikita Popov  %ov1 = extractvalue { i8, i1 } %wo1, 1
109c412a2edSNikita Popov  call void @use.i1(i1 %ov1)
110c412a2edSNikita Popov
111c412a2edSNikita Popov  %wo2 = call { i8, i1 } @llvm.sadd.with.overflow.i8(i8 %v0_100, i8 %v0_28)
112c412a2edSNikita Popov  %ov2 = extractvalue { i8, i1 } %wo2, 1
113c412a2edSNikita Popov  call void @use.i1(i1 %ov2)
114c412a2edSNikita Popov
115c412a2edSNikita Popov  %wo3 = call { i8, i1 } @llvm.ssub.with.overflow.i8(i8 %v0_100, i8 %vm27_0)
116c412a2edSNikita Popov  %ov3 = extractvalue { i8, i1 } %wo3, 1
117c412a2edSNikita Popov  call void @use.i1(i1 %ov3)
118c412a2edSNikita Popov
119c412a2edSNikita Popov  %wo4 = call { i8, i1 } @llvm.ssub.with.overflow.i8(i8 %v0_100, i8 %vm28_0)
120c412a2edSNikita Popov  %ov4 = extractvalue { i8, i1 } %wo4, 1
121c412a2edSNikita Popov  call void @use.i1(i1 %ov4)
122c412a2edSNikita Popov
123c412a2edSNikita Popov  %wo5 = call { i8, i1 } @llvm.smul.with.overflow.i8(i8 %v0_27, i8 %v1_4)
124c412a2edSNikita Popov  %ov5 = extractvalue { i8, i1 } %wo5, 1
125c412a2edSNikita Popov  call void @use.i1(i1 %ov5)
126c412a2edSNikita Popov
127c412a2edSNikita Popov  %wo6 = call { i8, i1 } @llvm.smul.with.overflow.i8(i8 %v0_27, i8 %v1_5)
128c412a2edSNikita Popov  %ov6 = extractvalue { i8, i1 } %wo6, 1
129c412a2edSNikita Popov  call void @use.i1(i1 %ov6)
130c412a2edSNikita Popov  ret void
131c412a2edSNikita Popov}
132c412a2edSNikita Popov
133c412a2edSNikita Popovdefine void @unsigned_result(ptr %p) {
134c412a2edSNikita Popov; CHECK-LABEL: @unsigned_result(
135c412a2edSNikita Popov; CHECK-NEXT:    [[V0_20:%.*]] = load i8, ptr [[P:%.*]], align 1, !range [[RNG13:![0-9]+]]
136c412a2edSNikita Popov; CHECK-NEXT:    [[V20_40:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG14:![0-9]+]]
137c412a2edSNikita Popov; CHECK-NEXT:    [[V0_10:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG15:![0-9]+]]
138c412a2edSNikita Popov; CHECK-NEXT:    [[V2_3:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG16:![0-9]+]]
139c412a2edSNikita Popov; CHECK-NEXT:    [[WO1:%.*]] = call { i8, i1 } @llvm.uadd.with.overflow.i8(i8 [[V0_20]], i8 [[V20_40]])
140c412a2edSNikita Popov; CHECK-NEXT:    [[RES1:%.*]] = extractvalue { i8, i1 } [[WO1]], 0
141f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
142f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
143c412a2edSNikita Popov; CHECK-NEXT:    [[CMP1_3:%.*]] = icmp ugt i8 [[RES1]], 20
144c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP1_3]])
145c412a2edSNikita Popov; CHECK-NEXT:    [[CMP1_4:%.*]] = icmp ult i8 [[RES1]], 60
146c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP1_4]])
147c412a2edSNikita Popov; CHECK-NEXT:    [[WO2:%.*]] = call { i8, i1 } @llvm.usub.with.overflow.i8(i8 [[V0_10]], i8 [[V20_40]])
148c412a2edSNikita Popov; CHECK-NEXT:    [[RES2:%.*]] = extractvalue { i8, i1 } [[WO2]], 0
149f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
150f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
151c412a2edSNikita Popov; CHECK-NEXT:    [[CMP2_3:%.*]] = icmp ugt i8 [[RES2]], -40
152c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP2_3]])
153c412a2edSNikita Popov; CHECK-NEXT:    [[CMP2_4:%.*]] = icmp ult i8 [[RES2]], -10
154c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP2_4]])
155c412a2edSNikita Popov; CHECK-NEXT:    [[WO3:%.*]] = call { i8, i1 } @llvm.umul.with.overflow.i8(i8 [[V20_40]], i8 [[V2_3]])
156c412a2edSNikita Popov; CHECK-NEXT:    [[RES3:%.*]] = extractvalue { i8, i1 } [[WO3]], 0
157f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
158f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
159c412a2edSNikita Popov; CHECK-NEXT:    [[CMP3_3:%.*]] = icmp ugt i8 [[RES3]], 40
160c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP3_3]])
161c412a2edSNikita Popov; CHECK-NEXT:    [[CMP3_4:%.*]] = icmp ult i8 [[RES3]], 120
162c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP3_4]])
163c412a2edSNikita Popov; CHECK-NEXT:    ret void
164c412a2edSNikita Popov;
165c412a2edSNikita Popov  %v0_20 = load i8, ptr %p, !range !{i8 0, i8 21}
166c412a2edSNikita Popov  %v20_40 = load i8, ptr %p, !range !{i8 20, i8 41}
167c412a2edSNikita Popov  %v0_10 = load i8, ptr %p, !range !{i8 0, i8 11}
168c412a2edSNikita Popov  %v2_3 = load i8, ptr %p, !range !{i8 2, i8 4}
169c412a2edSNikita Popov  %wo1 = call { i8, i1 } @llvm.uadd.with.overflow.i8(i8 %v0_20, i8 %v20_40)
170c412a2edSNikita Popov  %res1 = extractvalue { i8, i1 } %wo1, 0
171c412a2edSNikita Popov  %cmp1.1 = icmp uge i8 %res1, 20
172c412a2edSNikita Popov  call void @use.i1(i1 %cmp1.1)
173c412a2edSNikita Popov  %cmp1.2 = icmp ule i8 %res1, 60
174c412a2edSNikita Popov  call void @use.i1(i1 %cmp1.2)
175c412a2edSNikita Popov  %cmp1.3 = icmp ugt i8 %res1, 20
176c412a2edSNikita Popov  call void @use.i1(i1 %cmp1.3)
177c412a2edSNikita Popov  %cmp1.4 = icmp ult i8 %res1, 60
178c412a2edSNikita Popov  call void @use.i1(i1 %cmp1.4)
179c412a2edSNikita Popov
180c412a2edSNikita Popov  ; This case actually does overflow, but we can still determine the range.
181c412a2edSNikita Popov  %wo2 = call { i8, i1 } @llvm.usub.with.overflow.i8(i8 %v0_10, i8 %v20_40)
182c412a2edSNikita Popov  %res2 = extractvalue { i8, i1 } %wo2, 0
183c412a2edSNikita Popov  %cmp2.1 = icmp uge i8 %res2, -40
184c412a2edSNikita Popov  call void @use.i1(i1 %cmp2.1)
185c412a2edSNikita Popov  %cmp2.2 = icmp ule i8 %res2, -10
186c412a2edSNikita Popov  call void @use.i1(i1 %cmp2.2)
187c412a2edSNikita Popov  %cmp2.3 = icmp ugt i8 %res2, -40
188c412a2edSNikita Popov  call void @use.i1(i1 %cmp2.3)
189c412a2edSNikita Popov  %cmp2.4 = icmp ult i8 %res2, -10
190c412a2edSNikita Popov  call void @use.i1(i1 %cmp2.4)
191c412a2edSNikita Popov
192c412a2edSNikita Popov  %wo3 = call { i8, i1 } @llvm.umul.with.overflow.i8(i8 %v20_40, i8 %v2_3)
193c412a2edSNikita Popov  %res3 = extractvalue { i8, i1 } %wo3, 0
194c412a2edSNikita Popov  %cmp3.1 = icmp uge i8 %res3, 40
195c412a2edSNikita Popov  call void @use.i1(i1 %cmp3.1)
196c412a2edSNikita Popov  %cmp3.2 = icmp ule i8 %res3, 120
197c412a2edSNikita Popov  call void @use.i1(i1 %cmp3.2)
198c412a2edSNikita Popov  %cmp3.3 = icmp ugt i8 %res3, 40
199c412a2edSNikita Popov  call void @use.i1(i1 %cmp3.3)
200c412a2edSNikita Popov  %cmp3.4 = icmp ult i8 %res3, 120
201c412a2edSNikita Popov  call void @use.i1(i1 %cmp3.4)
202c412a2edSNikita Popov  ret void
203c412a2edSNikita Popov}
204c412a2edSNikita Popov
205c412a2edSNikita Popovdefine void @signed_result(ptr %p) {
206c412a2edSNikita Popov; CHECK-LABEL: @signed_result(
207c412a2edSNikita Popov; CHECK-NEXT:    [[V0_20:%.*]] = load i8, ptr [[P:%.*]], align 1, !range [[RNG13]]
208c412a2edSNikita Popov; CHECK-NEXT:    [[V20_40:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG14]]
209c412a2edSNikita Popov; CHECK-NEXT:    [[V0_10:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG15]]
210c412a2edSNikita Popov; CHECK-NEXT:    [[V2_3:%.*]] = load i8, ptr [[P]], align 1, !range [[RNG16]]
211c412a2edSNikita Popov; CHECK-NEXT:    [[WO1:%.*]] = call { i8, i1 } @llvm.sadd.with.overflow.i8(i8 [[V0_20]], i8 [[V20_40]])
212c412a2edSNikita Popov; CHECK-NEXT:    [[RES1:%.*]] = extractvalue { i8, i1 } [[WO1]], 0
213f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
214f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
215c412a2edSNikita Popov; CHECK-NEXT:    [[CMP1_3:%.*]] = icmp ugt i8 [[RES1]], 20
216c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP1_3]])
217c412a2edSNikita Popov; CHECK-NEXT:    [[CMP1_4:%.*]] = icmp ult i8 [[RES1]], 60
218c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP1_4]])
219c412a2edSNikita Popov; CHECK-NEXT:    [[WO2:%.*]] = call { i8, i1 } @llvm.ssub.with.overflow.i8(i8 [[V0_10]], i8 [[V20_40]])
220c412a2edSNikita Popov; CHECK-NEXT:    [[RES2:%.*]] = extractvalue { i8, i1 } [[WO2]], 0
221f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
222f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
223c412a2edSNikita Popov; CHECK-NEXT:    [[CMP2_3:%.*]] = icmp ugt i8 [[RES2]], -40
224c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP2_3]])
225c412a2edSNikita Popov; CHECK-NEXT:    [[CMP2_4:%.*]] = icmp ult i8 [[RES2]], -10
226c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP2_4]])
227c412a2edSNikita Popov; CHECK-NEXT:    [[WO3:%.*]] = call { i8, i1 } @llvm.smul.with.overflow.i8(i8 [[V20_40]], i8 [[V2_3]])
228c412a2edSNikita Popov; CHECK-NEXT:    [[RES3:%.*]] = extractvalue { i8, i1 } [[WO3]], 0
229f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
230f101196dSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 true)
231c412a2edSNikita Popov; CHECK-NEXT:    [[CMP3_3:%.*]] = icmp ugt i8 [[RES3]], 40
232c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP3_3]])
233c412a2edSNikita Popov; CHECK-NEXT:    [[CMP3_4:%.*]] = icmp ult i8 [[RES3]], 120
234c412a2edSNikita Popov; CHECK-NEXT:    call void @use.i1(i1 [[CMP3_4]])
235c412a2edSNikita Popov; CHECK-NEXT:    ret void
236c412a2edSNikita Popov;
237c412a2edSNikita Popov  %v0_20 = load i8, ptr %p, !range !{i8 0, i8 21}
238c412a2edSNikita Popov  %v20_40 = load i8, ptr %p, !range !{i8 20, i8 41}
239c412a2edSNikita Popov  %v0_10 = load i8, ptr %p, !range !{i8 0, i8 11}
240c412a2edSNikita Popov  %v2_3 = load i8, ptr %p, !range !{i8 2, i8 4}
241c412a2edSNikita Popov  %wo1 = call { i8, i1 } @llvm.sadd.with.overflow.i8(i8 %v0_20, i8 %v20_40)
242c412a2edSNikita Popov  %res1 = extractvalue { i8, i1 } %wo1, 0
243c412a2edSNikita Popov  %cmp1.1 = icmp uge i8 %res1, 20
244c412a2edSNikita Popov  call void @use.i1(i1 %cmp1.1)
245c412a2edSNikita Popov  %cmp1.2 = icmp ule i8 %res1, 60
246c412a2edSNikita Popov  call void @use.i1(i1 %cmp1.2)
247c412a2edSNikita Popov  %cmp1.3 = icmp ugt i8 %res1, 20
248c412a2edSNikita Popov  call void @use.i1(i1 %cmp1.3)
249c412a2edSNikita Popov  %cmp1.4 = icmp ult i8 %res1, 60
250c412a2edSNikita Popov  call void @use.i1(i1 %cmp1.4)
251c412a2edSNikita Popov
252c412a2edSNikita Popov  %wo2 = call { i8, i1 } @llvm.ssub.with.overflow.i8(i8 %v0_10, i8 %v20_40)
253c412a2edSNikita Popov  %res2 = extractvalue { i8, i1 } %wo2, 0
254c412a2edSNikita Popov  %cmp2.1 = icmp uge i8 %res2, -40
255c412a2edSNikita Popov  call void @use.i1(i1 %cmp2.1)
256c412a2edSNikita Popov  %cmp2.2 = icmp ule i8 %res2, -10
257c412a2edSNikita Popov  call void @use.i1(i1 %cmp2.2)
258c412a2edSNikita Popov  %cmp2.3 = icmp ugt i8 %res2, -40
259c412a2edSNikita Popov  call void @use.i1(i1 %cmp2.3)
260c412a2edSNikita Popov  %cmp2.4 = icmp ult i8 %res2, -10
261c412a2edSNikita Popov  call void @use.i1(i1 %cmp2.4)
262c412a2edSNikita Popov
263c412a2edSNikita Popov  %wo3 = call { i8, i1 } @llvm.smul.with.overflow.i8(i8 %v20_40, i8 %v2_3)
264c412a2edSNikita Popov  %res3 = extractvalue { i8, i1 } %wo3, 0
265c412a2edSNikita Popov  %cmp3.1 = icmp uge i8 %res3, 40
266c412a2edSNikita Popov  call void @use.i1(i1 %cmp3.1)
267c412a2edSNikita Popov  %cmp3.2 = icmp ule i8 %res3, 120
268c412a2edSNikita Popov  call void @use.i1(i1 %cmp3.2)
269c412a2edSNikita Popov  %cmp3.3 = icmp ugt i8 %res3, 40
270c412a2edSNikita Popov  call void @use.i1(i1 %cmp3.3)
271c412a2edSNikita Popov  %cmp3.4 = icmp ult i8 %res3, 120
272c412a2edSNikita Popov  call void @use.i1(i1 %cmp3.4)
273c412a2edSNikita Popov  ret void
274c412a2edSNikita Popov}
275c412a2edSNikita Popov
276c412a2edSNikita Popov; SCCP doesn't really support vector ranges yet, just make sure we don't crash.
277c412a2edSNikita Popovdefine <2 x i1> @vec(<2 x i8> %v1, <2 x i8> %v2) {
278c412a2edSNikita Popov; CHECK-LABEL: @vec(
279c412a2edSNikita Popov; CHECK-NEXT:    [[WO:%.*]] = call { <2 x i8>, <2 x i1> } @llvm.uadd.with.overflow.v2i8(<2 x i8> [[V1:%.*]], <2 x i8> [[V2:%.*]])
280c412a2edSNikita Popov; CHECK-NEXT:    [[OV:%.*]] = extractvalue { <2 x i8>, <2 x i1> } [[WO]], 1
281c412a2edSNikita Popov; CHECK-NEXT:    ret <2 x i1> [[OV]]
282c412a2edSNikita Popov;
283c412a2edSNikita Popov  %wo = call { <2 x i8>, <2 x i1> } @llvm.uadd.with.overflow.v2i8(<2 x i8> %v1, <2 x i8> %v2)
284c412a2edSNikita Popov  %ov = extractvalue { <2 x i8>, <2 x i1> } %wo, 1
285c412a2edSNikita Popov  ret <2 x i1> %ov
286c412a2edSNikita Popov}
287