1 ; RUN: opt -S -codegenprepare -mtriple=amdgcn-unknown-unknown -mcpu=tahiti < %s | FileCheck -check-prefix=OPT -check-prefix=OPT-SI -check-prefix=OPT-SICIVI %s
2 ; RUN: opt -S -codegenprepare -mtriple=amdgcn-unknown-unknown -mcpu=bonaire < %s | FileCheck -check-prefix=OPT -check-prefix=OPT-CI -check-prefix=OPT-SICIVI %s
3 ; RUN: opt -S -codegenprepare -mtriple=amdgcn-unknown-unknown -mcpu=tonga -mattr=-flat-for-global < %s | FileCheck -check-prefix=OPT -check-prefix=OPT-VI -check-prefix=OPT-SICIVI %s
4 ; RUN: opt -S -codegenprepare -mtriple=amdgcn-unknown-unknown -mcpu=gfx900 < %s | FileCheck -check-prefix=OPT -check-prefix=OPT-GFX9 %s
5 ; RUN: llc -march=amdgcn -mcpu=tahiti -mattr=-promote-alloca -amdgpu-scalarize-global-loads=false -amdgpu-sroa=0 < %s | FileCheck -check-prefix=GCN -check-prefix=SI -check-prefix=SICIVI %s
6 ; RUN: llc -march=amdgcn -mcpu=bonaire -mattr=-promote-alloca -amdgpu-scalarize-global-loads=false -amdgpu-sroa=0 < %s | FileCheck -check-prefix=GCN -check-prefix=CI -check-prefix=SICIVI %s
7 ; RUN: llc -march=amdgcn -mcpu=tonga -mattr=-flat-for-global -amdgpu-scalarize-global-loads=false -mattr=-promote-alloca -amdgpu-sroa=0 < %s | FileCheck -check-prefix=GCN -check-prefix=VI -check-prefix=SICIVI %s
8 ; RUN: llc -march=amdgcn -mcpu=gfx900 -mattr=-promote-alloca -amdgpu-scalarize-global-loads=false -amdgpu-sroa=0 < %s | FileCheck -check-prefix=GCN -check-prefix=GFX9 %s
10 target datalayout = "e-p:64:64-p1:64:64-p2:32:32-p3:32:32-p4:64:64-p5:32:32-p6:32:32-i64:64-v16:16-v24:32-v32:32-v48:64-v96:128-v192:256-v256:256-v512:512-v1024:1024-v2048:2048-n32:64-S32-A5"
12 ; OPT-LABEL: @test_sink_global_small_offset_i32(
13 ; OPT-CI-NOT: getelementptr i32, i32 addrspace(1)* %in
14 ; OPT-VI: getelementptr i32, i32 addrspace(1)* %in
16 ; OPT-CI: getelementptr i8,
18 ; GCN-LABEL: {{^}}test_sink_global_small_offset_i32:
19 define amdgpu_kernel void @test_sink_global_small_offset_i32(i32 addrspace(1)* %out, i32 addrspace(1)* %in) {
21 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 999999
22 %in.gep = getelementptr i32, i32 addrspace(1)* %in, i64 7
23 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
24 %tmp0 = icmp eq i32 %tid, 0
25 br i1 %tmp0, label %endif, label %if
28 %tmp1 = load i32, i32 addrspace(1)* %in.gep
32 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
33 store i32 %x, i32 addrspace(1)* %out.gep
40 ; OPT-LABEL: @test_sink_global_small_max_i32_ds_offset(
41 ; OPT: %in.gep = getelementptr i8, i8 addrspace(1)* %in, i64 65535
44 ; GCN-LABEL: {{^}}test_sink_global_small_max_i32_ds_offset:
45 ; GCN: s_and_saveexec_b64
46 ; SICIVI: buffer_load_sbyte {{v[0-9]+}}, off, {{s\[[0-9]+:[0-9]+\]}}, s{{[0-9]+$}}
47 ; GFX9: global_load_sbyte {{v[0-9]+}}, {{v\[[0-9]+:[0-9]+\]}}, off{{$}}
50 define amdgpu_kernel void @test_sink_global_small_max_i32_ds_offset(i32 addrspace(1)* %out, i8 addrspace(1)* %in) {
52 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 99999
53 %in.gep = getelementptr i8, i8 addrspace(1)* %in, i64 65535
54 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
55 %tmp0 = icmp eq i32 %tid, 0
56 br i1 %tmp0, label %endif, label %if
59 %tmp1 = load i8, i8 addrspace(1)* %in.gep
60 %tmp2 = sext i8 %tmp1 to i32
64 %x = phi i32 [ %tmp2, %if ], [ 0, %entry ]
65 store i32 %x, i32 addrspace(1)* %out.gep
72 ; GCN-LABEL: {{^}}test_sink_global_small_max_mubuf_offset:
73 ; GCN: s_and_saveexec_b64
74 ; SICIVI: buffer_load_sbyte {{v[0-9]+}}, off, {{s\[[0-9]+:[0-9]+\]}}, 0 offset:4095{{$}}
75 ; GFX9: global_load_sbyte {{v[0-9]+}}, {{v\[[0-9]+:[0-9]+\]}}, off offset:4095{{$}}
78 define amdgpu_kernel void @test_sink_global_small_max_mubuf_offset(i32 addrspace(1)* %out, i8 addrspace(1)* %in) {
80 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i32 1024
81 %in.gep = getelementptr i8, i8 addrspace(1)* %in, i64 4095
82 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
83 %tmp0 = icmp eq i32 %tid, 0
84 br i1 %tmp0, label %endif, label %if
87 %tmp1 = load i8, i8 addrspace(1)* %in.gep
88 %tmp2 = sext i8 %tmp1 to i32
92 %x = phi i32 [ %tmp2, %if ], [ 0, %entry ]
93 store i32 %x, i32 addrspace(1)* %out.gep
100 ; GCN-LABEL: {{^}}test_sink_global_small_max_plus_1_mubuf_offset:
101 ; GCN: s_and_saveexec_b64
102 ; SICIVI: buffer_load_sbyte {{v[0-9]+}}, off, {{s\[[0-9]+:[0-9]+\]}}, s{{[0-9]+$}}
103 ; GFX9: global_load_sbyte {{v[0-9]+}}, {{v\[[0-9]+:[0-9]+\]}}, off{{$}}
106 define amdgpu_kernel void @test_sink_global_small_max_plus_1_mubuf_offset(i32 addrspace(1)* %out, i8 addrspace(1)* %in) {
108 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 99999
109 %in.gep = getelementptr i8, i8 addrspace(1)* %in, i64 4096
110 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
111 %tmp0 = icmp eq i32 %tid, 0
112 br i1 %tmp0, label %endif, label %if
115 %tmp1 = load i8, i8 addrspace(1)* %in.gep
116 %tmp2 = sext i8 %tmp1 to i32
120 %x = phi i32 [ %tmp2, %if ], [ 0, %entry ]
121 store i32 %x, i32 addrspace(1)* %out.gep
128 ; OPT-LABEL: @test_sink_scratch_small_offset_i32(
129 ; OPT-NOT: getelementptr [512 x i32]
131 ; OPT: getelementptr i8,
133 ; GCN-LABEL: {{^}}test_sink_scratch_small_offset_i32:
134 ; GCN: s_and_saveexec_b64
135 ; GCN: buffer_store_dword {{v[0-9]+}}, off, {{s\[[0-9]+:[0-9]+\]}}, {{s[0-9]+}} offset:4092{{$}}
136 ; GCN: buffer_load_dword {{v[0-9]+}}, off, {{s\[[0-9]+:[0-9]+\]}}, {{s[0-9]+}} offset:4092{{$}}
138 define amdgpu_kernel void @test_sink_scratch_small_offset_i32(i32 addrspace(1)* %out, i32 addrspace(1)* %in, i32 %arg) {
140 %alloca = alloca [512 x i32], align 4, addrspace(5)
141 %out.gep.0 = getelementptr i32, i32 addrspace(1)* %out, i64 999998
142 %out.gep.1 = getelementptr i32, i32 addrspace(1)* %out, i64 999999
143 %add.arg = add i32 %arg, 8
144 %alloca.gep = getelementptr [512 x i32], [512 x i32] addrspace(5)* %alloca, i32 0, i32 1022
145 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
146 %tmp0 = icmp eq i32 %tid, 0
147 br i1 %tmp0, label %endif, label %if
150 store volatile i32 123, i32 addrspace(5)* %alloca.gep
151 %tmp1 = load volatile i32, i32 addrspace(5)* %alloca.gep
155 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
156 store i32 %x, i32 addrspace(1)* %out.gep.0
157 %load = load volatile i32, i32 addrspace(5)* %alloca.gep
158 store i32 %load, i32 addrspace(1)* %out.gep.1
165 ; This ends up not fitting due to the reserved 4 bytes at offset 0
166 ; OPT-LABEL: @test_sink_scratch_small_offset_i32_reserved(
167 ; OPT-NOT: getelementptr [512 x i32]
169 ; OPT: getelementptr i8,
171 ; GCN-LABEL: {{^}}test_sink_scratch_small_offset_i32_reserved:
172 ; GCN: s_and_saveexec_b64
173 ; GCN: v_mov_b32_e32 [[BASE_FI0:v[0-9]+]], 4
174 ; GCN: buffer_store_dword {{v[0-9]+}}, [[BASE_FI0]], {{s\[[0-9]+:[0-9]+\]}}, {{s[0-9]+}} offen offset:4092{{$}}
175 ; GCN: v_mov_b32_e32 [[BASE_FI1:v[0-9]+]], 4
176 ; GCN: buffer_load_dword {{v[0-9]+}}, [[BASE_FI1]], {{s\[[0-9]+:[0-9]+\]}}, {{s[0-9]+}} offen offset:4092{{$}}
177 ; GCN: {{^BB[0-9]+}}_2:
179 define amdgpu_kernel void @test_sink_scratch_small_offset_i32_reserved(i32 addrspace(1)* %out, i32 addrspace(1)* %in, i32 %arg) {
181 %alloca = alloca [512 x i32], align 4, addrspace(5)
182 %out.gep.0 = getelementptr i32, i32 addrspace(1)* %out, i64 999998
183 %out.gep.1 = getelementptr i32, i32 addrspace(1)* %out, i64 999999
184 %add.arg = add i32 %arg, 8
185 %alloca.gep = getelementptr [512 x i32], [512 x i32] addrspace(5)* %alloca, i32 0, i32 1023
186 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
187 %tmp0 = icmp eq i32 %tid, 0
188 br i1 %tmp0, label %endif, label %if
191 store volatile i32 123, i32 addrspace(5)* %alloca.gep
192 %tmp1 = load volatile i32, i32 addrspace(5)* %alloca.gep
196 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
197 store i32 %x, i32 addrspace(1)* %out.gep.0
198 %load = load volatile i32, i32 addrspace(5)* %alloca.gep
199 store i32 %load, i32 addrspace(1)* %out.gep.1
206 ; OPT-LABEL: @test_no_sink_scratch_large_offset_i32(
207 ; OPT: %alloca.gep = getelementptr [512 x i32], [512 x i32] addrspace(5)* %alloca, i32 0, i32 1024
211 ; GCN-LABEL: {{^}}test_no_sink_scratch_large_offset_i32:
212 ; GCN: s_and_saveexec_b64
213 ; GCN: buffer_store_dword {{v[0-9]+}}, {{v[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, {{s[0-9]+}} offen{{$}}
214 ; GCN: buffer_load_dword {{v[0-9]+}}, {{v[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, {{s[0-9]+}} offen{{$}}
215 ; GCN: {{^BB[0-9]+}}_2:
216 define amdgpu_kernel void @test_no_sink_scratch_large_offset_i32(i32 addrspace(1)* %out, i32 addrspace(1)* %in, i32 %arg) {
218 %alloca = alloca [512 x i32], align 4, addrspace(5)
219 %out.gep.0 = getelementptr i32, i32 addrspace(1)* %out, i64 999998
220 %out.gep.1 = getelementptr i32, i32 addrspace(1)* %out, i64 999999
221 %add.arg = add i32 %arg, 8
222 %alloca.gep = getelementptr [512 x i32], [512 x i32] addrspace(5)* %alloca, i32 0, i32 1024
223 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
224 %tmp0 = icmp eq i32 %tid, 0
225 br i1 %tmp0, label %endif, label %if
228 store volatile i32 123, i32 addrspace(5)* %alloca.gep
229 %tmp1 = load volatile i32, i32 addrspace(5)* %alloca.gep
233 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
234 store i32 %x, i32 addrspace(1)* %out.gep.0
235 %load = load volatile i32, i32 addrspace(5)* %alloca.gep
236 store i32 %load, i32 addrspace(1)* %out.gep.1
243 ; GCN-LABEL: {{^}}test_sink_global_vreg_sreg_i32:
244 ; GCN: s_and_saveexec_b64
245 ; CI: buffer_load_dword {{v[0-9]+}}, {{v\[[0-9]+:[0-9]+\]}}, {{s\[[0-9]+:[0-9]+\]}}, 0 addr64{{$}}
246 ; VI: flat_load_dword v{{[0-9]+}}, v[{{[0-9]+:[0-9]+}}]
247 ; GCN: {{^BB[0-9]+}}_2:
248 define amdgpu_kernel void @test_sink_global_vreg_sreg_i32(i32 addrspace(1)* %out, i32 addrspace(1)* %in, i32 %offset) {
250 %offset.ext = zext i32 %offset to i64
251 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 999999
252 %in.gep = getelementptr i32, i32 addrspace(1)* %in, i64 %offset.ext
253 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
254 %tmp0 = icmp eq i32 %tid, 0
255 br i1 %tmp0, label %endif, label %if
258 %tmp1 = load i32, i32 addrspace(1)* %in.gep
262 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
263 store i32 %x, i32 addrspace(1)* %out.gep
270 ; OPT-LABEL: @test_sink_constant_small_offset_i32
271 ; OPT-NOT: getelementptr i32, i32 addrspace(4)*
274 ; GCN-LABEL: {{^}}test_sink_constant_small_offset_i32:
275 ; GCN: s_and_saveexec_b64
276 ; SI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, 0x7{{$}}
277 ; GCN: s_or_b64 exec, exec
278 define amdgpu_kernel void @test_sink_constant_small_offset_i32(i32 addrspace(1)* %out, i32 addrspace(4)* %in) {
280 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 999999
281 %in.gep = getelementptr i32, i32 addrspace(4)* %in, i64 7
282 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
283 %tmp0 = icmp eq i32 %tid, 0
284 br i1 %tmp0, label %endif, label %if
287 %tmp1 = load i32, i32 addrspace(4)* %in.gep
291 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
292 store i32 %x, i32 addrspace(1)* %out.gep
299 ; OPT-LABEL: @test_sink_constant_max_8_bit_offset_i32
300 ; OPT-NOT: getelementptr i32, i32 addrspace(4)*
303 ; GCN-LABEL: {{^}}test_sink_constant_max_8_bit_offset_i32:
304 ; GCN: s_and_saveexec_b64
305 ; SI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, 0xff{{$}}
306 ; GCN: s_or_b64 exec, exec
307 define amdgpu_kernel void @test_sink_constant_max_8_bit_offset_i32(i32 addrspace(1)* %out, i32 addrspace(4)* %in) {
309 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 999999
310 %in.gep = getelementptr i32, i32 addrspace(4)* %in, i64 255
311 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
312 %tmp0 = icmp eq i32 %tid, 0
313 br i1 %tmp0, label %endif, label %if
316 %tmp1 = load i32, i32 addrspace(4)* %in.gep
320 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
321 store i32 %x, i32 addrspace(1)* %out.gep
328 ; OPT-LABEL: @test_sink_constant_max_8_bit_offset_p1_i32
329 ; OPT-SI: getelementptr i32, i32 addrspace(4)*
330 ; OPT-CI-NOT: getelementptr i32, i32 addrspace(4)*
331 ; OPT-VI-NOT: getelementptr i32, i32 addrspace(4)*
334 ; GCN-LABEL: {{^}}test_sink_constant_max_8_bit_offset_p1_i32:
335 ; GCN: s_and_saveexec_b64
336 ; SI: s_movk_i32 [[OFFSET:s[0-9]+]], 0x400
338 ; SI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, [[OFFSET]]{{$}}
339 ; GCN: s_or_b64 exec, exec
340 define amdgpu_kernel void @test_sink_constant_max_8_bit_offset_p1_i32(i32 addrspace(1)* %out, i32 addrspace(4)* %in) {
342 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 999999
343 %in.gep = getelementptr i32, i32 addrspace(4)* %in, i64 256
344 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
345 %tmp0 = icmp eq i32 %tid, 0
346 br i1 %tmp0, label %endif, label %if
349 %tmp1 = load i32, i32 addrspace(4)* %in.gep
353 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
354 store i32 %x, i32 addrspace(1)* %out.gep
361 ; OPT-LABEL: @test_sink_constant_max_32_bit_offset_i32
362 ; OPT-SI: getelementptr i32, i32 addrspace(4)*
363 ; OPT-CI-NOT: getelementptr i32, i32 addrspace(4)*
366 ; GCN-LABEL: {{^}}test_sink_constant_max_32_bit_offset_i32:
367 ; GCN: s_and_saveexec_b64
368 ; GCN: s_add_u32 s{{[0-9]+}}, s{{[0-9]+}}, -4{{$}}
369 ; GCN: s_addc_u32 s{{[0-9]+}}, s{{[0-9]+}}, 3{{$}}
370 ; SI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, 0x0{{$}}
371 ; GCN: s_or_b64 exec, exec
372 define amdgpu_kernel void @test_sink_constant_max_32_bit_offset_i32(i32 addrspace(1)* %out, i32 addrspace(4)* %in) {
374 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 999999
375 %in.gep = getelementptr i32, i32 addrspace(4)* %in, i64 4294967295
376 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
377 %tmp0 = icmp eq i32 %tid, 0
378 br i1 %tmp0, label %endif, label %if
381 %tmp1 = load i32, i32 addrspace(4)* %in.gep
385 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
386 store i32 %x, i32 addrspace(1)* %out.gep
393 ; OPT-LABEL: @test_sink_constant_max_32_bit_offset_p1_i32
394 ; OPT: getelementptr i32, i32 addrspace(4)*
397 ; GCN-LABEL: {{^}}test_sink_constant_max_32_bit_offset_p1_i32:
398 ; GCN: s_and_saveexec_b64
401 ; SI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, 0x0{{$}}
402 ; GCN: s_or_b64 exec, exec
403 define amdgpu_kernel void @test_sink_constant_max_32_bit_offset_p1_i32(i32 addrspace(1)* %out, i32 addrspace(4)* %in) {
405 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 999999
406 %in.gep = getelementptr i32, i32 addrspace(4)* %in, i64 17179869181
407 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
408 %tmp0 = icmp eq i32 %tid, 0
409 br i1 %tmp0, label %endif, label %if
412 %tmp1 = load i32, i32 addrspace(4)* %in.gep
416 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
417 store i32 %x, i32 addrspace(1)* %out.gep
424 ; GCN-LABEL: {{^}}test_sink_constant_max_20_bit_byte_offset_i32:
425 ; GCN: s_and_saveexec_b64
426 ; SI: s_mov_b32 [[OFFSET:s[0-9]+]], 0xffffc{{$}}
427 ; SI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, [[OFFSET]]{{$}}
429 ; CI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, 0x3ffff{{$}}
430 ; VI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, 0xffffc{{$}}
432 ; GCN: s_or_b64 exec, exec
433 define amdgpu_kernel void @test_sink_constant_max_20_bit_byte_offset_i32(i32 addrspace(1)* %out, i32 addrspace(4)* %in) {
435 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 999999
436 %in.gep = getelementptr i32, i32 addrspace(4)* %in, i64 262143
437 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
438 %tmp0 = icmp eq i32 %tid, 0
439 br i1 %tmp0, label %endif, label %if
442 %tmp1 = load i32, i32 addrspace(4)* %in.gep
446 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
447 store i32 %x, i32 addrspace(1)* %out.gep
454 ; OPT-LABEL: @test_sink_constant_max_20_bit_byte_offset_p1_i32
455 ; OPT-SI: getelementptr i32, i32 addrspace(4)*
456 ; OPT-CI-NOT: getelementptr i32, i32 addrspace(4)*
457 ; OPT-VI: getelementptr i32, i32 addrspace(4)*
460 ; GCN-LABEL: {{^}}test_sink_constant_max_20_bit_byte_offset_p1_i32:
461 ; GCN: s_and_saveexec_b64
462 ; SI: s_mov_b32 [[OFFSET:s[0-9]+]], 0x100000{{$}}
463 ; SI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, [[OFFSET]]{{$}}
465 ; CI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, 0x40000{{$}}
467 ; VI: s_mov_b32 [[OFFSET:s[0-9]+]], 0x100000{{$}}
468 ; VI: s_load_dword s{{[0-9]+}}, {{s\[[0-9]+:[0-9]+\]}}, [[OFFSET]]{{$}}
470 ; GCN: s_or_b64 exec, exec
471 define amdgpu_kernel void @test_sink_constant_max_20_bit_byte_offset_p1_i32(i32 addrspace(1)* %out, i32 addrspace(4)* %in) {
473 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 999999
474 %in.gep = getelementptr i32, i32 addrspace(4)* %in, i64 262144
475 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
476 %tmp0 = icmp eq i32 %tid, 0
477 br i1 %tmp0, label %endif, label %if
480 %tmp1 = load i32, i32 addrspace(4)* %in.gep
484 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
485 store i32 %x, i32 addrspace(1)* %out.gep
492 %struct.foo = type { [3 x float], [3 x float] }
494 ; OPT-LABEL: @sink_ds_address(
495 ; OPT: getelementptr inbounds i8,
497 ; GCN-LABEL: {{^}}sink_ds_address:
498 ; GCN: s_load_dword [[SREG1:s[0-9]+]],
499 ; GCN: v_mov_b32_e32 [[VREG1:v[0-9]+]], [[SREG1]]
500 ; GCN-DAG: ds_read2_b32 v[{{[0-9+:[0-9]+}}], [[VREG1]] offset0:3 offset1:5
501 define amdgpu_kernel void @sink_ds_address(%struct.foo addrspace(3)* nocapture %ptr) nounwind {
503 %x = getelementptr inbounds %struct.foo, %struct.foo addrspace(3)* %ptr, i32 0, i32 1, i32 0
504 %y = getelementptr inbounds %struct.foo, %struct.foo addrspace(3)* %ptr, i32 0, i32 1, i32 2
508 %a = load float, float addrspace(3)* %x, align 4
509 %b = load float, float addrspace(3)* %y, align 4
510 %cmp = fcmp one float %a, %b
511 br i1 %cmp, label %bb34, label %bb33
520 ; Address offset is not a multiple of 4. This is a valid mubuf offset,
523 ; OPT-LABEL: @test_sink_constant_small_max_mubuf_offset_load_i32_align_1(
526 ; OPT: getelementptr i8, {{.*}} 4095
527 define amdgpu_kernel void @test_sink_constant_small_max_mubuf_offset_load_i32_align_1(i32 addrspace(1)* %out, i8 addrspace(4)* %in) {
529 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i32 1024
530 %in.gep = getelementptr i8, i8 addrspace(4)* %in, i64 4095
531 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
532 %tmp0 = icmp eq i32 %tid, 0
533 br i1 %tmp0, label %endif, label %if
536 %bitcast = bitcast i8 addrspace(4)* %in.gep to i32 addrspace(4)*
537 %tmp1 = load i32, i32 addrspace(4)* %bitcast, align 1
541 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
542 store i32 %x, i32 addrspace(1)* %out.gep
549 ; OPT-LABEL: @test_sink_local_small_offset_atomicrmw_i32(
550 ; OPT: %0 = bitcast i32 addrspace(3)* %in to i8 addrspace(3)*
551 ; OPT: %sunkaddr = getelementptr i8, i8 addrspace(3)* %0, i32 28
552 ; OPT: %1 = bitcast i8 addrspace(3)* %sunkaddr to i32 addrspace(3)*
553 ; OPT: %tmp1 = atomicrmw add i32 addrspace(3)* %1, i32 2 seq_cst
554 define amdgpu_kernel void @test_sink_local_small_offset_atomicrmw_i32(i32 addrspace(3)* %out, i32 addrspace(3)* %in) {
556 %out.gep = getelementptr i32, i32 addrspace(3)* %out, i32 999999
557 %in.gep = getelementptr i32, i32 addrspace(3)* %in, i32 7
558 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
559 %tmp0 = icmp eq i32 %tid, 0
560 br i1 %tmp0, label %endif, label %if
563 %tmp1 = atomicrmw add i32 addrspace(3)* %in.gep, i32 2 seq_cst
567 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
568 store i32 %x, i32 addrspace(3)* %out.gep
575 ; OPT-LABEL: @test_sink_local_small_offset_cmpxchg_i32(
576 ; OPT: %0 = bitcast i32 addrspace(3)* %in to i8 addrspace(3)*
577 ; OPT: %sunkaddr = getelementptr i8, i8 addrspace(3)* %0, i32 28
578 ; OPT: %1 = bitcast i8 addrspace(3)* %sunkaddr to i32 addrspace(3)*
579 ; OPT: %tmp1.struct = cmpxchg i32 addrspace(3)* %1, i32 undef, i32 2 seq_cst monotonic
580 define amdgpu_kernel void @test_sink_local_small_offset_cmpxchg_i32(i32 addrspace(3)* %out, i32 addrspace(3)* %in) {
582 %out.gep = getelementptr i32, i32 addrspace(3)* %out, i32 999999
583 %in.gep = getelementptr i32, i32 addrspace(3)* %in, i32 7
584 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
585 %tmp0 = icmp eq i32 %tid, 0
586 br i1 %tmp0, label %endif, label %if
589 %tmp1.struct = cmpxchg i32 addrspace(3)* %in.gep, i32 undef, i32 2 seq_cst monotonic
590 %tmp1 = extractvalue { i32, i1 } %tmp1.struct, 0
594 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
595 store i32 %x, i32 addrspace(3)* %out.gep
602 ; OPT-LABEL: @test_wrong_operand_local_small_offset_cmpxchg_i32(
603 ; OPT: %in.gep = getelementptr i32, i32 addrspace(3)* %in, i32 7
605 ; OPT: cmpxchg i32 addrspace(3)* addrspace(3)* undef, i32 addrspace(3)* %in.gep, i32 addrspace(3)* undef seq_cst monotonic
606 define amdgpu_kernel void @test_wrong_operand_local_small_offset_cmpxchg_i32(i32 addrspace(3)* addrspace(3)* %out, i32 addrspace(3)* %in) {
608 %out.gep = getelementptr i32 addrspace(3)*, i32 addrspace(3)* addrspace(3)* %out, i32 999999
609 %in.gep = getelementptr i32, i32 addrspace(3)* %in, i32 7
610 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
611 %tmp0 = icmp eq i32 %tid, 0
612 br i1 %tmp0, label %endif, label %if
615 %tmp1.struct = cmpxchg i32 addrspace(3)* addrspace(3)* undef, i32 addrspace(3)* %in.gep, i32 addrspace(3)* undef seq_cst monotonic
616 %tmp1 = extractvalue { i32 addrspace(3)*, i1 } %tmp1.struct, 0
620 %x = phi i32 addrspace(3)* [ %tmp1, %if ], [ null, %entry ]
621 store i32 addrspace(3)* %x, i32 addrspace(3)* addrspace(3)* %out.gep
628 ; OPT-LABEL: @test_sink_local_small_offset_atomic_inc_i32(
629 ; OPT: %0 = bitcast i32 addrspace(3)* %in to i8 addrspace(3)*
630 ; OPT: %sunkaddr = getelementptr i8, i8 addrspace(3)* %0, i32 28
631 ; OPT: %1 = bitcast i8 addrspace(3)* %sunkaddr to i32 addrspace(3)*
632 ; OPT: %tmp1 = call i32 @llvm.amdgcn.atomic.inc.i32.p3i32(i32 addrspace(3)* %1, i32 2, i32 0, i32 0, i1 false)
633 define amdgpu_kernel void @test_sink_local_small_offset_atomic_inc_i32(i32 addrspace(3)* %out, i32 addrspace(3)* %in) {
635 %out.gep = getelementptr i32, i32 addrspace(3)* %out, i32 999999
636 %in.gep = getelementptr i32, i32 addrspace(3)* %in, i32 7
637 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
638 %tmp0 = icmp eq i32 %tid, 0
639 br i1 %tmp0, label %endif, label %if
642 %tmp1 = call i32 @llvm.amdgcn.atomic.inc.i32.p3i32(i32 addrspace(3)* %in.gep, i32 2, i32 0, i32 0, i1 false)
646 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
647 store i32 %x, i32 addrspace(3)* %out.gep
654 ; OPT-LABEL: @test_sink_local_small_offset_atomic_dec_i32(
655 ; OPT: %0 = bitcast i32 addrspace(3)* %in to i8 addrspace(3)*
656 ; OPT: %sunkaddr = getelementptr i8, i8 addrspace(3)* %0, i32 28
657 ; OPT: %1 = bitcast i8 addrspace(3)* %sunkaddr to i32 addrspace(3)*
658 ; OPT: %tmp1 = call i32 @llvm.amdgcn.atomic.dec.i32.p3i32(i32 addrspace(3)* %1, i32 2, i32 0, i32 0, i1 false)
659 define amdgpu_kernel void @test_sink_local_small_offset_atomic_dec_i32(i32 addrspace(3)* %out, i32 addrspace(3)* %in) {
661 %out.gep = getelementptr i32, i32 addrspace(3)* %out, i32 999999
662 %in.gep = getelementptr i32, i32 addrspace(3)* %in, i32 7
663 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
664 %tmp0 = icmp eq i32 %tid, 0
665 br i1 %tmp0, label %endif, label %if
668 %tmp1 = call i32 @llvm.amdgcn.atomic.dec.i32.p3i32(i32 addrspace(3)* %in.gep, i32 2, i32 0, i32 0, i1 false)
672 %x = phi i32 [ %tmp1, %if ], [ 0, %entry ]
673 store i32 %x, i32 addrspace(3)* %out.gep
680 ; OPT-LABEL: @test_sink_global_small_min_scratch_global_offset(
681 ; OPT-SICIVI: %in.gep = getelementptr i8, i8 addrspace(1)* %in, i64 -4096
683 ; OPT-SICIVI: %tmp1 = load i8, i8 addrspace(1)* %in.gep
686 ; OPT-GFX9: %sunkaddr = getelementptr i8, i8 addrspace(1)* %in, i64 -4096
687 ; OPT-GFX9: load i8, i8 addrspace(1)* %sunkaddr
689 ; GCN-LABEL: {{^}}test_sink_global_small_min_scratch_global_offset:
690 ; GFX9: global_load_sbyte v{{[0-9]+}}, v{{\[[0-9]+:[0-9]+\]}}, off offset:-4096{{$}}
691 define amdgpu_kernel void @test_sink_global_small_min_scratch_global_offset(i32 addrspace(1)* %out, i8 addrspace(1)* %in) {
693 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i32 1024
694 %in.gep = getelementptr i8, i8 addrspace(1)* %in, i64 -4096
695 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
696 %tmp0 = icmp eq i32 %tid, 0
697 br i1 %tmp0, label %endif, label %if
700 %tmp1 = load i8, i8 addrspace(1)* %in.gep
701 %tmp2 = sext i8 %tmp1 to i32
705 %x = phi i32 [ %tmp2, %if ], [ 0, %entry ]
706 store i32 %x, i32 addrspace(1)* %out.gep
713 ; OPT-LABEL: @test_sink_global_small_min_scratch_global_neg1_offset(
714 ; OPT: %in.gep = getelementptr i8, i8 addrspace(1)* %in, i64 -4097
716 ; OPT: load i8, i8 addrspace(1)* %in.gep
718 ; GCN-LABEL: {{^}}test_sink_global_small_min_scratch_global_neg1_offset:
719 define amdgpu_kernel void @test_sink_global_small_min_scratch_global_neg1_offset(i32 addrspace(1)* %out, i8 addrspace(1)* %in) {
721 %out.gep = getelementptr i32, i32 addrspace(1)* %out, i64 99999
722 %in.gep = getelementptr i8, i8 addrspace(1)* %in, i64 -4097
723 %tid = call i32 @llvm.amdgcn.mbcnt.lo(i32 -1, i32 0) #0
724 %tmp0 = icmp eq i32 %tid, 0
725 br i1 %tmp0, label %endif, label %if
728 %tmp1 = load i8, i8 addrspace(1)* %in.gep
729 %tmp2 = sext i8 %tmp1 to i32
733 %x = phi i32 [ %tmp2, %if ], [ 0, %entry ]
734 store i32 %x, i32 addrspace(1)* %out.gep
741 declare i32 @llvm.amdgcn.mbcnt.lo(i32, i32) #0
742 declare i32 @llvm.amdgcn.atomic.inc.i32.p3i32(i32 addrspace(3)* nocapture, i32, i32, i32, i1) #2
743 declare i32 @llvm.amdgcn.atomic.dec.i32.p3i32(i32 addrspace(3)* nocapture, i32, i32, i32, i1) #2
745 attributes #0 = { nounwind readnone }
746 attributes #1 = { nounwind }
747 attributes #2 = { nounwind argmemonly }