blob: b46729043021a1f0d4161e3b547548122eee6ff5 [file] [log] [blame]
Matt Arsenault3a619852016-02-27 20:26:57 +00001; RUN: llc -verify-machineinstrs -march=amdgcn < %s | FileCheck -check-prefix=GCN %s
2; RUN: llc -verify-machineinstrs -march=amdgcn -mcpu=tonga < %s | FileCheck -check-prefix=GCN %s
Tom Stellard80580692015-01-20 17:49:43 +00003
4; When a frame index offset is more than 12-bits, make sure we don't store
5; it in mubuf's offset field.
6
Tom Stellard8255af42015-01-20 17:49:45 +00007; Also, make sure we use the same register for storing the scratch buffer addresss
8; for both stores. This register is allocated by the register scavenger, so we
9; should be able to reuse the same regiser for each scratch buffer access.
10
Tom Stellard78655fc2015-07-16 19:40:09 +000011; GCN-LABEL: {{^}}legal_offset_fi:
Matt Arsenault707780b2017-02-22 21:05:25 +000012; GCN: buffer_store_dword v{{[0-9]+}}, off, s[{{[0-9]+}}:{{[0-9]+}}], s{{[0-9]+}} offset:4{{$}}
13; GCN: v_mov_b32_e32 [[OFFSET:v[0-9]+]], 0x8004
Tom Stellard78655fc2015-07-16 19:40:09 +000014; GCN: buffer_store_dword v{{[0-9]+}}, [[OFFSET]], s[{{[0-9]+}}:{{[0-9]+}}], s{{[0-9]+}} offen{{$}}
Tom Stellard80580692015-01-20 17:49:43 +000015
16define void @legal_offset_fi(i32 addrspace(1)* %out, i32 %cond, i32 %if_offset, i32 %else_offset) {
17entry:
18 %scratch0 = alloca [8192 x i32]
19 %scratch1 = alloca [8192 x i32]
20
David Blaikie79e6c742015-02-27 19:29:02 +000021 %scratchptr0 = getelementptr [8192 x i32], [8192 x i32]* %scratch0, i32 0, i32 0
Tom Stellard80580692015-01-20 17:49:43 +000022 store i32 1, i32* %scratchptr0
23
David Blaikie79e6c742015-02-27 19:29:02 +000024 %scratchptr1 = getelementptr [8192 x i32], [8192 x i32]* %scratch1, i32 0, i32 0
Tom Stellard80580692015-01-20 17:49:43 +000025 store i32 2, i32* %scratchptr1
26
27 %cmp = icmp eq i32 %cond, 0
28 br i1 %cmp, label %if, label %else
29
30if:
David Blaikie79e6c742015-02-27 19:29:02 +000031 %if_ptr = getelementptr [8192 x i32], [8192 x i32]* %scratch0, i32 0, i32 %if_offset
David Blaikiea79ac142015-02-27 21:17:42 +000032 %if_value = load i32, i32* %if_ptr
Tom Stellard80580692015-01-20 17:49:43 +000033 br label %done
34
35else:
David Blaikie79e6c742015-02-27 19:29:02 +000036 %else_ptr = getelementptr [8192 x i32], [8192 x i32]* %scratch1, i32 0, i32 %else_offset
David Blaikiea79ac142015-02-27 21:17:42 +000037 %else_value = load i32, i32* %else_ptr
Tom Stellard80580692015-01-20 17:49:43 +000038 br label %done
39
40done:
41 %value = phi i32 [%if_value, %if], [%else_value, %else]
42 store i32 %value, i32 addrspace(1)* %out
43 ret void
44
45 ret void
46
47}
48
Matt Arsenaultcb38a6b2016-03-21 18:02:18 +000049; GCN-LABEL: {{^}}legal_offset_fi_offset:
Matt Arsenault0efdd062016-09-09 22:29:28 +000050; GCN-DAG: buffer_store_dword v{{[0-9]+}}, v{{[0-9]+}}, s[{{[0-9]+}}:{{[0-9]+}}], s{{[0-9]+}} offen{{$}}
Tom Stellard0d162b12016-11-16 18:42:17 +000051; This constant isn't folded, because it has multiple uses.
Matt Arsenault707780b2017-02-22 21:05:25 +000052; GCN-DAG: v_mov_b32_e32 [[K8000:v[0-9]+]], 0x8004
Tom Stellard0d162b12016-11-16 18:42:17 +000053; GCN-DAG: v_add_i32_e32 [[OFFSET:v[0-9]+]], vcc, [[K8000]]
Tom Stellard78655fc2015-07-16 19:40:09 +000054; GCN: buffer_store_dword v{{[0-9]+}}, [[OFFSET]], s[{{[0-9]+}}:{{[0-9]+}}], s{{[0-9]+}} offen{{$}}
Tom Stellard80580692015-01-20 17:49:43 +000055
56define void @legal_offset_fi_offset(i32 addrspace(1)* %out, i32 %cond, i32 addrspace(1)* %offsets, i32 %if_offset, i32 %else_offset) {
57entry:
58 %scratch0 = alloca [8192 x i32]
59 %scratch1 = alloca [8192 x i32]
60
David Blaikiea79ac142015-02-27 21:17:42 +000061 %offset0 = load i32, i32 addrspace(1)* %offsets
David Blaikie79e6c742015-02-27 19:29:02 +000062 %scratchptr0 = getelementptr [8192 x i32], [8192 x i32]* %scratch0, i32 0, i32 %offset0
Tom Stellard80580692015-01-20 17:49:43 +000063 store i32 %offset0, i32* %scratchptr0
64
David Blaikie79e6c742015-02-27 19:29:02 +000065 %offsetptr1 = getelementptr i32, i32 addrspace(1)* %offsets, i32 1
David Blaikiea79ac142015-02-27 21:17:42 +000066 %offset1 = load i32, i32 addrspace(1)* %offsetptr1
David Blaikie79e6c742015-02-27 19:29:02 +000067 %scratchptr1 = getelementptr [8192 x i32], [8192 x i32]* %scratch1, i32 0, i32 %offset1
Tom Stellard80580692015-01-20 17:49:43 +000068 store i32 %offset1, i32* %scratchptr1
69
70 %cmp = icmp eq i32 %cond, 0
71 br i1 %cmp, label %if, label %else
72
73if:
David Blaikie79e6c742015-02-27 19:29:02 +000074 %if_ptr = getelementptr [8192 x i32], [8192 x i32]* %scratch0, i32 0, i32 %if_offset
David Blaikiea79ac142015-02-27 21:17:42 +000075 %if_value = load i32, i32* %if_ptr
Tom Stellard80580692015-01-20 17:49:43 +000076 br label %done
77
78else:
David Blaikie79e6c742015-02-27 19:29:02 +000079 %else_ptr = getelementptr [8192 x i32], [8192 x i32]* %scratch1, i32 0, i32 %else_offset
David Blaikiea79ac142015-02-27 21:17:42 +000080 %else_value = load i32, i32* %else_ptr
Tom Stellard80580692015-01-20 17:49:43 +000081 br label %done
82
83done:
84 %value = phi i32 [%if_value, %if], [%else_value, %else]
85 store i32 %value, i32 addrspace(1)* %out
86 ret void
87}
88
Matt Arsenaultcb38a6b2016-03-21 18:02:18 +000089; GCN-LABEL: {{^}}neg_vaddr_offset:
90; GCN: buffer_store_dword v{{[0-9]+}}, v{{[0-9]+}}, s[{{[0-9]+:[0-9]+}}], s{{[0-9]+}} offen offset:16{{$}}
Tom Stellard78655fc2015-07-16 19:40:09 +000091define void @neg_vaddr_offset(i32 %offset) {
92entry:
93 %array = alloca [8192 x i32]
94 %ptr_offset = add i32 %offset, 4
95 %ptr = getelementptr [8192 x i32], [8192 x i32]* %array, i32 0, i32 %ptr_offset
96 store i32 0, i32* %ptr
97 ret void
98}
99
Matt Arsenaultcb38a6b2016-03-21 18:02:18 +0000100; GCN-LABEL: {{^}}pos_vaddr_offset:
Matt Arsenault707780b2017-02-22 21:05:25 +0000101; GCN: buffer_store_dword v{{[0-9]+}}, off, s[{{[0-9]+:[0-9]+}}], s{{[0-9]+}} offset:20
Tom Stellard78655fc2015-07-16 19:40:09 +0000102define void @pos_vaddr_offset(i32 addrspace(1)* %out, i32 %offset) {
103entry:
104 %array = alloca [8192 x i32]
105 %ptr = getelementptr [8192 x i32], [8192 x i32]* %array, i32 0, i32 4
106 store i32 0, i32* %ptr
107 %load_ptr = getelementptr [8192 x i32], [8192 x i32]* %array, i32 0, i32 %offset
108 %val = load i32, i32* %load_ptr
109 store i32 %val, i32 addrspace(1)* %out
110 ret void
111}