1 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2 ; RUN: llc < %s -mtriple=riscv32 -mattr=+m | FileCheck %s --check-prefixes=RISCV32
4 define { i128, i8 } @muloti_test(i128 %l, i128 %r) #0 {
5 ; RISCV32-LABEL: muloti_test:
6 ; RISCV32: # %bb.0: # %start
7 ; RISCV32-NEXT: addi sp, sp, -96
8 ; RISCV32-NEXT: sw ra, 92(sp)
9 ; RISCV32-NEXT: sw s0, 88(sp)
10 ; RISCV32-NEXT: sw s1, 84(sp)
11 ; RISCV32-NEXT: sw s2, 80(sp)
12 ; RISCV32-NEXT: sw s3, 76(sp)
13 ; RISCV32-NEXT: sw s4, 72(sp)
14 ; RISCV32-NEXT: sw s5, 68(sp)
15 ; RISCV32-NEXT: sw s6, 64(sp)
16 ; RISCV32-NEXT: sw s7, 60(sp)
17 ; RISCV32-NEXT: sw s8, 56(sp)
18 ; RISCV32-NEXT: lw s2, 12(a1)
19 ; RISCV32-NEXT: lw s6, 8(a1)
20 ; RISCV32-NEXT: lw s3, 12(a2)
21 ; RISCV32-NEXT: lw s7, 8(a2)
22 ; RISCV32-NEXT: lw s0, 0(a1)
23 ; RISCV32-NEXT: lw s8, 4(a1)
24 ; RISCV32-NEXT: lw s1, 0(a2)
25 ; RISCV32-NEXT: lw s5, 4(a2)
26 ; RISCV32-NEXT: mv s4, a0
27 ; RISCV32-NEXT: sw zero, 20(sp)
28 ; RISCV32-NEXT: sw zero, 16(sp)
29 ; RISCV32-NEXT: sw zero, 36(sp)
30 ; RISCV32-NEXT: sw zero, 32(sp)
31 ; RISCV32-NEXT: sw s5, 12(sp)
32 ; RISCV32-NEXT: sw s1, 8(sp)
33 ; RISCV32-NEXT: sw s8, 28(sp)
34 ; RISCV32-NEXT: addi a0, sp, 40
35 ; RISCV32-NEXT: addi a1, sp, 24
36 ; RISCV32-NEXT: addi a2, sp, 8
37 ; RISCV32-NEXT: sw s0, 24(sp)
38 ; RISCV32-NEXT: call __multi3
39 ; RISCV32-NEXT: mul a0, s8, s7
40 ; RISCV32-NEXT: mul a1, s3, s0
41 ; RISCV32-NEXT: add a0, a1, a0
42 ; RISCV32-NEXT: mulhu a5, s7, s0
43 ; RISCV32-NEXT: add a0, a5, a0
44 ; RISCV32-NEXT: mul a1, s5, s6
45 ; RISCV32-NEXT: mul a2, s2, s1
46 ; RISCV32-NEXT: add a1, a2, a1
47 ; RISCV32-NEXT: mulhu t0, s6, s1
48 ; RISCV32-NEXT: add t1, t0, a1
49 ; RISCV32-NEXT: add a6, t1, a0
50 ; RISCV32-NEXT: mul a1, s7, s0
51 ; RISCV32-NEXT: mul a3, s6, s1
52 ; RISCV32-NEXT: add a4, a3, a1
53 ; RISCV32-NEXT: lw a1, 52(sp)
54 ; RISCV32-NEXT: lw a2, 48(sp)
55 ; RISCV32-NEXT: sltu a3, a4, a3
56 ; RISCV32-NEXT: add a3, a6, a3
57 ; RISCV32-NEXT: add a3, a1, a3
58 ; RISCV32-NEXT: add a6, a2, a4
59 ; RISCV32-NEXT: sltu a2, a6, a2
60 ; RISCV32-NEXT: add a7, a3, a2
61 ; RISCV32-NEXT: beq a7, a1, .LBB0_2
62 ; RISCV32-NEXT: # %bb.1: # %start
63 ; RISCV32-NEXT: sltu a2, a7, a1
64 ; RISCV32-NEXT: .LBB0_2: # %start
65 ; RISCV32-NEXT: sltu a0, a0, a5
66 ; RISCV32-NEXT: snez a1, s8
67 ; RISCV32-NEXT: snez a3, s3
68 ; RISCV32-NEXT: and a1, a3, a1
69 ; RISCV32-NEXT: mulhu a3, s3, s0
70 ; RISCV32-NEXT: snez a3, a3
71 ; RISCV32-NEXT: or a1, a1, a3
72 ; RISCV32-NEXT: mulhu a3, s8, s7
73 ; RISCV32-NEXT: snez a3, a3
74 ; RISCV32-NEXT: or a1, a1, a3
75 ; RISCV32-NEXT: or a0, a1, a0
76 ; RISCV32-NEXT: sltu a1, t1, t0
77 ; RISCV32-NEXT: snez a3, s5
78 ; RISCV32-NEXT: snez a4, s2
79 ; RISCV32-NEXT: and a3, a4, a3
80 ; RISCV32-NEXT: mulhu a4, s2, s1
81 ; RISCV32-NEXT: snez a4, a4
82 ; RISCV32-NEXT: or a3, a3, a4
83 ; RISCV32-NEXT: mulhu a4, s5, s6
84 ; RISCV32-NEXT: snez a4, a4
85 ; RISCV32-NEXT: or a3, a3, a4
86 ; RISCV32-NEXT: or a1, a3, a1
87 ; RISCV32-NEXT: or a3, s7, s3
88 ; RISCV32-NEXT: snez a3, a3
89 ; RISCV32-NEXT: or a4, s6, s2
90 ; RISCV32-NEXT: snez a4, a4
91 ; RISCV32-NEXT: and a3, a4, a3
92 ; RISCV32-NEXT: or a1, a3, a1
93 ; RISCV32-NEXT: or a0, a1, a0
94 ; RISCV32-NEXT: lw a1, 44(sp)
95 ; RISCV32-NEXT: lw a3, 40(sp)
96 ; RISCV32-NEXT: or a0, a0, a2
97 ; RISCV32-NEXT: andi a0, a0, 1
98 ; RISCV32-NEXT: sw a1, 4(s4)
99 ; RISCV32-NEXT: sw a3, 0(s4)
100 ; RISCV32-NEXT: sw a6, 8(s4)
101 ; RISCV32-NEXT: sw a7, 12(s4)
102 ; RISCV32-NEXT: sb a0, 16(s4)
103 ; RISCV32-NEXT: lw s8, 56(sp)
104 ; RISCV32-NEXT: lw s7, 60(sp)
105 ; RISCV32-NEXT: lw s6, 64(sp)
106 ; RISCV32-NEXT: lw s5, 68(sp)
107 ; RISCV32-NEXT: lw s4, 72(sp)
108 ; RISCV32-NEXT: lw s3, 76(sp)
109 ; RISCV32-NEXT: lw s2, 80(sp)
110 ; RISCV32-NEXT: lw s1, 84(sp)
111 ; RISCV32-NEXT: lw s0, 88(sp)
112 ; RISCV32-NEXT: lw ra, 92(sp)
113 ; RISCV32-NEXT: addi sp, sp, 96
116 %0 = tail call { i128, i1 } @llvm.umul.with.overflow.i128(i128 %l, i128 %r) #2
117 %1 = extractvalue { i128, i1 } %0, 0
118 %2 = extractvalue { i128, i1 } %0, 1
119 %3 = zext i1 %2 to i8
120 %4 = insertvalue { i128, i8 } undef, i128 %1, 0
121 %5 = insertvalue { i128, i8 } %4, i8 %3, 1
125 ; Function Attrs: nounwind readnone speculatable
126 declare { i128, i1 } @llvm.umul.with.overflow.i128(i128, i128) #1
128 attributes #0 = { nounwind readnone }
129 attributes #1 = { nounwind readnone speculatable }
130 attributes #2 = { nounwind }