Bump version to 19.1.0-rc3
[llvm-project.git] / llvm / test / CodeGen / AMDGPU / mul_uint24-amdgcn.ll
bloba1099554559afabb1ba77e1317396b01bd65a7cd
1 ; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py
2 ; RUN: llc -mtriple=amdgcn -verify-machineinstrs < %s | FileCheck -enable-var-scope -check-prefixes=GCN,SI %s
3 ; RUN: llc -mtriple=amdgcn -mcpu=tonga -mattr=-flat-for-global -verify-machineinstrs < %s | FileCheck -enable-var-scope -check-prefixes=GCN,VI %s
4 ; RUN: llc -mtriple=amdgcn -mcpu=gfx900 -mattr=-flat-for-global -verify-machineinstrs < %s | FileCheck -enable-var-scope -check-prefixes=GCN,GFX9 %s
6 declare i32 @llvm.amdgcn.workitem.id.x() nounwind readnone
7 declare i32 @llvm.amdgcn.workitem.id.y() nounwind readnone
9 define amdgpu_kernel void @test_umul24_i32(ptr addrspace(1) %out, i32 %a, i32 %b) {
10 ; SI-LABEL: test_umul24_i32:
11 ; SI:       ; %bb.0: ; %entry
12 ; SI-NEXT:    s_load_dwordx4 s[0:3], s[2:3], 0x9
13 ; SI-NEXT:    s_mov_b32 s7, 0xf000
14 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
15 ; SI-NEXT:    s_and_b32 s2, s2, 0xffffff
16 ; SI-NEXT:    s_and_b32 s3, s3, 0xffffff
17 ; SI-NEXT:    s_mul_i32 s2, s2, s3
18 ; SI-NEXT:    s_mov_b32 s6, -1
19 ; SI-NEXT:    s_mov_b32 s4, s0
20 ; SI-NEXT:    s_mov_b32 s5, s1
21 ; SI-NEXT:    v_mov_b32_e32 v0, s2
22 ; SI-NEXT:    buffer_store_dword v0, off, s[4:7], 0
23 ; SI-NEXT:    s_endpgm
25 ; VI-LABEL: test_umul24_i32:
26 ; VI:       ; %bb.0: ; %entry
27 ; VI-NEXT:    s_load_dwordx4 s[0:3], s[2:3], 0x24
28 ; VI-NEXT:    s_mov_b32 s7, 0xf000
29 ; VI-NEXT:    s_mov_b32 s6, -1
30 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
31 ; VI-NEXT:    s_mov_b32 s4, s0
32 ; VI-NEXT:    s_mov_b32 s5, s1
33 ; VI-NEXT:    s_and_b32 s0, s2, 0xffffff
34 ; VI-NEXT:    s_and_b32 s1, s3, 0xffffff
35 ; VI-NEXT:    s_mul_i32 s0, s0, s1
36 ; VI-NEXT:    v_mov_b32_e32 v0, s0
37 ; VI-NEXT:    buffer_store_dword v0, off, s[4:7], 0
38 ; VI-NEXT:    s_endpgm
40 ; GFX9-LABEL: test_umul24_i32:
41 ; GFX9:       ; %bb.0: ; %entry
42 ; GFX9-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
43 ; GFX9-NEXT:    s_mov_b32 s3, 0xf000
44 ; GFX9-NEXT:    s_mov_b32 s2, -1
45 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
46 ; GFX9-NEXT:    s_mov_b32 s0, s4
47 ; GFX9-NEXT:    s_mov_b32 s1, s5
48 ; GFX9-NEXT:    s_and_b32 s4, s6, 0xffffff
49 ; GFX9-NEXT:    s_and_b32 s5, s7, 0xffffff
50 ; GFX9-NEXT:    s_mul_i32 s4, s4, s5
51 ; GFX9-NEXT:    v_mov_b32_e32 v0, s4
52 ; GFX9-NEXT:    buffer_store_dword v0, off, s[0:3], 0
53 ; GFX9-NEXT:    s_endpgm
54 entry:
55   %0 = shl i32 %a, 8
56   %a_24 = lshr i32 %0, 8
57   %1 = shl i32 %b, 8
58   %b_24 = lshr i32 %1, 8
59   %2 = mul i32 %a_24, %b_24
60   store i32 %2, ptr addrspace(1) %out
61   ret void
64 define amdgpu_kernel void @test_umul24_i16_sext(ptr addrspace(1) %out, i16 %a, i16 %b) {
65 ; SI-LABEL: test_umul24_i16_sext:
66 ; SI:       ; %bb.0: ; %entry
67 ; SI-NEXT:    s_load_dword s4, s[2:3], 0xb
68 ; SI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x9
69 ; SI-NEXT:    s_mov_b32 s3, 0xf000
70 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
71 ; SI-NEXT:    s_lshr_b32 s2, s4, 16
72 ; SI-NEXT:    s_mul_i32 s4, s4, s2
73 ; SI-NEXT:    s_sext_i32_i16 s4, s4
74 ; SI-NEXT:    s_mov_b32 s2, -1
75 ; SI-NEXT:    v_mov_b32_e32 v0, s4
76 ; SI-NEXT:    buffer_store_dword v0, off, s[0:3], 0
77 ; SI-NEXT:    s_endpgm
79 ; VI-LABEL: test_umul24_i16_sext:
80 ; VI:       ; %bb.0: ; %entry
81 ; VI-NEXT:    s_load_dword s4, s[2:3], 0x2c
82 ; VI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x24
83 ; VI-NEXT:    s_mov_b32 s3, 0xf000
84 ; VI-NEXT:    s_mov_b32 s2, -1
85 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
86 ; VI-NEXT:    s_lshr_b32 s5, s4, 16
87 ; VI-NEXT:    s_mul_i32 s4, s4, s5
88 ; VI-NEXT:    s_sext_i32_i16 s4, s4
89 ; VI-NEXT:    v_mov_b32_e32 v0, s4
90 ; VI-NEXT:    buffer_store_dword v0, off, s[0:3], 0
91 ; VI-NEXT:    s_endpgm
93 ; GFX9-LABEL: test_umul24_i16_sext:
94 ; GFX9:       ; %bb.0: ; %entry
95 ; GFX9-NEXT:    s_load_dword s4, s[2:3], 0x2c
96 ; GFX9-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x24
97 ; GFX9-NEXT:    s_mov_b32 s3, 0xf000
98 ; GFX9-NEXT:    s_mov_b32 s2, -1
99 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
100 ; GFX9-NEXT:    s_lshr_b32 s5, s4, 16
101 ; GFX9-NEXT:    s_mul_i32 s4, s4, s5
102 ; GFX9-NEXT:    s_sext_i32_i16 s4, s4
103 ; GFX9-NEXT:    v_mov_b32_e32 v0, s4
104 ; GFX9-NEXT:    buffer_store_dword v0, off, s[0:3], 0
105 ; GFX9-NEXT:    s_endpgm
106 entry:
107   %mul = mul i16 %a, %b
108   %ext = sext i16 %mul to i32
109   store i32 %ext, ptr addrspace(1) %out
110   ret void
113 define amdgpu_kernel void @test_umul24_i16_vgpr_sext(ptr addrspace(1) %out, ptr addrspace(1) %in) {
114 ; SI-LABEL: test_umul24_i16_vgpr_sext:
115 ; SI:       ; %bb.0:
116 ; SI-NEXT:    s_load_dwordx4 s[0:3], s[2:3], 0x9
117 ; SI-NEXT:    s_mov_b32 s7, 0xf000
118 ; SI-NEXT:    s_mov_b32 s10, 0
119 ; SI-NEXT:    v_lshlrev_b32_e32 v2, 1, v0
120 ; SI-NEXT:    v_mov_b32_e32 v3, 0
121 ; SI-NEXT:    v_lshlrev_b32_e32 v0, 1, v1
122 ; SI-NEXT:    s_mov_b32 s11, s7
123 ; SI-NEXT:    v_mov_b32_e32 v1, v3
124 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
125 ; SI-NEXT:    s_mov_b64 s[8:9], s[2:3]
126 ; SI-NEXT:    buffer_load_ushort v2, v[2:3], s[8:11], 0 addr64
127 ; SI-NEXT:    buffer_load_ushort v0, v[0:1], s[8:11], 0 addr64
128 ; SI-NEXT:    s_mov_b32 s6, -1
129 ; SI-NEXT:    s_mov_b32 s4, s0
130 ; SI-NEXT:    s_mov_b32 s5, s1
131 ; SI-NEXT:    s_waitcnt vmcnt(0)
132 ; SI-NEXT:    v_mul_u32_u24_e32 v0, v2, v0
133 ; SI-NEXT:    v_bfe_i32 v0, v0, 0, 16
134 ; SI-NEXT:    buffer_store_dword v0, off, s[4:7], 0
135 ; SI-NEXT:    s_endpgm
137 ; VI-LABEL: test_umul24_i16_vgpr_sext:
138 ; VI:       ; %bb.0:
139 ; VI-NEXT:    s_load_dwordx4 s[0:3], s[2:3], 0x24
140 ; VI-NEXT:    v_lshlrev_b32_e32 v0, 1, v0
141 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
142 ; VI-NEXT:    v_mov_b32_e32 v3, s3
143 ; VI-NEXT:    v_add_u32_e32 v2, vcc, s2, v0
144 ; VI-NEXT:    v_addc_u32_e32 v3, vcc, 0, v3, vcc
145 ; VI-NEXT:    v_lshlrev_b32_e32 v0, 1, v1
146 ; VI-NEXT:    v_mov_b32_e32 v1, s3
147 ; VI-NEXT:    v_add_u32_e32 v0, vcc, s2, v0
148 ; VI-NEXT:    v_addc_u32_e32 v1, vcc, 0, v1, vcc
149 ; VI-NEXT:    flat_load_ushort v2, v[2:3]
150 ; VI-NEXT:    flat_load_ushort v0, v[0:1]
151 ; VI-NEXT:    s_mov_b32 s3, 0xf000
152 ; VI-NEXT:    s_mov_b32 s2, -1
153 ; VI-NEXT:    s_waitcnt vmcnt(0)
154 ; VI-NEXT:    v_mul_lo_u16_e32 v0, v2, v0
155 ; VI-NEXT:    v_bfe_i32 v0, v0, 0, 16
156 ; VI-NEXT:    buffer_store_dword v0, off, s[0:3], 0
157 ; VI-NEXT:    s_endpgm
159 ; GFX9-LABEL: test_umul24_i16_vgpr_sext:
160 ; GFX9:       ; %bb.0:
161 ; GFX9-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
162 ; GFX9-NEXT:    v_lshlrev_b32_e32 v0, 1, v0
163 ; GFX9-NEXT:    v_lshlrev_b32_e32 v1, 1, v1
164 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
165 ; GFX9-NEXT:    global_load_ushort v2, v0, s[6:7]
166 ; GFX9-NEXT:    global_load_ushort v3, v1, s[6:7]
167 ; GFX9-NEXT:    s_mov_b32 s7, 0xf000
168 ; GFX9-NEXT:    s_mov_b32 s6, -1
169 ; GFX9-NEXT:    s_waitcnt vmcnt(0)
170 ; GFX9-NEXT:    v_mul_lo_u16_e32 v0, v2, v3
171 ; GFX9-NEXT:    v_bfe_i32 v0, v0, 0, 16
172 ; GFX9-NEXT:    buffer_store_dword v0, off, s[4:7], 0
173 ; GFX9-NEXT:    s_endpgm
174   %tid.x = call i32 @llvm.amdgcn.workitem.id.x()
175   %tid.y = call i32 @llvm.amdgcn.workitem.id.y()
176   %ptr_a = getelementptr i16, ptr addrspace(1) %in, i32 %tid.x
177   %ptr_b = getelementptr i16, ptr addrspace(1) %in, i32 %tid.y
178   %a = load i16, ptr addrspace(1) %ptr_a
179   %b = load i16, ptr addrspace(1) %ptr_b
180   %mul = mul i16 %a, %b
181   %val = sext i16 %mul to i32
182   store i32 %val, ptr addrspace(1) %out
183   ret void
186 define amdgpu_kernel void @test_umul24_i16(ptr addrspace(1) %out, i16 %a, i16 %b) {
187 ; SI-LABEL: test_umul24_i16:
188 ; SI:       ; %bb.0: ; %entry
189 ; SI-NEXT:    s_load_dword s4, s[2:3], 0xb
190 ; SI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x9
191 ; SI-NEXT:    s_mov_b32 s3, 0xf000
192 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
193 ; SI-NEXT:    s_lshr_b32 s2, s4, 16
194 ; SI-NEXT:    s_mul_i32 s4, s4, s2
195 ; SI-NEXT:    s_and_b32 s4, s4, 0xffff
196 ; SI-NEXT:    s_mov_b32 s2, -1
197 ; SI-NEXT:    v_mov_b32_e32 v0, s4
198 ; SI-NEXT:    buffer_store_dword v0, off, s[0:3], 0
199 ; SI-NEXT:    s_endpgm
201 ; VI-LABEL: test_umul24_i16:
202 ; VI:       ; %bb.0: ; %entry
203 ; VI-NEXT:    s_load_dword s4, s[2:3], 0x2c
204 ; VI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x24
205 ; VI-NEXT:    s_mov_b32 s3, 0xf000
206 ; VI-NEXT:    s_mov_b32 s2, -1
207 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
208 ; VI-NEXT:    s_lshr_b32 s5, s4, 16
209 ; VI-NEXT:    s_mul_i32 s4, s4, s5
210 ; VI-NEXT:    s_and_b32 s4, s4, 0xffff
211 ; VI-NEXT:    v_mov_b32_e32 v0, s4
212 ; VI-NEXT:    buffer_store_dword v0, off, s[0:3], 0
213 ; VI-NEXT:    s_endpgm
215 ; GFX9-LABEL: test_umul24_i16:
216 ; GFX9:       ; %bb.0: ; %entry
217 ; GFX9-NEXT:    s_load_dword s4, s[2:3], 0x2c
218 ; GFX9-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x24
219 ; GFX9-NEXT:    s_mov_b32 s3, 0xf000
220 ; GFX9-NEXT:    s_mov_b32 s2, -1
221 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
222 ; GFX9-NEXT:    s_lshr_b32 s5, s4, 16
223 ; GFX9-NEXT:    s_mul_i32 s4, s4, s5
224 ; GFX9-NEXT:    s_and_b32 s4, s4, 0xffff
225 ; GFX9-NEXT:    v_mov_b32_e32 v0, s4
226 ; GFX9-NEXT:    buffer_store_dword v0, off, s[0:3], 0
227 ; GFX9-NEXT:    s_endpgm
228 entry:
229   %mul = mul i16 %a, %b
230   %ext = zext i16 %mul to i32
231   store i32 %ext, ptr addrspace(1) %out
232   ret void
235 define amdgpu_kernel void @test_umul24_i16_vgpr(ptr addrspace(1) %out, ptr addrspace(1) %in) {
236 ; SI-LABEL: test_umul24_i16_vgpr:
237 ; SI:       ; %bb.0:
238 ; SI-NEXT:    s_load_dwordx4 s[0:3], s[2:3], 0x9
239 ; SI-NEXT:    s_mov_b32 s7, 0xf000
240 ; SI-NEXT:    s_mov_b32 s10, 0
241 ; SI-NEXT:    v_lshlrev_b32_e32 v2, 1, v0
242 ; SI-NEXT:    v_mov_b32_e32 v3, 0
243 ; SI-NEXT:    v_lshlrev_b32_e32 v0, 1, v1
244 ; SI-NEXT:    s_mov_b32 s11, s7
245 ; SI-NEXT:    v_mov_b32_e32 v1, v3
246 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
247 ; SI-NEXT:    s_mov_b64 s[8:9], s[2:3]
248 ; SI-NEXT:    buffer_load_ushort v2, v[2:3], s[8:11], 0 addr64
249 ; SI-NEXT:    buffer_load_ushort v0, v[0:1], s[8:11], 0 addr64
250 ; SI-NEXT:    s_mov_b32 s6, -1
251 ; SI-NEXT:    s_mov_b32 s4, s0
252 ; SI-NEXT:    s_mov_b32 s5, s1
253 ; SI-NEXT:    s_waitcnt vmcnt(0)
254 ; SI-NEXT:    v_mul_u32_u24_e32 v0, v2, v0
255 ; SI-NEXT:    v_and_b32_e32 v0, 0xffff, v0
256 ; SI-NEXT:    buffer_store_dword v0, off, s[4:7], 0
257 ; SI-NEXT:    s_endpgm
259 ; VI-LABEL: test_umul24_i16_vgpr:
260 ; VI:       ; %bb.0:
261 ; VI-NEXT:    s_load_dwordx4 s[0:3], s[2:3], 0x24
262 ; VI-NEXT:    v_lshlrev_b32_e32 v0, 1, v0
263 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
264 ; VI-NEXT:    v_mov_b32_e32 v3, s3
265 ; VI-NEXT:    v_add_u32_e32 v2, vcc, s2, v0
266 ; VI-NEXT:    v_addc_u32_e32 v3, vcc, 0, v3, vcc
267 ; VI-NEXT:    v_lshlrev_b32_e32 v0, 1, v1
268 ; VI-NEXT:    v_mov_b32_e32 v1, s3
269 ; VI-NEXT:    v_add_u32_e32 v0, vcc, s2, v0
270 ; VI-NEXT:    v_addc_u32_e32 v1, vcc, 0, v1, vcc
271 ; VI-NEXT:    flat_load_ushort v2, v[2:3]
272 ; VI-NEXT:    flat_load_ushort v0, v[0:1]
273 ; VI-NEXT:    s_mov_b32 s3, 0xf000
274 ; VI-NEXT:    s_mov_b32 s2, -1
275 ; VI-NEXT:    s_waitcnt vmcnt(0)
276 ; VI-NEXT:    v_mul_lo_u16_e32 v0, v2, v0
277 ; VI-NEXT:    buffer_store_dword v0, off, s[0:3], 0
278 ; VI-NEXT:    s_endpgm
280 ; GFX9-LABEL: test_umul24_i16_vgpr:
281 ; GFX9:       ; %bb.0:
282 ; GFX9-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
283 ; GFX9-NEXT:    v_lshlrev_b32_e32 v0, 1, v0
284 ; GFX9-NEXT:    v_lshlrev_b32_e32 v1, 1, v1
285 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
286 ; GFX9-NEXT:    global_load_ushort v2, v0, s[6:7]
287 ; GFX9-NEXT:    global_load_ushort v3, v1, s[6:7]
288 ; GFX9-NEXT:    s_mov_b32 s7, 0xf000
289 ; GFX9-NEXT:    s_mov_b32 s6, -1
290 ; GFX9-NEXT:    s_waitcnt vmcnt(0)
291 ; GFX9-NEXT:    v_mul_lo_u16_e32 v0, v2, v3
292 ; GFX9-NEXT:    buffer_store_dword v0, off, s[4:7], 0
293 ; GFX9-NEXT:    s_endpgm
294   %tid.x = call i32 @llvm.amdgcn.workitem.id.x()
295   %tid.y = call i32 @llvm.amdgcn.workitem.id.y()
296   %ptr_a = getelementptr i16, ptr addrspace(1) %in, i32 %tid.x
297   %ptr_b = getelementptr i16, ptr addrspace(1) %in, i32 %tid.y
298   %a = load i16, ptr addrspace(1) %ptr_a
299   %b = load i16, ptr addrspace(1) %ptr_b
300   %mul = mul i16 %a, %b
301   %val = zext i16 %mul to i32
302   store i32 %val, ptr addrspace(1) %out
303   ret void
306 define amdgpu_kernel void @test_umul24_i8_vgpr(ptr addrspace(1) %out, ptr addrspace(1) %a, ptr addrspace(1) %b) {
307 ; SI-LABEL: test_umul24_i8_vgpr:
308 ; SI:       ; %bb.0: ; %entry
309 ; SI-NEXT:    v_mov_b32_e32 v3, v0
310 ; SI-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x9
311 ; SI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0xd
312 ; SI-NEXT:    s_mov_b32 s11, 0xf000
313 ; SI-NEXT:    s_mov_b32 s14, 0
314 ; SI-NEXT:    v_mov_b32_e32 v4, 0
315 ; SI-NEXT:    s_mov_b32 s15, s11
316 ; SI-NEXT:    v_mov_b32_e32 v2, v4
317 ; SI-NEXT:    s_mov_b64 s[2:3], s[14:15]
318 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
319 ; SI-NEXT:    s_mov_b64 s[12:13], s[6:7]
320 ; SI-NEXT:    buffer_load_ubyte v0, v[3:4], s[12:15], 0 addr64
321 ; SI-NEXT:    buffer_load_ubyte v1, v[1:2], s[0:3], 0 addr64
322 ; SI-NEXT:    s_mov_b32 s10, -1
323 ; SI-NEXT:    s_mov_b32 s8, s4
324 ; SI-NEXT:    s_mov_b32 s9, s5
325 ; SI-NEXT:    s_waitcnt vmcnt(0)
326 ; SI-NEXT:    v_mul_u32_u24_e32 v0, v0, v1
327 ; SI-NEXT:    v_bfe_i32 v0, v0, 0, 8
328 ; SI-NEXT:    buffer_store_dword v0, off, s[8:11], 0
329 ; SI-NEXT:    s_endpgm
331 ; VI-LABEL: test_umul24_i8_vgpr:
332 ; VI:       ; %bb.0: ; %entry
333 ; VI-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
334 ; VI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x34
335 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
336 ; VI-NEXT:    v_mov_b32_e32 v3, s7
337 ; VI-NEXT:    v_add_u32_e32 v2, vcc, s6, v0
338 ; VI-NEXT:    v_addc_u32_e32 v3, vcc, 0, v3, vcc
339 ; VI-NEXT:    v_mov_b32_e32 v4, s1
340 ; VI-NEXT:    v_add_u32_e32 v0, vcc, s0, v1
341 ; VI-NEXT:    v_addc_u32_e32 v1, vcc, 0, v4, vcc
342 ; VI-NEXT:    flat_load_ubyte v2, v[2:3]
343 ; VI-NEXT:    flat_load_ubyte v0, v[0:1]
344 ; VI-NEXT:    s_mov_b32 s7, 0xf000
345 ; VI-NEXT:    s_mov_b32 s6, -1
346 ; VI-NEXT:    s_waitcnt vmcnt(0)
347 ; VI-NEXT:    v_mul_lo_u16_e32 v0, v2, v0
348 ; VI-NEXT:    v_bfe_i32 v0, v0, 0, 8
349 ; VI-NEXT:    buffer_store_dword v0, off, s[4:7], 0
350 ; VI-NEXT:    s_endpgm
352 ; GFX9-LABEL: test_umul24_i8_vgpr:
353 ; GFX9:       ; %bb.0: ; %entry
354 ; GFX9-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
355 ; GFX9-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x34
356 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
357 ; GFX9-NEXT:    global_load_ubyte v2, v0, s[6:7]
358 ; GFX9-NEXT:    global_load_ubyte v3, v1, s[0:1]
359 ; GFX9-NEXT:    s_mov_b32 s7, 0xf000
360 ; GFX9-NEXT:    s_mov_b32 s6, -1
361 ; GFX9-NEXT:    s_waitcnt vmcnt(0)
362 ; GFX9-NEXT:    v_mul_lo_u16_e32 v0, v2, v3
363 ; GFX9-NEXT:    v_bfe_i32 v0, v0, 0, 8
364 ; GFX9-NEXT:    buffer_store_dword v0, off, s[4:7], 0
365 ; GFX9-NEXT:    s_endpgm
366 entry:
367   %tid.x = call i32 @llvm.amdgcn.workitem.id.x()
368   %tid.y = call i32 @llvm.amdgcn.workitem.id.y()
369   %a.ptr = getelementptr i8, ptr addrspace(1) %a, i32 %tid.x
370   %b.ptr = getelementptr i8, ptr addrspace(1) %b, i32 %tid.y
371   %a.l = load i8, ptr addrspace(1) %a.ptr
372   %b.l = load i8, ptr addrspace(1) %b.ptr
373   %mul = mul i8 %a.l, %b.l
374   %ext = sext i8 %mul to i32
375   store i32 %ext, ptr addrspace(1) %out
376   ret void
379 define amdgpu_kernel void @test_umulhi24_i32_i64(ptr addrspace(1) %out, i32 %a, i32 %b) {
380 ; SI-LABEL: test_umulhi24_i32_i64:
381 ; SI:       ; %bb.0: ; %entry
382 ; SI-NEXT:    s_load_dwordx4 s[0:3], s[2:3], 0x9
383 ; SI-NEXT:    s_mov_b32 s7, 0xf000
384 ; SI-NEXT:    s_mov_b32 s6, -1
385 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
386 ; SI-NEXT:    s_mov_b32 s4, s0
387 ; SI-NEXT:    s_mov_b32 s5, s1
388 ; SI-NEXT:    v_mov_b32_e32 v0, s3
389 ; SI-NEXT:    v_mul_hi_u32_u24_e32 v0, s2, v0
390 ; SI-NEXT:    buffer_store_dword v0, off, s[4:7], 0
391 ; SI-NEXT:    s_endpgm
393 ; VI-LABEL: test_umulhi24_i32_i64:
394 ; VI:       ; %bb.0: ; %entry
395 ; VI-NEXT:    s_load_dwordx4 s[0:3], s[2:3], 0x24
396 ; VI-NEXT:    s_mov_b32 s7, 0xf000
397 ; VI-NEXT:    s_mov_b32 s6, -1
398 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
399 ; VI-NEXT:    v_mov_b32_e32 v0, s3
400 ; VI-NEXT:    s_mov_b32 s4, s0
401 ; VI-NEXT:    s_mov_b32 s5, s1
402 ; VI-NEXT:    v_mul_hi_u32_u24_e32 v0, s2, v0
403 ; VI-NEXT:    buffer_store_dword v0, off, s[4:7], 0
404 ; VI-NEXT:    s_endpgm
406 ; GFX9-LABEL: test_umulhi24_i32_i64:
407 ; GFX9:       ; %bb.0: ; %entry
408 ; GFX9-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
409 ; GFX9-NEXT:    s_mov_b32 s3, 0xf000
410 ; GFX9-NEXT:    s_mov_b32 s2, -1
411 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
412 ; GFX9-NEXT:    s_mov_b32 s0, s4
413 ; GFX9-NEXT:    s_mov_b32 s1, s5
414 ; GFX9-NEXT:    s_and_b32 s4, s6, 0xffffff
415 ; GFX9-NEXT:    s_and_b32 s5, s7, 0xffffff
416 ; GFX9-NEXT:    s_mul_hi_u32 s4, s4, s5
417 ; GFX9-NEXT:    v_mov_b32_e32 v0, s4
418 ; GFX9-NEXT:    buffer_store_dword v0, off, s[0:3], 0
419 ; GFX9-NEXT:    s_endpgm
420 entry:
421   %a.24 = and i32 %a, 16777215
422   %b.24 = and i32 %b, 16777215
423   %a.24.i64 = zext i32 %a.24 to i64
424   %b.24.i64 = zext i32 %b.24 to i64
425   %mul48 = mul i64 %a.24.i64, %b.24.i64
426   %mul48.hi = lshr i64 %mul48, 32
427   %mul24hi = trunc i64 %mul48.hi to i32
428   store i32 %mul24hi, ptr addrspace(1) %out
429   ret void
432 define amdgpu_kernel void @test_umulhi24(ptr addrspace(1) %out, i64 %a, i64 %b) {
433 ; SI-LABEL: test_umulhi24:
434 ; SI:       ; %bb.0: ; %entry
435 ; SI-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x9
436 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
437 ; SI-NEXT:    s_load_dword s7, s[2:3], 0xd
438 ; SI-NEXT:    s_mov_b32 s3, 0xf000
439 ; SI-NEXT:    s_mov_b32 s2, -1
440 ; SI-NEXT:    s_mov_b32 s0, s4
441 ; SI-NEXT:    s_mov_b32 s1, s5
442 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
443 ; SI-NEXT:    v_mov_b32_e32 v0, s7
444 ; SI-NEXT:    v_mul_hi_u32_u24_e32 v0, s6, v0
445 ; SI-NEXT:    buffer_store_dword v0, off, s[0:3], 0
446 ; SI-NEXT:    s_endpgm
448 ; VI-LABEL: test_umulhi24:
449 ; VI:       ; %bb.0: ; %entry
450 ; VI-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
451 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
452 ; VI-NEXT:    s_load_dword s7, s[2:3], 0x34
453 ; VI-NEXT:    s_mov_b32 s3, 0xf000
454 ; VI-NEXT:    s_mov_b32 s2, -1
455 ; VI-NEXT:    s_mov_b32 s0, s4
456 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
457 ; VI-NEXT:    v_mov_b32_e32 v0, s7
458 ; VI-NEXT:    s_mov_b32 s1, s5
459 ; VI-NEXT:    v_mul_hi_u32_u24_e32 v0, s6, v0
460 ; VI-NEXT:    buffer_store_dword v0, off, s[0:3], 0
461 ; VI-NEXT:    s_endpgm
463 ; GFX9-LABEL: test_umulhi24:
464 ; GFX9:       ; %bb.0: ; %entry
465 ; GFX9-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
466 ; GFX9-NEXT:    s_load_dword s0, s[2:3], 0x34
467 ; GFX9-NEXT:    s_mov_b32 s11, 0xf000
468 ; GFX9-NEXT:    s_mov_b32 s10, -1
469 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
470 ; GFX9-NEXT:    s_and_b32 s1, s6, 0xffffff
471 ; GFX9-NEXT:    s_and_b32 s0, s0, 0xffffff
472 ; GFX9-NEXT:    s_mul_hi_u32 s0, s1, s0
473 ; GFX9-NEXT:    s_mov_b32 s8, s4
474 ; GFX9-NEXT:    s_mov_b32 s9, s5
475 ; GFX9-NEXT:    v_mov_b32_e32 v0, s0
476 ; GFX9-NEXT:    buffer_store_dword v0, off, s[8:11], 0
477 ; GFX9-NEXT:    s_endpgm
478 entry:
479   %a.24 = and i64 %a, 16777215
480   %b.24 = and i64 %b, 16777215
481   %mul48 = mul i64 %a.24, %b.24
482   %mul48.hi = lshr i64 %mul48, 32
483   %mul24.hi = trunc i64 %mul48.hi to i32
484   store i32 %mul24.hi, ptr addrspace(1) %out
485   ret void
488 ; Multiply with 24-bit inputs and 64-bit output.
489 define amdgpu_kernel void @test_umul24_i64(ptr addrspace(1) %out, i64 %a, i64 %b) {
490 ; SI-LABEL: test_umul24_i64:
491 ; SI:       ; %bb.0: ; %entry
492 ; SI-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x9
493 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
494 ; SI-NEXT:    s_load_dword s7, s[2:3], 0xd
495 ; SI-NEXT:    s_mov_b32 s3, 0xf000
496 ; SI-NEXT:    s_mov_b32 s2, -1
497 ; SI-NEXT:    s_mov_b32 s0, s4
498 ; SI-NEXT:    s_mov_b32 s1, s5
499 ; SI-NEXT:    s_and_b32 s4, s6, 0xffffff
500 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
501 ; SI-NEXT:    s_and_b32 s5, s7, 0xffffff
502 ; SI-NEXT:    v_mov_b32_e32 v0, s7
503 ; SI-NEXT:    s_mul_i32 s4, s4, s5
504 ; SI-NEXT:    v_mul_hi_u32_u24_e32 v1, s6, v0
505 ; SI-NEXT:    v_mov_b32_e32 v0, s4
506 ; SI-NEXT:    buffer_store_dwordx2 v[0:1], off, s[0:3], 0
507 ; SI-NEXT:    s_endpgm
509 ; VI-LABEL: test_umul24_i64:
510 ; VI:       ; %bb.0: ; %entry
511 ; VI-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
512 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
513 ; VI-NEXT:    s_load_dword s7, s[2:3], 0x34
514 ; VI-NEXT:    s_mov_b32 s3, 0xf000
515 ; VI-NEXT:    s_mov_b32 s2, -1
516 ; VI-NEXT:    s_mov_b32 s0, s4
517 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
518 ; VI-NEXT:    v_mov_b32_e32 v0, s7
519 ; VI-NEXT:    s_mov_b32 s1, s5
520 ; VI-NEXT:    v_mul_hi_u32_u24_e32 v1, s6, v0
521 ; VI-NEXT:    v_mul_u32_u24_e32 v0, s6, v0
522 ; VI-NEXT:    buffer_store_dwordx2 v[0:1], off, s[0:3], 0
523 ; VI-NEXT:    s_endpgm
525 ; GFX9-LABEL: test_umul24_i64:
526 ; GFX9:       ; %bb.0: ; %entry
527 ; GFX9-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
528 ; GFX9-NEXT:    s_load_dword s0, s[2:3], 0x34
529 ; GFX9-NEXT:    s_mov_b32 s11, 0xf000
530 ; GFX9-NEXT:    s_mov_b32 s10, -1
531 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
532 ; GFX9-NEXT:    s_and_b32 s1, s6, 0xffffff
533 ; GFX9-NEXT:    s_and_b32 s0, s0, 0xffffff
534 ; GFX9-NEXT:    s_mul_hi_u32 s2, s1, s0
535 ; GFX9-NEXT:    s_mul_i32 s1, s1, s0
536 ; GFX9-NEXT:    s_mov_b32 s8, s4
537 ; GFX9-NEXT:    s_mov_b32 s9, s5
538 ; GFX9-NEXT:    v_mov_b32_e32 v0, s1
539 ; GFX9-NEXT:    v_mov_b32_e32 v1, s2
540 ; GFX9-NEXT:    buffer_store_dwordx2 v[0:1], off, s[8:11], 0
541 ; GFX9-NEXT:    s_endpgm
542 entry:
543   %tmp0 = shl i64 %a, 40
544   %a_24 = lshr i64 %tmp0, 40
545   %tmp1 = shl i64 %b, 40
546   %b_24 = lshr i64 %tmp1, 40
547   %tmp2 = mul i64 %a_24, %b_24
548   store i64 %tmp2, ptr addrspace(1) %out
549   ret void
552 define i64 @test_umul48_i64(i64 %lhs, i64 %rhs) {
553 ; GCN-LABEL: test_umul48_i64:
554 ; GCN:       ; %bb.0:
555 ; GCN-NEXT:    s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
556 ; GCN-NEXT:    v_mul_hi_u32_u24_e32 v1, v0, v2
557 ; GCN-NEXT:    v_mul_u32_u24_e32 v0, v0, v2
558 ; GCN-NEXT:    s_setpc_b64 s[30:31]
559   %lhs24 = and i64 %lhs, 16777215
560   %rhs24 = and i64 %rhs, 16777215
561   %mul = mul i64 %lhs24, %rhs24
562   ret i64 %mul
565 define <2 x i64> @test_umul48_v2i64(<2 x i64> %lhs, <2 x i64> %rhs) {
566 ; GCN-LABEL: test_umul48_v2i64:
567 ; GCN:       ; %bb.0:
568 ; GCN-NEXT:    s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
569 ; GCN-NEXT:    v_mul_hi_u32_u24_e32 v1, v0, v4
570 ; GCN-NEXT:    v_mul_u32_u24_e32 v0, v0, v4
571 ; GCN-NEXT:    v_mul_hi_u32_u24_e32 v3, v2, v6
572 ; GCN-NEXT:    v_mul_u32_u24_e32 v2, v2, v6
573 ; GCN-NEXT:    s_setpc_b64 s[30:31]
574   %lhs24 = and <2 x i64> %lhs, <i64 16777215, i64 16777215>
575   %rhs24 = and <2 x i64> %rhs, <i64 16777215, i64 16777215>
576   %mul = mul <2 x i64> %lhs24, %rhs24
577   ret <2 x i64> %mul
580 define amdgpu_kernel void @test_umul24_i64_square(ptr addrspace(1) %out, [8 x i32], i64 %a) {
581 ; SI-LABEL: test_umul24_i64_square:
582 ; SI:       ; %bb.0: ; %entry
583 ; SI-NEXT:    s_load_dword s4, s[2:3], 0x13
584 ; SI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x9
585 ; SI-NEXT:    s_mov_b32 s3, 0xf000
586 ; SI-NEXT:    s_mov_b32 s2, -1
587 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
588 ; SI-NEXT:    s_and_b32 s5, s4, 0xffffff
589 ; SI-NEXT:    s_mul_i32 s5, s5, s5
590 ; SI-NEXT:    v_mul_hi_u32_u24_e64 v1, s4, s4
591 ; SI-NEXT:    v_mov_b32_e32 v0, s5
592 ; SI-NEXT:    buffer_store_dwordx2 v[0:1], off, s[0:3], 0
593 ; SI-NEXT:    s_endpgm
595 ; VI-LABEL: test_umul24_i64_square:
596 ; VI:       ; %bb.0: ; %entry
597 ; VI-NEXT:    s_load_dword s4, s[2:3], 0x4c
598 ; VI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x24
599 ; VI-NEXT:    s_mov_b32 s3, 0xf000
600 ; VI-NEXT:    s_mov_b32 s2, -1
601 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
602 ; VI-NEXT:    v_mul_hi_u32_u24_e64 v1, s4, s4
603 ; VI-NEXT:    v_mul_u32_u24_e64 v0, s4, s4
604 ; VI-NEXT:    buffer_store_dwordx2 v[0:1], off, s[0:3], 0
605 ; VI-NEXT:    s_endpgm
607 ; GFX9-LABEL: test_umul24_i64_square:
608 ; GFX9:       ; %bb.0: ; %entry
609 ; GFX9-NEXT:    s_load_dword s4, s[2:3], 0x4c
610 ; GFX9-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x24
611 ; GFX9-NEXT:    s_mov_b32 s3, 0xf000
612 ; GFX9-NEXT:    s_mov_b32 s2, -1
613 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
614 ; GFX9-NEXT:    s_and_b32 s4, s4, 0xffffff
615 ; GFX9-NEXT:    s_mul_hi_u32 s5, s4, s4
616 ; GFX9-NEXT:    s_mul_i32 s4, s4, s4
617 ; GFX9-NEXT:    v_mov_b32_e32 v0, s4
618 ; GFX9-NEXT:    v_mov_b32_e32 v1, s5
619 ; GFX9-NEXT:    buffer_store_dwordx2 v[0:1], off, s[0:3], 0
620 ; GFX9-NEXT:    s_endpgm
621 entry:
622   %tmp0 = shl i64 %a, 40
623   %a.24 = lshr i64 %tmp0, 40
624   %tmp2 = mul i64 %a.24, %a.24
625   store i64 %tmp2, ptr addrspace(1) %out
626   ret void
629 define amdgpu_kernel void @test_umulhi16_i32(ptr addrspace(1) %out, i32 %a, i32 %b) {
630 ; SI-LABEL: test_umulhi16_i32:
631 ; SI:       ; %bb.0: ; %entry
632 ; SI-NEXT:    s_load_dwordx4 s[0:3], s[2:3], 0x9
633 ; SI-NEXT:    s_mov_b32 s7, 0xf000
634 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
635 ; SI-NEXT:    s_and_b32 s2, s2, 0xffff
636 ; SI-NEXT:    s_and_b32 s3, s3, 0xffff
637 ; SI-NEXT:    s_mul_i32 s2, s2, s3
638 ; SI-NEXT:    s_lshr_b32 s2, s2, 16
639 ; SI-NEXT:    s_mov_b32 s6, -1
640 ; SI-NEXT:    s_mov_b32 s4, s0
641 ; SI-NEXT:    s_mov_b32 s5, s1
642 ; SI-NEXT:    v_mov_b32_e32 v0, s2
643 ; SI-NEXT:    buffer_store_short v0, off, s[4:7], 0
644 ; SI-NEXT:    s_endpgm
646 ; VI-LABEL: test_umulhi16_i32:
647 ; VI:       ; %bb.0: ; %entry
648 ; VI-NEXT:    s_load_dwordx4 s[0:3], s[2:3], 0x24
649 ; VI-NEXT:    s_mov_b32 s7, 0xf000
650 ; VI-NEXT:    s_mov_b32 s6, -1
651 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
652 ; VI-NEXT:    s_mov_b32 s4, s0
653 ; VI-NEXT:    s_mov_b32 s5, s1
654 ; VI-NEXT:    s_and_b32 s0, s2, 0xffff
655 ; VI-NEXT:    s_and_b32 s1, s3, 0xffff
656 ; VI-NEXT:    s_mul_i32 s0, s0, s1
657 ; VI-NEXT:    s_lshr_b32 s0, s0, 16
658 ; VI-NEXT:    v_mov_b32_e32 v0, s0
659 ; VI-NEXT:    buffer_store_short v0, off, s[4:7], 0
660 ; VI-NEXT:    s_endpgm
662 ; GFX9-LABEL: test_umulhi16_i32:
663 ; GFX9:       ; %bb.0: ; %entry
664 ; GFX9-NEXT:    s_load_dwordx4 s[4:7], s[2:3], 0x24
665 ; GFX9-NEXT:    v_mov_b32_e32 v0, 0
666 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
667 ; GFX9-NEXT:    s_and_b32 s0, s6, 0xffff
668 ; GFX9-NEXT:    s_and_b32 s1, s7, 0xffff
669 ; GFX9-NEXT:    s_mul_i32 s0, s0, s1
670 ; GFX9-NEXT:    v_mov_b32_e32 v1, s0
671 ; GFX9-NEXT:    global_store_short_d16_hi v0, v1, s[4:5]
672 ; GFX9-NEXT:    s_endpgm
673 entry:
674   %a.16 = and i32 %a, 65535
675   %b.16 = and i32 %b, 65535
676   %mul = mul i32 %a.16, %b.16
677   %hi = lshr i32 %mul, 16
678   %mulhi = trunc i32 %hi to i16
679   store i16 %mulhi, ptr addrspace(1) %out
680   ret void
683 define amdgpu_kernel void @test_umul24_i33(ptr addrspace(1) %out, i33 %a, i33 %b) {
684 ; SI-LABEL: test_umul24_i33:
685 ; SI:       ; %bb.0: ; %entry
686 ; SI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x9
687 ; SI-NEXT:    s_load_dword s4, s[2:3], 0xb
688 ; SI-NEXT:    s_load_dword s5, s[2:3], 0xd
689 ; SI-NEXT:    s_mov_b32 s3, 0xf000
690 ; SI-NEXT:    s_mov_b32 s2, -1
691 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
692 ; SI-NEXT:    s_and_b32 s6, s4, 0xffffff
693 ; SI-NEXT:    s_and_b32 s7, s5, 0xffffff
694 ; SI-NEXT:    v_mov_b32_e32 v0, s5
695 ; SI-NEXT:    v_mul_hi_u32_u24_e32 v0, s4, v0
696 ; SI-NEXT:    s_mul_i32 s6, s6, s7
697 ; SI-NEXT:    v_and_b32_e32 v1, 1, v0
698 ; SI-NEXT:    v_mov_b32_e32 v0, s6
699 ; SI-NEXT:    buffer_store_dwordx2 v[0:1], off, s[0:3], 0
700 ; SI-NEXT:    s_endpgm
702 ; VI-LABEL: test_umul24_i33:
703 ; VI:       ; %bb.0: ; %entry
704 ; VI-NEXT:    s_load_dword s4, s[2:3], 0x34
705 ; VI-NEXT:    s_load_dword s5, s[2:3], 0x2c
706 ; VI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x24
707 ; VI-NEXT:    s_mov_b32 s3, 0xf000
708 ; VI-NEXT:    s_mov_b32 s2, -1
709 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
710 ; VI-NEXT:    v_mov_b32_e32 v1, s4
711 ; VI-NEXT:    v_mul_u32_u24_e32 v0, s5, v1
712 ; VI-NEXT:    v_mul_hi_u32_u24_e32 v1, s5, v1
713 ; VI-NEXT:    v_and_b32_e32 v1, 1, v1
714 ; VI-NEXT:    buffer_store_dwordx2 v[0:1], off, s[0:3], 0
715 ; VI-NEXT:    s_endpgm
717 ; GFX9-LABEL: test_umul24_i33:
718 ; GFX9:       ; %bb.0: ; %entry
719 ; GFX9-NEXT:    s_load_dword s4, s[2:3], 0x2c
720 ; GFX9-NEXT:    s_load_dword s5, s[2:3], 0x34
721 ; GFX9-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x24
722 ; GFX9-NEXT:    s_mov_b32 s3, 0xf000
723 ; GFX9-NEXT:    s_mov_b32 s2, -1
724 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
725 ; GFX9-NEXT:    s_and_b32 s4, s4, 0xffffff
726 ; GFX9-NEXT:    s_and_b32 s5, s5, 0xffffff
727 ; GFX9-NEXT:    s_mul_i32 s6, s4, s5
728 ; GFX9-NEXT:    s_mul_hi_u32 s4, s4, s5
729 ; GFX9-NEXT:    s_and_b32 s4, s4, 1
730 ; GFX9-NEXT:    v_mov_b32_e32 v0, s6
731 ; GFX9-NEXT:    v_mov_b32_e32 v1, s4
732 ; GFX9-NEXT:    buffer_store_dwordx2 v[0:1], off, s[0:3], 0
733 ; GFX9-NEXT:    s_endpgm
734 entry:
735   %tmp0 = shl i33 %a, 9
736   %a_24 = lshr i33 %tmp0, 9
737   %tmp1 = shl i33 %b, 9
738   %b_24 = lshr i33 %tmp1, 9
739   %tmp2 = mul i33 %a_24, %b_24
740   %ext = zext i33 %tmp2 to i64
741   store i64 %ext, ptr addrspace(1) %out
742   ret void
745 define amdgpu_kernel void @test_umulhi24_i33(ptr addrspace(1) %out, i33 %a, i33 %b) {
746 ; SI-LABEL: test_umulhi24_i33:
747 ; SI:       ; %bb.0: ; %entry
748 ; SI-NEXT:    s_load_dword s4, s[2:3], 0xd
749 ; SI-NEXT:    s_load_dword s5, s[2:3], 0xb
750 ; SI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x9
751 ; SI-NEXT:    s_mov_b32 s3, 0xf000
752 ; SI-NEXT:    s_mov_b32 s2, -1
753 ; SI-NEXT:    s_waitcnt lgkmcnt(0)
754 ; SI-NEXT:    v_mov_b32_e32 v0, s4
755 ; SI-NEXT:    v_mul_hi_u32_u24_e32 v0, s5, v0
756 ; SI-NEXT:    v_and_b32_e32 v0, 1, v0
757 ; SI-NEXT:    buffer_store_dword v0, off, s[0:3], 0
758 ; SI-NEXT:    s_endpgm
760 ; VI-LABEL: test_umulhi24_i33:
761 ; VI:       ; %bb.0: ; %entry
762 ; VI-NEXT:    s_load_dword s4, s[2:3], 0x34
763 ; VI-NEXT:    s_load_dword s5, s[2:3], 0x2c
764 ; VI-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x24
765 ; VI-NEXT:    s_mov_b32 s3, 0xf000
766 ; VI-NEXT:    s_mov_b32 s2, -1
767 ; VI-NEXT:    s_waitcnt lgkmcnt(0)
768 ; VI-NEXT:    v_mov_b32_e32 v0, s4
769 ; VI-NEXT:    v_mul_hi_u32_u24_e32 v0, s5, v0
770 ; VI-NEXT:    v_and_b32_e32 v0, 1, v0
771 ; VI-NEXT:    buffer_store_dword v0, off, s[0:3], 0
772 ; VI-NEXT:    s_endpgm
774 ; GFX9-LABEL: test_umulhi24_i33:
775 ; GFX9:       ; %bb.0: ; %entry
776 ; GFX9-NEXT:    s_load_dword s4, s[2:3], 0x2c
777 ; GFX9-NEXT:    s_load_dword s5, s[2:3], 0x34
778 ; GFX9-NEXT:    s_load_dwordx2 s[0:1], s[2:3], 0x24
779 ; GFX9-NEXT:    s_mov_b32 s3, 0xf000
780 ; GFX9-NEXT:    s_mov_b32 s2, -1
781 ; GFX9-NEXT:    s_waitcnt lgkmcnt(0)
782 ; GFX9-NEXT:    s_and_b32 s4, s4, 0xffffff
783 ; GFX9-NEXT:    s_and_b32 s5, s5, 0xffffff
784 ; GFX9-NEXT:    s_mul_hi_u32 s4, s4, s5
785 ; GFX9-NEXT:    s_and_b32 s4, s4, 1
786 ; GFX9-NEXT:    v_mov_b32_e32 v0, s4
787 ; GFX9-NEXT:    buffer_store_dword v0, off, s[0:3], 0
788 ; GFX9-NEXT:    s_endpgm
789 entry:
790   %tmp0 = shl i33 %a, 9
791   %a_24 = lshr i33 %tmp0, 9
792   %tmp1 = shl i33 %b, 9
793   %b_24 = lshr i33 %tmp1, 9
794   %tmp2 = mul i33 %a_24, %b_24
795   %hi = lshr i33 %tmp2, 32
796   %trunc = trunc i33 %hi to i32
797   store i32 %trunc, ptr addrspace(1) %out
798   ret void
802 ; Make sure the created any_extend is ignored to use the real bits
803 ; being multiplied.
804 define i17 @test_umul24_anyextend_i24_src0_src1(i24 %a, i24 %b) {
805 ; GCN-LABEL: test_umul24_anyextend_i24_src0_src1:
806 ; GCN:       ; %bb.0: ; %entry
807 ; GCN-NEXT:    s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
808 ; GCN-NEXT:    v_mul_u32_u24_e32 v0, 0xea, v0
809 ; GCN-NEXT:    v_mul_u32_u24_e32 v1, 0x39b, v1
810 ; GCN-NEXT:    v_mul_u32_u24_e32 v0, v0, v1
811 ; GCN-NEXT:    v_and_b32_e32 v0, 0x1fffe, v0
812 ; GCN-NEXT:    v_mul_u32_u24_e32 v0, 0x63, v0
813 ; GCN-NEXT:    s_setpc_b64 s[30:31]
814 entry:
815   %aa = mul i24 %a, 234
816   %bb = mul i24 %b, 923
817   %a_32 = zext i24 %aa to i32
818   %b_32 = zext i24 %bb to i32
819   %mul = mul i32 %a_32, %b_32
820   %trunc = trunc i32 %mul to i17
821   %arst = mul i17 %trunc, 99
822   ret i17 %arst
825 define i17 @test_umul24_anyextend_i23_src0_src1(i23 %a, i23 %b) {
826 ; GCN-LABEL: test_umul24_anyextend_i23_src0_src1:
827 ; GCN:       ; %bb.0: ; %entry
828 ; GCN-NEXT:    s_waitcnt vmcnt(0) expcnt(0) lgkmcnt(0)
829 ; GCN-NEXT:    v_and_b32_e32 v0, 0x7fffff, v0
830 ; GCN-NEXT:    v_and_b32_e32 v1, 0x7fffff, v1
831 ; GCN-NEXT:    v_mul_u32_u24_e32 v0, 0xea, v0
832 ; GCN-NEXT:    v_mul_u32_u24_e32 v1, 0x39b, v1
833 ; GCN-NEXT:    v_and_b32_e32 v0, 0x7ffffe, v0
834 ; GCN-NEXT:    v_and_b32_e32 v1, 0x7fffff, v1
835 ; GCN-NEXT:    v_mul_u32_u24_e32 v0, v0, v1
836 ; GCN-NEXT:    v_and_b32_e32 v0, 0x1fffe, v0
837 ; GCN-NEXT:    v_mul_u32_u24_e32 v0, 0x63, v0
838 ; GCN-NEXT:    s_setpc_b64 s[30:31]
839 entry:
840   %aa = mul i23 %a, 234
841   %bb = mul i23 %b, 923
842   %a_32 = zext i23 %aa to i32
843   %b_32 = zext i23 %bb to i32
844   %mul = mul i32 %a_32, %b_32
845   %trunc = trunc i32 %mul to i17
846   %arst = mul i17 %trunc, 99
847   ret i17 %arst