1 ; RUN: llc -march=mips -mcpu=mips32 -verify-machineinstrs -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,ACC32,ACC32-TRAP
2 ; RUN: llc -march=mips -mcpu=mips32r2 -verify-machineinstrs -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,ACC32,ACC32-TRAP
3 ; RUN: llc -march=mips -mcpu=mips32r6 -verify-machineinstrs -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,GPR32,GPR32-TRAP
4 ; RUN: llc -march=mips64 -mcpu=mips64 -verify-machineinstrs -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,ACC64,ACC64-TRAP
5 ; RUN: llc -march=mips64 -mcpu=mips64r2 -verify-machineinstrs -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,ACC64,ACC64-TRAP
6 ; RUN: llc -march=mips64 -mcpu=mips64r6 -verify-machineinstrs -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,GPR64,GPR64-TRAP
8 ; RUN: llc -march=mips -mcpu=mips32 -mno-check-zero-division -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,ACC32,NOCHECK
9 ; RUN: llc -march=mips -mcpu=mips32r2 -mno-check-zero-division -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,ACC32,NOCHECK
10 ; RUN: llc -march=mips -mcpu=mips32r6 -mno-check-zero-division -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,GPR32,NOCHECK
11 ; RUN: llc -march=mips64 -mcpu=mips64 -mno-check-zero-division -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,ACC64,NOCHECK
12 ; RUN: llc -march=mips64 -mcpu=mips64r2 -mno-check-zero-division -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,ACC64,NOCHECK
13 ; RUN: llc -march=mips64 -mcpu=mips64r6 -mno-check-zero-division -relocation-model=pic < %s | FileCheck %s -check-prefixes=ALL,GPR64,NOCHECK
17 ; ACC32 - Accumulator based multiply/divide on 32-bit targets
18 ; ACC64 - Same as ACC32 but only for 64-bit targets
19 ; GPR32 - GPR based multiply/divide on 32-bit targets
20 ; GPR64 - Same as GPR32 but only for 64-bit targets
21 ; ACC32-TRAP - Same as TRAP and ACC32 combined
22 ; ACC64-TRAP - Same as TRAP and ACC64 combined
23 ; GPR32-TRAP - Same as TRAP and GPR32 combined
24 ; GPR64-TRAP - Same as TRAP and GPR64 combined
25 ; NOCHECK - Division by zero will not be detected
27 @g0 = common global i32 0, align 4
28 @g1 = common global i32 0, align 4
30 define i32 @sdiv1(i32 signext %a0, i32 signext %a1) nounwind readnone {
34 ; ACC32: div $zero, $4, $5
35 ; ACC32-TRAP: teq $5, $zero, 7
37 ; ACC64: div $zero, $4, $5
38 ; ACC64-TRAP: teq $5, $zero, 7
40 ; GPR32: div $2, $4, $5
41 ; GPR32-TRAP: teq $5, $zero, 7
43 ; GPR64: div $2, $4, $5
44 ; GPR64-TRAP: teq $5, $zero, 7
53 %div = sdiv i32 %a0, %a1
57 define i32 @srem1(i32 signext %a0, i32 signext %a1) nounwind readnone {
61 ; ACC32: div $zero, $4, $5
62 ; ACC32-TRAP: teq $5, $zero, 7
64 ; ACC64: div $zero, $4, $5
65 ; ACC64-TRAP: teq $5, $zero, 7
67 ; GPR32: mod $2, $4, $5
68 ; GPR32-TRAP: teq $5, $zero, 7
70 ; GPR64: mod $2, $4, $5
71 ; GPR64-TRAP: teq $5, $zero, 7
80 %rem = srem i32 %a0, %a1
84 define i32 @udiv1(i32 signext %a0, i32 signext %a1) nounwind readnone {
88 ; ACC32: divu $zero, $4, $5
89 ; ACC32-TRAP: teq $5, $zero, 7
91 ; ACC64: divu $zero, $4, $5
92 ; ACC64-TRAP: teq $5, $zero, 7
94 ; GPR32: divu $2, $4, $5
95 ; GPR32-TRAP: teq $5, $zero, 7
97 ; GPR64: divu $2, $4, $5
98 ; GPR64-TRAP: teq $5, $zero, 7
106 %div = udiv i32 %a0, %a1
110 define i32 @urem1(i32 signext %a0, i32 signext %a1) nounwind readnone {
114 ; ACC32: divu $zero, $4, $5
115 ; ACC32-TRAP: teq $5, $zero, 7
117 ; ACC64: divu $zero, $4, $5
118 ; ACC64-TRAP: teq $5, $zero, 7
120 ; GPR32: modu $2, $4, $5
121 ; GPR32-TRAP: teq $5, $zero, 7
123 ; GPR64: modu $2, $4, $5
124 ; GPR64-TRAP: teq $5, $zero, 7
133 %rem = urem i32 %a0, %a1
137 define i32 @sdivrem1(i32 signext %a0, i32 signext %a1, i32* nocapture %r) nounwind {
139 ; ALL-LABEL: sdivrem1:
141 ; ACC32: div $zero, $4, $5
142 ; ACC32-TRAP: teq $5, $zero, 7
145 ; ACC32: mfhi $[[R0:[0-9]+]]
146 ; ACC32: sw $[[R0]], 0(${{[0-9]+}})
148 ; ACC64: div $zero, $4, $5
149 ; ACC64-TRAP: teq $5, $zero, 7
152 ; ACC64: mfhi $[[R0:[0-9]+]]
153 ; ACC64: sw $[[R0]], 0(${{[0-9]+}})
155 ; GPR32-DAG: mod $[[R0:[0-9]+]], $4, $5
156 ; GPR32-TRAP: teq $5, $zero, 7
158 ; GPR32: sw $[[R0]], 0(${{[0-9]+}})
159 ; GPR32-DAG: div $2, $4, $5
160 ; GPR32-TRAP: teq $5, $zero, 7
162 ; GPR64-DAG: mod $[[R0:[0-9]+]], $4, $5
163 ; GPR64-TRAP: teq $5, $zero, 7
165 ; GPR64: sw $[[R0]], 0(${{[0-9]+}})
166 ; GPR64-DAG: div $2, $4, $5
167 ; GPR64-TRAP: teq $5, $zero, 7
172 %rem = srem i32 %a0, %a1
173 store i32 %rem, i32* %r, align 4
174 %div = sdiv i32 %a0, %a1
178 define i32 @udivrem1(i32 signext %a0, i32 signext %a1, i32* nocapture %r) nounwind {
180 ; ALL-LABEL: udivrem1:
182 ; ACC32: divu $zero, $4, $5
183 ; ACC32-TRAP: teq $5, $zero, 7
186 ; ACC32: mfhi $[[R0:[0-9]+]]
187 ; ACC32: sw $[[R0]], 0(${{[0-9]+}})
189 ; ACC64: divu $zero, $4, $5
190 ; ACC64-TRAP: teq $5, $zero, 7
193 ; ACC64: mfhi $[[R0:[0-9]+]]
194 ; ACC64: sw $[[R0]], 0(${{[0-9]+}})
196 ; GPR32-DAG: modu $[[R0:[0-9]+]], $4, $5
197 ; GPR32-TRAP: teq $5, $zero, 7
198 ; GPR32: sw $[[R0]], 0(${{[0-9]+}})
200 ; GPR32-DAG: divu $2, $4, $5
201 ; GPR32-TRAP: teq $5, $zero, 7
204 ; GPR64-DAG: modu $[[R0:[0-9]+]], $4, $5
205 ; GPR64-TRAP: teq $5, $zero, 7
207 ; GPR64: sw $[[R0]], 0(${{[0-9]+}})
208 ; GPR64-DAG: divu $2, $4, $5
209 ; GPR64-TRAP: teq $5, $zero, 7
214 %rem = urem i32 %a0, %a1
215 store i32 %rem, i32* %r, align 4
216 %div = udiv i32 %a0, %a1
220 ; FIXME: It's not clear what this is supposed to test.
221 define i32 @killFlags() {
223 %0 = load i32, i32* @g0, align 4
224 %1 = load i32, i32* @g1, align 4
225 %div = sdiv i32 %0, %1
229 define i64 @sdiv2(i64 %a0, i64 %a1) nounwind readnone {
233 ; ACC32: lw $25, %call16(__divdi3)(
236 ; ACC64: ddiv $zero, $4, $5
237 ; ACC64-TRAP: teq $5, $zero, 7
239 ; GPR64: ddiv $2, $4, $5
240 ; GPR64-TRAP: teq $5, $zero, 7
248 %div = sdiv i64 %a0, %a1
252 define i64 @srem2(i64 %a0, i64 %a1) nounwind readnone {
256 ; ACC32: lw $25, %call16(__moddi3)(
259 ; ACC64: div $zero, $4, $5
260 ; ACC64-TRAP: teq $5, $zero, 7
262 ; GPR64: dmod $2, $4, $5
263 ; GPR64-TRAP: teq $5, $zero, 7
271 %rem = srem i64 %a0, %a1
275 define i64 @udiv2(i64 %a0, i64 %a1) nounwind readnone {
279 ; ACC32: lw $25, %call16(__udivdi3)(
282 ; ACC64: divu $zero, $4, $5
283 ; ACC64-TRAP: teq $5, $zero, 7
285 ; GPR64: ddivu $2, $4, $5
286 ; GPR64-TRAP: teq $5, $zero, 7
293 %div = udiv i64 %a0, %a1
297 define i64 @urem2(i64 %a0, i64 %a1) nounwind readnone {
301 ; ACC32: lw $25, %call16(__umoddi3)(
304 ; ACC64: divu $zero, $4, $5
305 ; ACC64-TRAP: teq $5, $zero, 7
307 ; GPR64: dmodu $2, $4, $5
308 ; GPR64-TRAP: teq $5, $zero, 7
316 %rem = urem i64 %a0, %a1
320 define i64 @sdivrem2(i64 %a0, i64 %a1, i64* nocapture %r) nounwind {
322 ; ALL-LABEL: sdivrem2:
324 ; sdivrem2 is too complex to effectively check. We can at least check for the
326 ; ACC32: lw $25, %call16(__moddi3)(
328 ; ACC32: lw $25, %call16(__divdi3)(
331 ; ACC64: ddiv $zero, $4, $5
332 ; ACC64-TRAP: teq $5, $zero, 7
335 ; ACC64: mfhi $[[R0:[0-9]+]]
336 ; ACC64: sd $[[R0]], 0(${{[0-9]+}})
338 ; GPR64-DAG: dmod $[[R0:[0-9]+]], $4, $5
339 ; GPR64-TRAP: teq $5, $zero, 7
341 ; GPR64: sd $[[R0]], 0(${{[0-9]+}})
343 ; GPR64-DAG: ddiv $2, $4, $5
344 ; GPR64-TRAP: teq $5, $zero, 7
349 %rem = srem i64 %a0, %a1
350 store i64 %rem, i64* %r, align 8
351 %div = sdiv i64 %a0, %a1
355 define i64 @udivrem2(i64 %a0, i64 %a1, i64* nocapture %r) nounwind {
357 ; ALL-LABEL: udivrem2:
359 ; udivrem2 is too complex to effectively check. We can at least check for the
361 ; ACC32: lw $25, %call16(__umoddi3)(
363 ; ACC32: lw $25, %call16(__udivdi3)(
366 ; ACC64: ddivu $zero, $4, $5
367 ; ACC64-TRAP: teq $5, $zero, 7
370 ; ACC64: mfhi $[[R0:[0-9]+]]
371 ; ACC64: sd $[[R0]], 0(${{[0-9]+}})
373 ; GPR64: dmodu $[[R0:[0-9]+]], $4, $5
374 ; GPR64-TRAP: teq $5, $zero, 7
376 ; GPR64: sd $[[R0]], 0(${{[0-9]+}})
378 ; GPR64-DAG: ddivu $2, $4, $5
379 ; GPR64-TRAP: teq $5, $zero, 7
384 %rem = urem i64 %a0, %a1
385 store i64 %rem, i64* %r, align 8
386 %div = udiv i64 %a0, %a1