• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1; Test 64-bit addition in which the second operand is constant.
2;
3; RUN: llc < %s -mtriple=s390x-linux-gnu -mcpu=z10 | FileCheck %s
4; RUN: llc < %s -mtriple=s390x-linux-gnu -mcpu=z196 | FileCheck %s
5
6declare i32 @foo()
7
8; Check additions of 1.
9define zeroext i1 @f1(i64 %dummy, i64 %a, i64 *%res) {
10; CHECK-LABEL: f1:
11; CHECK: aghi %r3, 1
12; CHECK-DAG: stg %r3, 0(%r4)
13; CHECK-DAG: ipm [[REG:%r[0-5]]]
14; CHECK-DAG: afi [[REG]], 1342177280
15; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
16; CHECK: br %r14
17  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 1)
18  %val = extractvalue {i64, i1} %t, 0
19  %obit = extractvalue {i64, i1} %t, 1
20  store i64 %val, i64 *%res
21  ret i1 %obit
22
23}
24
25; Check the high end of the AGHI range.
26define zeroext i1 @f2(i64 %dummy, i64 %a, i64 *%res) {
27; CHECK-LABEL: f2:
28; CHECK: aghi %r3, 32767
29; CHECK-DAG: stg %r3, 0(%r4)
30; CHECK-DAG: ipm [[REG:%r[0-5]]]
31; CHECK-DAG: afi [[REG]], 1342177280
32; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
33; CHECK: br %r14
34  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 32767)
35  %val = extractvalue {i64, i1} %t, 0
36  %obit = extractvalue {i64, i1} %t, 1
37  store i64 %val, i64 *%res
38  ret i1 %obit
39}
40
41; Check the next value up, which must use AGFI instead.
42define zeroext i1 @f3(i64 %dummy, i64 %a, i64 *%res) {
43; CHECK-LABEL: f3:
44; CHECK: agfi %r3, 32768
45; CHECK-DAG: stg %r3, 0(%r4)
46; CHECK-DAG: ipm [[REG:%r[0-5]]]
47; CHECK-DAG: afi [[REG]], 1342177280
48; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
49; CHECK: br %r14
50  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 32768)
51  %val = extractvalue {i64, i1} %t, 0
52  %obit = extractvalue {i64, i1} %t, 1
53  store i64 %val, i64 *%res
54  ret i1 %obit
55}
56
57; Check the high end of the AGFI range.
58define zeroext i1 @f4(i64 %dummy, i64 %a, i64 *%res) {
59; CHECK-LABEL: f4:
60; CHECK: agfi %r3, 2147483647
61; CHECK-DAG: stg %r3, 0(%r4)
62; CHECK-DAG: ipm [[REG:%r[0-5]]]
63; CHECK-DAG: afi [[REG]], 1342177280
64; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
65; CHECK: br %r14
66  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 2147483647)
67  %val = extractvalue {i64, i1} %t, 0
68  %obit = extractvalue {i64, i1} %t, 1
69  store i64 %val, i64 *%res
70  ret i1 %obit
71}
72
73; Check the next value up, which must be loaded into a register first.
74define zeroext i1 @f5(i64 %dummy, i64 %a, i64 *%res) {
75; CHECK-LABEL: f5:
76; CHECK: llilh [[REG1:%r[0-9]+]], 32768
77; CHECK: agr [[REG1]], %r3
78; CHECK-DAG: stg [[REG1]], 0(%r4)
79; CHECK-DAG: ipm [[REG:%r[0-5]]]
80; CHECK-DAG: afi [[REG]], 1342177280
81; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
82; CHECK: br %r14
83  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 2147483648)
84  %val = extractvalue {i64, i1} %t, 0
85  %obit = extractvalue {i64, i1} %t, 1
86  store i64 %val, i64 *%res
87  ret i1 %obit
88}
89
90; Check the high end of the negative AGHI range.
91define zeroext i1 @f6(i64 %dummy, i64 %a, i64 *%res) {
92; CHECK-LABEL: f6:
93; CHECK: aghi %r3, -1
94; CHECK-DAG: stg %r3, 0(%r4)
95; CHECK-DAG: ipm [[REG:%r[0-5]]]
96; CHECK-DAG: afi [[REG]], 1342177280
97; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
98; CHECK: br %r14
99  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 -1)
100  %val = extractvalue {i64, i1} %t, 0
101  %obit = extractvalue {i64, i1} %t, 1
102  store i64 %val, i64 *%res
103  ret i1 %obit
104}
105
106; Check the low end of the AGHI range.
107define zeroext i1 @f7(i64 %dummy, i64 %a, i64 *%res) {
108; CHECK-LABEL: f7:
109; CHECK: aghi %r3, -32768
110; CHECK-DAG: stg %r3, 0(%r4)
111; CHECK-DAG: ipm [[REG:%r[0-5]]]
112; CHECK-DAG: afi [[REG]], 1342177280
113; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
114; CHECK: br %r14
115  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 -32768)
116  %val = extractvalue {i64, i1} %t, 0
117  %obit = extractvalue {i64, i1} %t, 1
118  store i64 %val, i64 *%res
119  ret i1 %obit
120}
121
122; Check the next value down, which must use AGFI instead.
123define zeroext i1 @f8(i64 %dummy, i64 %a, i64 *%res) {
124; CHECK-LABEL: f8:
125; CHECK: agfi %r3, -32769
126; CHECK-DAG: stg %r3, 0(%r4)
127; CHECK-DAG: ipm [[REG:%r[0-5]]]
128; CHECK-DAG: afi [[REG]], 1342177280
129; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
130; CHECK: br %r14
131  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 -32769)
132  %val = extractvalue {i64, i1} %t, 0
133  %obit = extractvalue {i64, i1} %t, 1
134  store i64 %val, i64 *%res
135  ret i1 %obit
136}
137
138; Check the low end of the AGFI range.
139define zeroext i1 @f9(i64 %dummy, i64 %a, i64 *%res) {
140; CHECK-LABEL: f9:
141; CHECK: agfi %r3, -2147483648
142; CHECK-DAG: stg %r3, 0(%r4)
143; CHECK-DAG: ipm [[REG:%r[0-5]]]
144; CHECK-DAG: afi [[REG]], 1342177280
145; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
146; CHECK: br %r14
147  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 -2147483648)
148  %val = extractvalue {i64, i1} %t, 0
149  %obit = extractvalue {i64, i1} %t, 1
150  store i64 %val, i64 *%res
151  ret i1 %obit
152}
153
154; Check the next value down, which can use register subtraction instead.
155define zeroext i1 @f10(i64 %dummy, i64 %a, i64 *%res) {
156; CHECK-LABEL: f10:
157; CHECK: llilf [[REG1:%r[0-9]+]], 2147483649
158; CHECK: sgr %r3, [[REG1]]
159; CHECK-DAG: stg %r3, 0(%r4)
160; CHECK-DAG: ipm [[REG:%r[0-5]]]
161; CHECK-DAG: afi [[REG]], 1342177280
162; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
163; CHECK: br %r14
164  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 -2147483649)
165  %val = extractvalue {i64, i1} %t, 0
166  %obit = extractvalue {i64, i1} %t, 1
167  store i64 %val, i64 *%res
168  ret i1 %obit
169}
170
171; We may be able to use LLILH instead of LLILF.
172define zeroext i1 @f11(i64 %dummy, i64 %a, i64 *%res) {
173; CHECK-LABEL: f11:
174; CHECK: llilh [[REG1:%r[0-9]+]], 32769
175; CHECK: sgr %r3, [[REG1]]
176; CHECK-DAG: stg %r3, 0(%r4)
177; CHECK-DAG: ipm [[REG:%r[0-5]]]
178; CHECK-DAG: afi [[REG]], 1342177280
179; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
180; CHECK: br %r14
181  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 -2147549184)
182  %val = extractvalue {i64, i1} %t, 0
183  %obit = extractvalue {i64, i1} %t, 1
184  store i64 %val, i64 *%res
185  ret i1 %obit
186}
187
188; Check low end of the LLILF/SGR range.
189define zeroext i1 @f12(i64 %dummy, i64 %a, i64 *%res) {
190; CHECK-LABEL: f12:
191; CHECK: llilf [[REG1:%r[0-9]+]], 4294967295
192; CHECK: sgr %r3, [[REG1]]
193; CHECK-DAG: stg %r3, 0(%r4)
194; CHECK-DAG: ipm [[REG:%r[0-5]]]
195; CHECK-DAG: afi [[REG]], 1342177280
196; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
197; CHECK: br %r14
198  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 -4294967295)
199  %val = extractvalue {i64, i1} %t, 0
200  %obit = extractvalue {i64, i1} %t, 1
201  store i64 %val, i64 *%res
202  ret i1 %obit
203}
204
205; Check the next value down, which must use register addition instead.
206define zeroext i1 @f13(i64 %dummy, i64 %a, i64 *%res) {
207; CHECK-LABEL: f13:
208; CHECK: llihf [[REG1:%r[0-9]+]], 4294967295
209; CHECK: agr [[REG1]], %r3
210; CHECK-DAG: stg [[REG1]], 0(%r4)
211; CHECK-DAG: ipm [[REG:%r[0-5]]]
212; CHECK-DAG: afi [[REG]], 1342177280
213; CHECK-DAG: risbg %r2, [[REG]], 63, 191, 33
214; CHECK: br %r14
215  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 -4294967296)
216  %val = extractvalue {i64, i1} %t, 0
217  %obit = extractvalue {i64, i1} %t, 1
218  store i64 %val, i64 *%res
219  ret i1 %obit
220}
221
222; Check using the overflow result for a branch.
223define void @f14(i64 %dummy, i64 %a, i64 *%res) {
224; CHECK-LABEL: f14:
225; CHECK: aghi %r3, 1
226; CHECK: stg %r3, 0(%r4)
227; CHECK: {{jgo foo@PLT|bnor %r14}}
228; CHECK: {{br %r14|jg foo@PLT}}
229  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 1)
230  %val = extractvalue {i64, i1} %t, 0
231  %obit = extractvalue {i64, i1} %t, 1
232  store i64 %val, i64 *%res
233  br i1 %obit, label %call, label %exit
234
235call:
236  tail call i32 @foo()
237  br label %exit
238
239exit:
240  ret void
241}
242
243; ... and the same with the inverted direction.
244define void @f15(i64 %dummy, i64 %a, i64 *%res) {
245; CHECK-LABEL: f15:
246; CHECK: aghi %r3, 1
247; CHECK: stg %r3, 0(%r4)
248; CHECK: {{jgno foo@PLT|bor %r14}}
249; CHECK: {{br %r14|jg foo@PLT}}
250  %t = call {i64, i1} @llvm.sadd.with.overflow.i64(i64 %a, i64 1)
251  %val = extractvalue {i64, i1} %t, 0
252  %obit = extractvalue {i64, i1} %t, 1
253  store i64 %val, i64 *%res
254  br i1 %obit, label %exit, label %call
255
256call:
257  tail call i32 @foo()
258  br label %exit
259
260exit:
261  ret void
262}
263
264declare {i64, i1} @llvm.sadd.with.overflow.i64(i64, i64) nounwind readnone
265
266