Eli Friedman | 73e8a784 | 2018-08-16 18:39:39 +0000 | [diff] [blame] | 1 | ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py |
| 2 | ; RUN: llc < %s -mtriple=sparc-unknown-linux-gnu | FileCheck %s --check-prefixes=SPARC |
| 3 | ; RUN: llc < %s -mtriple=sparc64-unknown-linux-gnu | FileCheck %s --check-prefixes=SPARC64 |
| 4 | |
| 5 | define { i128, i8 } @muloti_test(i128 %l, i128 %r) unnamed_addr #0 { |
| 6 | ; SPARC-LABEL: muloti_test: |
| 7 | ; SPARC: .cfi_startproc |
| 8 | ; SPARC-NEXT: ! %bb.0: ! %start |
| 9 | ; SPARC-NEXT: save %sp, -128, %sp |
| 10 | ; SPARC-NEXT: .cfi_def_cfa_register %fp |
| 11 | ; SPARC-NEXT: .cfi_window_save |
| 12 | ; SPARC-NEXT: .cfi_register 15, 31 |
| 13 | ; SPARC-NEXT: ld [%fp+92], %l3 |
| 14 | ; SPARC-NEXT: ld [%fp+96], %g2 |
| 15 | ; SPARC-NEXT: umul %i2, %i5, %g3 |
| 16 | ; SPARC-NEXT: rd %y, %g4 |
| 17 | ; SPARC-NEXT: st %g4, [%fp+-20] ! 4-byte Folded Spill |
| 18 | ; SPARC-NEXT: umul %i4, %i3, %g4 |
| 19 | ; SPARC-NEXT: rd %y, %l0 |
| 20 | ; SPARC-NEXT: st %l0, [%fp+-24] ! 4-byte Folded Spill |
| 21 | ; SPARC-NEXT: st %g2, [%sp+96] |
| 22 | ; SPARC-NEXT: st %i5, [%fp+-8] ! 4-byte Folded Spill |
| 23 | ; SPARC-NEXT: umul %i5, %i3, %l0 |
| 24 | ; SPARC-NEXT: rd %y, %l5 |
| 25 | ; SPARC-NEXT: st %l3, [%sp+92] |
| 26 | ; SPARC-NEXT: umul %l3, %i1, %l4 |
| 27 | ; SPARC-NEXT: rd %y, %i5 |
| 28 | ; SPARC-NEXT: st %i5, [%fp+-12] ! 4-byte Folded Spill |
| 29 | ; SPARC-NEXT: add %g4, %g3, %l2 |
| 30 | ; SPARC-NEXT: mov %i0, %i5 |
| 31 | ; SPARC-NEXT: umul %i0, %g2, %g3 |
| 32 | ; SPARC-NEXT: rd %y, %i0 |
| 33 | ; SPARC-NEXT: st %i0, [%fp+-16] ! 4-byte Folded Spill |
| 34 | ; SPARC-NEXT: add %l5, %l2, %l1 |
| 35 | ; SPARC-NEXT: st %i1, [%fp+-4] ! 4-byte Folded Spill |
| 36 | ; SPARC-NEXT: umul %i1, %g2, %g2 |
| 37 | ; SPARC-NEXT: rd %y, %l6 |
| 38 | ; SPARC-NEXT: add %g3, %l4, %i0 |
| 39 | ; SPARC-NEXT: add %l6, %i0, %l7 |
| 40 | ; SPARC-NEXT: addcc %g2, %l0, %l4 |
| 41 | ; SPARC-NEXT: mov %g0, %l0 |
| 42 | ; SPARC-NEXT: addxcc %l7, %l1, %i1 |
| 43 | ; SPARC-NEXT: mov %l0, %o0 |
| 44 | ; SPARC-NEXT: mov %l0, %o1 |
| 45 | ; SPARC-NEXT: mov %i2, %o2 |
| 46 | ; SPARC-NEXT: mov %i3, %o3 |
| 47 | ; SPARC-NEXT: mov %l0, %o4 |
| 48 | ; SPARC-NEXT: call __multi3 |
| 49 | ; SPARC-NEXT: mov %l0, %o5 |
| 50 | ; SPARC-NEXT: addcc %o1, %l4, %i3 |
| 51 | ; SPARC-NEXT: addxcc %o0, %i1, %g2 |
| 52 | ; SPARC-NEXT: mov 1, %g3 |
| 53 | ; SPARC-NEXT: cmp %g2, %o0 |
| 54 | ; SPARC-NEXT: bcs .LBB0_2 |
| 55 | ; SPARC-NEXT: mov %g3, %g4 |
| 56 | ; SPARC-NEXT: ! %bb.1: ! %start |
| 57 | ; SPARC-NEXT: mov %l0, %g4 |
| 58 | ; SPARC-NEXT: .LBB0_2: ! %start |
| 59 | ; SPARC-NEXT: cmp %i3, %o1 |
| 60 | ; SPARC-NEXT: bcs .LBB0_4 |
| 61 | ; SPARC-NEXT: mov %g3, %o4 |
| 62 | ; SPARC-NEXT: ! %bb.3: ! %start |
| 63 | ; SPARC-NEXT: mov %l0, %o4 |
| 64 | ; SPARC-NEXT: .LBB0_4: ! %start |
| 65 | ; SPARC-NEXT: cmp %g2, %o0 |
| 66 | ; SPARC-NEXT: be .LBB0_6 |
| 67 | ; SPARC-NEXT: nop |
| 68 | ; SPARC-NEXT: ! %bb.5: ! %start |
| 69 | ; SPARC-NEXT: mov %g4, %o4 |
| 70 | ; SPARC-NEXT: .LBB0_6: ! %start |
| 71 | ; SPARC-NEXT: xor %g2, %o0, %i1 |
| 72 | ; SPARC-NEXT: xor %i3, %o1, %g4 |
| 73 | ; SPARC-NEXT: or %g4, %i1, %i1 |
| 74 | ; SPARC-NEXT: cmp %i1, 0 |
| 75 | ; SPARC-NEXT: be .LBB0_8 |
| 76 | ; SPARC-NEXT: mov %l0, %g4 |
| 77 | ; SPARC-NEXT: ! %bb.7: ! %start |
| 78 | ; SPARC-NEXT: mov %o4, %g4 |
| 79 | ; SPARC-NEXT: .LBB0_8: ! %start |
| 80 | ; SPARC-NEXT: cmp %l1, %l5 |
| 81 | ; SPARC-NEXT: mov %g3, %l1 |
| 82 | ; SPARC-NEXT: bcs .LBB0_10 |
| 83 | ; SPARC-NEXT: mov %i5, %i1 |
| 84 | ; SPARC-NEXT: ! %bb.9: ! %start |
| 85 | ; SPARC-NEXT: mov %l0, %l1 |
| 86 | ; SPARC-NEXT: .LBB0_10: ! %start |
| 87 | ; SPARC-NEXT: cmp %l2, 0 |
| 88 | ; SPARC-NEXT: be .LBB0_12 |
| 89 | ; SPARC-NEXT: mov %l0, %o0 |
| 90 | ; SPARC-NEXT: ! %bb.11: ! %start |
| 91 | ; SPARC-NEXT: mov %l1, %o0 |
| 92 | ; SPARC-NEXT: .LBB0_12: ! %start |
| 93 | ; SPARC-NEXT: cmp %i2, 0 |
| 94 | ; SPARC-NEXT: bne .LBB0_14 |
| 95 | ; SPARC-NEXT: mov %g3, %i2 |
| 96 | ; SPARC-NEXT: ! %bb.13: ! %start |
| 97 | ; SPARC-NEXT: mov %l0, %i2 |
| 98 | ; SPARC-NEXT: .LBB0_14: ! %start |
| 99 | ; SPARC-NEXT: cmp %i4, 0 |
| 100 | ; SPARC-NEXT: bne .LBB0_16 |
| 101 | ; SPARC-NEXT: mov %g3, %o1 |
| 102 | ; SPARC-NEXT: ! %bb.15: ! %start |
| 103 | ; SPARC-NEXT: mov %l0, %o1 |
| 104 | ; SPARC-NEXT: .LBB0_16: ! %start |
| 105 | ; SPARC-NEXT: ld [%fp+-24], %i5 ! 4-byte Folded Reload |
| 106 | ; SPARC-NEXT: cmp %i5, 0 |
| 107 | ; SPARC-NEXT: bne .LBB0_18 |
| 108 | ; SPARC-NEXT: mov %g3, %l5 |
| 109 | ; SPARC-NEXT: ! %bb.17: ! %start |
| 110 | ; SPARC-NEXT: mov %l0, %l5 |
| 111 | ; SPARC-NEXT: .LBB0_18: ! %start |
| 112 | ; SPARC-NEXT: ld [%fp+-20], %i5 ! 4-byte Folded Reload |
| 113 | ; SPARC-NEXT: cmp %i5, 0 |
| 114 | ; SPARC-NEXT: bne .LBB0_20 |
| 115 | ; SPARC-NEXT: mov %g3, %l1 |
| 116 | ; SPARC-NEXT: ! %bb.19: ! %start |
| 117 | ; SPARC-NEXT: mov %l0, %l1 |
| 118 | ; SPARC-NEXT: .LBB0_20: ! %start |
| 119 | ; SPARC-NEXT: cmp %l7, %l6 |
| 120 | ; SPARC-NEXT: bcs .LBB0_22 |
| 121 | ; SPARC-NEXT: mov %g3, %l6 |
| 122 | ; SPARC-NEXT: ! %bb.21: ! %start |
| 123 | ; SPARC-NEXT: mov %l0, %l6 |
| 124 | ; SPARC-NEXT: .LBB0_22: ! %start |
| 125 | ; SPARC-NEXT: cmp %i0, 0 |
| 126 | ; SPARC-NEXT: be .LBB0_24 |
| 127 | ; SPARC-NEXT: mov %l0, %l2 |
| 128 | ; SPARC-NEXT: ! %bb.23: ! %start |
| 129 | ; SPARC-NEXT: mov %l6, %l2 |
| 130 | ; SPARC-NEXT: .LBB0_24: ! %start |
| 131 | ; SPARC-NEXT: cmp %l3, 0 |
| 132 | ; SPARC-NEXT: bne .LBB0_26 |
| 133 | ; SPARC-NEXT: mov %g3, %l3 |
| 134 | ; SPARC-NEXT: ! %bb.25: ! %start |
| 135 | ; SPARC-NEXT: mov %l0, %l3 |
| 136 | ; SPARC-NEXT: .LBB0_26: ! %start |
| 137 | ; SPARC-NEXT: cmp %i1, 0 |
| 138 | ; SPARC-NEXT: bne .LBB0_28 |
| 139 | ; SPARC-NEXT: mov %g3, %l4 |
| 140 | ; SPARC-NEXT: ! %bb.27: ! %start |
| 141 | ; SPARC-NEXT: mov %l0, %l4 |
| 142 | ; SPARC-NEXT: .LBB0_28: ! %start |
| 143 | ; SPARC-NEXT: and %o1, %i2, %i2 |
| 144 | ; SPARC-NEXT: ld [%fp+-16], %i0 ! 4-byte Folded Reload |
| 145 | ; SPARC-NEXT: cmp %i0, 0 |
| 146 | ; SPARC-NEXT: and %l4, %l3, %l4 |
| 147 | ; SPARC-NEXT: bne .LBB0_30 |
| 148 | ; SPARC-NEXT: mov %g3, %l6 |
| 149 | ; SPARC-NEXT: ! %bb.29: ! %start |
| 150 | ; SPARC-NEXT: mov %l0, %l6 |
| 151 | ; SPARC-NEXT: .LBB0_30: ! %start |
| 152 | ; SPARC-NEXT: or %i2, %l5, %l3 |
| 153 | ; SPARC-NEXT: ld [%fp+-12], %i0 ! 4-byte Folded Reload |
| 154 | ; SPARC-NEXT: cmp %i0, 0 |
| 155 | ; SPARC-NEXT: or %l4, %l6, %i2 |
| 156 | ; SPARC-NEXT: bne .LBB0_32 |
| 157 | ; SPARC-NEXT: mov %g3, %l4 |
| 158 | ; SPARC-NEXT: ! %bb.31: ! %start |
| 159 | ; SPARC-NEXT: mov %l0, %l4 |
| 160 | ; SPARC-NEXT: .LBB0_32: ! %start |
| 161 | ; SPARC-NEXT: or %l3, %l1, %l1 |
| 162 | ; SPARC-NEXT: ld [%fp+-8], %i0 ! 4-byte Folded Reload |
| 163 | ; SPARC-NEXT: or %i0, %i4, %i0 |
| 164 | ; SPARC-NEXT: cmp %i0, 0 |
| 165 | ; SPARC-NEXT: or %i2, %l4, %i5 |
| 166 | ; SPARC-NEXT: bne .LBB0_34 |
| 167 | ; SPARC-NEXT: mov %g3, %i2 |
| 168 | ; SPARC-NEXT: ! %bb.33: ! %start |
| 169 | ; SPARC-NEXT: mov %l0, %i2 |
| 170 | ; SPARC-NEXT: .LBB0_34: ! %start |
| 171 | ; SPARC-NEXT: or %l1, %o0, %i4 |
| 172 | ; SPARC-NEXT: ld [%fp+-4], %i0 ! 4-byte Folded Reload |
| 173 | ; SPARC-NEXT: or %i0, %i1, %i0 |
| 174 | ; SPARC-NEXT: cmp %i0, 0 |
| 175 | ; SPARC-NEXT: bne .LBB0_36 |
| 176 | ; SPARC-NEXT: or %i5, %l2, %i0 |
| 177 | ; SPARC-NEXT: ! %bb.35: ! %start |
| 178 | ; SPARC-NEXT: mov %l0, %g3 |
| 179 | ; SPARC-NEXT: .LBB0_36: ! %start |
| 180 | ; SPARC-NEXT: and %g3, %i2, %i1 |
| 181 | ; SPARC-NEXT: or %i1, %i0, %i0 |
| 182 | ; SPARC-NEXT: or %i0, %i4, %i0 |
| 183 | ; SPARC-NEXT: or %i0, %g4, %i0 |
| 184 | ; SPARC-NEXT: and %i0, 1, %i4 |
| 185 | ; SPARC-NEXT: mov %g2, %i0 |
| 186 | ; SPARC-NEXT: mov %i3, %i1 |
| 187 | ; SPARC-NEXT: mov %o2, %i2 |
| 188 | ; SPARC-NEXT: ret |
| 189 | ; SPARC-NEXT: restore %g0, %o3, %o3 |
| 190 | ; |
| 191 | ; SPARC64-LABEL: muloti_test: |
| 192 | ; SPARC64: .cfi_startproc |
| 193 | ; SPARC64-NEXT: .register %g2, #scratch |
| 194 | ; SPARC64-NEXT: ! %bb.0: ! %start |
| 195 | ; SPARC64-NEXT: save %sp, -176, %sp |
| 196 | ; SPARC64-NEXT: .cfi_def_cfa_register %fp |
| 197 | ; SPARC64-NEXT: .cfi_window_save |
| 198 | ; SPARC64-NEXT: .cfi_register 15, 31 |
| 199 | ; SPARC64-NEXT: srax %i2, 63, %o0 |
| 200 | ; SPARC64-NEXT: srax %i1, 63, %o2 |
| 201 | ; SPARC64-NEXT: mov %i2, %o1 |
| 202 | ; SPARC64-NEXT: call __multi3 |
| 203 | ; SPARC64-NEXT: mov %i1, %o3 |
| 204 | ; SPARC64-NEXT: mov %o0, %i4 |
| 205 | ; SPARC64-NEXT: mov %o1, %i5 |
| 206 | ; SPARC64-NEXT: srax %i0, 63, %o0 |
| 207 | ; SPARC64-NEXT: srax %i3, 63, %o2 |
| 208 | ; SPARC64-NEXT: mov %i0, %o1 |
| 209 | ; SPARC64-NEXT: call __multi3 |
| 210 | ; SPARC64-NEXT: mov %i3, %o3 |
| 211 | ; SPARC64-NEXT: mov %o0, %l0 |
| 212 | ; SPARC64-NEXT: add %o1, %i5, %i5 |
| 213 | ; SPARC64-NEXT: mov 0, %o0 |
| 214 | ; SPARC64-NEXT: mov %i1, %o1 |
| 215 | ; SPARC64-NEXT: mov %o0, %o2 |
| 216 | ; SPARC64-NEXT: call __multi3 |
| 217 | ; SPARC64-NEXT: mov %i3, %o3 |
| 218 | ; SPARC64-NEXT: add %o0, %i5, %i1 |
| 219 | ; SPARC64-NEXT: mov %g0, %i3 |
| 220 | ; SPARC64-NEXT: cmp %i1, %o0 |
| 221 | ; SPARC64-NEXT: mov %i3, %g2 |
| 222 | ; SPARC64-NEXT: movcs %xcc, 1, %g2 |
| 223 | ; SPARC64-NEXT: cmp %i5, 0 |
| 224 | ; SPARC64-NEXT: move %xcc, 0, %g2 |
| 225 | ; SPARC64-NEXT: cmp %i4, 0 |
| 226 | ; SPARC64-NEXT: mov %i3, %i4 |
| 227 | ; SPARC64-NEXT: movne %xcc, 1, %i4 |
| 228 | ; SPARC64-NEXT: cmp %l0, 0 |
| 229 | ; SPARC64-NEXT: mov %i3, %i5 |
| 230 | ; SPARC64-NEXT: movne %xcc, 1, %i5 |
| 231 | ; SPARC64-NEXT: cmp %i2, 0 |
| 232 | ; SPARC64-NEXT: mov %i3, %i2 |
| 233 | ; SPARC64-NEXT: movne %xcc, 1, %i2 |
| 234 | ; SPARC64-NEXT: cmp %i0, 0 |
| 235 | ; SPARC64-NEXT: movne %xcc, 1, %i3 |
| 236 | ; SPARC64-NEXT: and %i3, %i2, %i0 |
| 237 | ; SPARC64-NEXT: or %i0, %i5, %i0 |
| 238 | ; SPARC64-NEXT: or %i0, %i4, %i0 |
| 239 | ; SPARC64-NEXT: or %i0, %g2, %i0 |
| 240 | ; SPARC64-NEXT: srl %i0, 0, %i2 |
| 241 | ; SPARC64-NEXT: mov %i1, %i0 |
| 242 | ; SPARC64-NEXT: ret |
| 243 | ; SPARC64-NEXT: restore %g0, %o1, %o1 |
| 244 | start: |
| 245 | %0 = tail call { i128, i1 } @llvm.umul.with.overflow.i128(i128 %l, i128 %r) #2 |
| 246 | %1 = extractvalue { i128, i1 } %0, 0 |
| 247 | %2 = extractvalue { i128, i1 } %0, 1 |
| 248 | %3 = zext i1 %2 to i8 |
| 249 | %4 = insertvalue { i128, i8 } undef, i128 %1, 0 |
| 250 | %5 = insertvalue { i128, i8 } %4, i8 %3, 1 |
| 251 | ret { i128, i8 } %5 |
| 252 | } |
| 253 | |
| 254 | ; Function Attrs: nounwind readnone speculatable |
| 255 | declare { i128, i1 } @llvm.umul.with.overflow.i128(i128, i128) #1 |
| 256 | |
| 257 | attributes #0 = { nounwind readnone uwtable } |
| 258 | attributes #1 = { nounwind readnone speculatable } |
| 259 | attributes #2 = { nounwind } |