blob: 723c78ad647aee49851ed86a7806192042dbcdeb [file] [log] [blame]
Matt Arsenaulta2025382017-08-03 23:24:05 +00001; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=fiji -verify-machineinstrs < %s | FileCheck -enable-var-scope -check-prefixes=GCN,VI %s
2; RUN: llc -mtriple=amdgcn-amd-amdhsa -mcpu=hawaii -verify-machineinstrs < %s | FileCheck -enable-var-scope -check-prefixes=GCN,CI %s
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +00003
4%struct.ByValStruct = type { [4 x i32] }
5
6; GCN-LABEL: {{^}}void_func_byval_struct:
7; GCN: s_mov_b32 s5, s32
Matt Arsenaultd1867c02017-08-02 00:59:51 +00008; GCN: buffer_load_dword [[LOAD0:v[0-9]+]], off, s[0:3], s5 offset:4{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +00009; GCN-NOT: s32
Matt Arsenaultd1867c02017-08-02 00:59:51 +000010; GCN: buffer_store_dword [[LOAD0]], off, s[0:3], s5 offset:4{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000011; GCN-NOT: s32
12
Matt Arsenaultd1867c02017-08-02 00:59:51 +000013; GCN: buffer_load_dword [[LOAD1:v[0-9]+]], off, s[0:3], s5 offset:20{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000014; GCN-NOT: s32
Matt Arsenaultd1867c02017-08-02 00:59:51 +000015; GCN: buffer_store_dword [[LOAD1]], off, s[0:3], s5 offset:20{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000016; GCN-NOT: s32
17define void @void_func_byval_struct(%struct.ByValStruct* byval noalias nocapture align 4 %arg0, %struct.ByValStruct* byval noalias nocapture align 4 %arg1) #1 {
18entry:
19 %arrayidx = getelementptr inbounds %struct.ByValStruct, %struct.ByValStruct* %arg0, i32 0, i32 0, i32 0
20 %tmp = load volatile i32, i32* %arrayidx, align 4
21 %add = add nsw i32 %tmp, 1
22 store volatile i32 %add, i32* %arrayidx, align 4
23 %arrayidx2 = getelementptr inbounds %struct.ByValStruct, %struct.ByValStruct* %arg1, i32 0, i32 0, i32 0
24 %tmp1 = load volatile i32, i32* %arrayidx2, align 4
25 %add3 = add nsw i32 %tmp1, 2
26 store volatile i32 %add3, i32* %arrayidx2, align 4
27 store volatile i32 9, i32 addrspace(1)* null, align 4
28 ret void
29}
30
31; GCN-LABEL: {{^}}void_func_byval_struct_non_leaf:
32; GCN: s_mov_b32 s5, s32
Matt Arsenault8e8f8f42017-08-02 01:52:45 +000033; GCN-DAG: buffer_store_dword v32
34; GCN-DAG: buffer_store_dword v33
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000035; GCN: v_writelane_b32
36
Matt Arsenault8e8f8f42017-08-02 01:52:45 +000037; GCN-DAG: s_add_u32 s32, s32, 0xb00{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000038
Matt Arsenaultd1867c02017-08-02 00:59:51 +000039; GCN-DAG: buffer_load_dword [[LOAD0:v[0-9]+]], off, s[0:3], s5 offset:4{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000040; GCN: v_add_i32_e32 [[ADD0:v[0-9]+]], vcc, 1, [[LOAD0]]
Matt Arsenaultd1867c02017-08-02 00:59:51 +000041; GCN: buffer_store_dword [[ADD0]], off, s[0:3], s5 offset:4{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000042
Matt Arsenaultd1867c02017-08-02 00:59:51 +000043; GCN: buffer_load_dword [[LOAD1:v[0-9]+]], off, s[0:3], s5 offset:20{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000044; GCN: v_add_i32_e32 [[ADD1:v[0-9]+]], vcc, 2, [[LOAD1]]
45
46; GCN: s_swappc_b64
47
Matt Arsenaultd1867c02017-08-02 00:59:51 +000048; GCN: buffer_store_dword [[ADD1]], off, s[0:3], s5 offset:20{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000049
50; GCN: v_readlane_b32
51; GCN: buffer_load_dword v32,
Matt Arsenault8e8f8f42017-08-02 01:52:45 +000052; GCN: buffer_load_dword v33,
53; GCN: s_sub_u32 s32, s32, 0xb00{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000054; GCN: s_setpc_b64
55define void @void_func_byval_struct_non_leaf(%struct.ByValStruct* byval noalias nocapture align 4 %arg0, %struct.ByValStruct* byval noalias nocapture align 4 %arg1) #1 {
56entry:
57 %arrayidx = getelementptr inbounds %struct.ByValStruct, %struct.ByValStruct* %arg0, i32 0, i32 0, i32 0
58 %tmp = load volatile i32, i32* %arrayidx, align 4
59 %add = add nsw i32 %tmp, 1
60 store volatile i32 %add, i32* %arrayidx, align 4
61 %arrayidx2 = getelementptr inbounds %struct.ByValStruct, %struct.ByValStruct* %arg1, i32 0, i32 0, i32 0
62 %tmp1 = load volatile i32, i32* %arrayidx2, align 4
63 %add3 = add nsw i32 %tmp1, 2
64 call void @external_void_func_void()
65 store volatile i32 %add3, i32* %arrayidx2, align 4
66 store volatile i32 9, i32 addrspace(1)* null, align 4
67 ret void
68}
69
70; GCN-LABEL: {{^}}call_void_func_byval_struct_func:
71; GCN: s_mov_b32 s5, s32
Matt Arsenault8e8f8f42017-08-02 01:52:45 +000072; GCN: s_add_u32 s32, s32, 0xc00{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000073; GCN: v_writelane_b32
74
75; GCN-DAG: s_add_u32 s32, s32, 0x800{{$}}
76; GCN-DAG: v_mov_b32_e32 [[NINE:v[0-9]+]], 9
77; GCN-DAG: v_mov_b32_e32 [[THIRTEEN:v[0-9]+]], 13
78
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000079; GCN-DAG: buffer_store_dword [[NINE]], off, s[0:3], s5 offset:8
80; GCN-DAG: buffer_store_dword [[THIRTEEN]], off, s[0:3], s5 offset:24
81
Matt Arsenaultacc5e822017-08-02 00:43:42 +000082; GCN: buffer_load_dword [[LOAD0:v[0-9]+]], off, s[0:3], s5 offset:8
83; GCN: buffer_load_dword [[LOAD1:v[0-9]+]], off, s[0:3], s5 offset:12
84; GCN: buffer_load_dword [[LOAD2:v[0-9]+]], off, s[0:3], s5 offset:16
85; GCN: buffer_load_dword [[LOAD3:v[0-9]+]], off, s[0:3], s5 offset:20
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000086
87
Matt Arsenaultd1867c02017-08-02 00:59:51 +000088; GCN-DAG: buffer_store_dword [[LOAD0]], off, s[0:3], s32 offset:4{{$}}
89; GCN-DAG: buffer_store_dword [[LOAD1]], off, s[0:3], s32 offset:8
90; GCN-DAG: buffer_store_dword [[LOAD2]], off, s[0:3], s32 offset:12
91; GCN-DAG: buffer_store_dword [[LOAD3]], off, s[0:3], s32 offset:16
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000092
Matt Arsenaultacc5e822017-08-02 00:43:42 +000093; GCN: buffer_load_dword [[LOAD4:v[0-9]+]], off, s[0:3], s5 offset:24
94; GCN: buffer_load_dword [[LOAD5:v[0-9]+]], off, s[0:3], s5 offset:28
95; GCN: buffer_load_dword [[LOAD6:v[0-9]+]], off, s[0:3], s5 offset:32
96; GCN: buffer_load_dword [[LOAD7:v[0-9]+]], off, s[0:3], s5 offset:36
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +000097
Matt Arsenaultd1867c02017-08-02 00:59:51 +000098; GCN-DAG: buffer_store_dword [[LOAD4]], off, s[0:3], s32 offset:20
99; GCN-DAG: buffer_store_dword [[LOAD5]], off, s[0:3], s32 offset:24
100; GCN-DAG: buffer_store_dword [[LOAD6]], off, s[0:3], s32 offset:28
101; GCN-DAG: buffer_store_dword [[LOAD7]], off, s[0:3], s32 offset:32
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +0000102
103; GCN: s_swappc_b64
104; GCN-NEXT: s_sub_u32 s32, s32, 0x800{{$}}
105
106; GCN: v_readlane_b32
107
Matt Arsenault8e8f8f42017-08-02 01:52:45 +0000108; GCN: s_sub_u32 s32, s32, 0xc00{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +0000109; GCN-NEXT: s_waitcnt
110; GCN-NEXT: s_setpc_b64
111define void @call_void_func_byval_struct_func() #0 {
112entry:
113 %arg0 = alloca %struct.ByValStruct, align 4
114 %arg1 = alloca %struct.ByValStruct, align 4
115 %tmp = bitcast %struct.ByValStruct* %arg0 to i8*
116 call void @llvm.lifetime.start.p0i8(i64 32, i8* %tmp)
117 %tmp1 = bitcast %struct.ByValStruct* %arg1 to i8*
118 call void @llvm.lifetime.start.p0i8(i64 32, i8* %tmp1)
119 %arrayidx = getelementptr inbounds %struct.ByValStruct, %struct.ByValStruct* %arg0, i32 0, i32 0, i32 0
120 store volatile i32 9, i32* %arrayidx, align 4
121 %arrayidx2 = getelementptr inbounds %struct.ByValStruct, %struct.ByValStruct* %arg1, i32 0, i32 0, i32 0
122 store volatile i32 13, i32* %arrayidx2, align 4
123 call void @void_func_byval_struct(%struct.ByValStruct* byval nonnull align 4 %arg0, %struct.ByValStruct* byval nonnull align 4 %arg1)
124 call void @llvm.lifetime.end.p0i8(i64 32, i8* %tmp1)
125 call void @llvm.lifetime.end.p0i8(i64 32, i8* %tmp)
126 ret void
127}
128
129; GCN-LABEL: {{^}}call_void_func_byval_struct_kernel:
Geoff Berry4e38e022017-08-17 04:04:11 +0000130; GCN: s_mov_b32 s33, s7
131; GCN: s_add_u32 s32, s33, 0xa00{{$}}
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +0000132
133; GCN-DAG: v_mov_b32_e32 [[NINE:v[0-9]+]], 9
134; GCN-DAG: v_mov_b32_e32 [[THIRTEEN:v[0-9]+]], 13
Geoff Berry4e38e022017-08-17 04:04:11 +0000135; GCN-DAG: buffer_store_dword [[NINE]], off, s[0:3], s33 offset:8
136; GCN: buffer_store_dword [[THIRTEEN]], off, s[0:3], s33 offset:24
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +0000137
138; GCN-DAG: s_add_u32 s32, s32, 0x800{{$}}
139
Geoff Berry4e38e022017-08-17 04:04:11 +0000140; GCN-DAG: buffer_load_dword [[LOAD0:v[0-9]+]], off, s[0:3], s33 offset:8
141; GCN-DAG: buffer_load_dword [[LOAD1:v[0-9]+]], off, s[0:3], s33 offset:12
142; GCN-DAG: buffer_load_dword [[LOAD2:v[0-9]+]], off, s[0:3], s33 offset:16
143; GCN-DAG: buffer_load_dword [[LOAD3:v[0-9]+]], off, s[0:3], s33 offset:20
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +0000144
Matt Arsenaultd1867c02017-08-02 00:59:51 +0000145; GCN-DAG: buffer_store_dword [[LOAD0]], off, s[0:3], s32 offset:4{{$}}
146; GCN-DAG: buffer_store_dword [[LOAD1]], off, s[0:3], s32 offset:8
147; GCN-DAG: buffer_store_dword [[LOAD2]], off, s[0:3], s32 offset:12
148; GCN-DAG: buffer_store_dword [[LOAD3]], off, s[0:3], s32 offset:16
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +0000149
Matt Arsenaultacc5e822017-08-02 00:43:42 +0000150; GCN-DAG: buffer_load_dword [[LOAD4:v[0-9]+]], off, s[0:3], s33 offset:24
151; GCN-DAG: buffer_load_dword [[LOAD5:v[0-9]+]], off, s[0:3], s33 offset:28
152; GCN-DAG: buffer_load_dword [[LOAD6:v[0-9]+]], off, s[0:3], s33 offset:32
153; GCN-DAG: buffer_load_dword [[LOAD7:v[0-9]+]], off, s[0:3], s33 offset:36
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +0000154
Matt Arsenaultd1867c02017-08-02 00:59:51 +0000155; GCN-DAG: buffer_store_dword [[LOAD4]], off, s[0:3], s32 offset:20
156; GCN-DAG: buffer_store_dword [[LOAD5]], off, s[0:3], s32 offset:24
157; GCN-DAG: buffer_store_dword [[LOAD6]], off, s[0:3], s32 offset:28
158; GCN-DAG: buffer_store_dword [[LOAD7]], off, s[0:3], s32 offset:32
Matt Arsenaultb62a4eb2017-08-01 19:54:18 +0000159
160
161; GCN: s_swappc_b64
162; FIXME: Dead SP modfication
163; GCN-NEXT: s_sub_u32 s32, s32, 0x800{{$}}
164; GCN-NEXT: s_endpgm
165define amdgpu_kernel void @call_void_func_byval_struct_kernel() #0 {
166entry:
167 %arg0 = alloca %struct.ByValStruct, align 4
168 %arg1 = alloca %struct.ByValStruct, align 4
169 %tmp = bitcast %struct.ByValStruct* %arg0 to i8*
170 call void @llvm.lifetime.start.p0i8(i64 32, i8* %tmp)
171 %tmp1 = bitcast %struct.ByValStruct* %arg1 to i8*
172 call void @llvm.lifetime.start.p0i8(i64 32, i8* %tmp1)
173 %arrayidx = getelementptr inbounds %struct.ByValStruct, %struct.ByValStruct* %arg0, i32 0, i32 0, i32 0
174 store volatile i32 9, i32* %arrayidx, align 4
175 %arrayidx2 = getelementptr inbounds %struct.ByValStruct, %struct.ByValStruct* %arg1, i32 0, i32 0, i32 0
176 store volatile i32 13, i32* %arrayidx2, align 4
177 call void @void_func_byval_struct(%struct.ByValStruct* byval nonnull align 4 %arg0, %struct.ByValStruct* byval nonnull align 4 %arg1)
178 call void @llvm.lifetime.end.p0i8(i64 32, i8* %tmp1)
179 call void @llvm.lifetime.end.p0i8(i64 32, i8* %tmp)
180 ret void
181}
182
183; GCN-LABEL: {{^}}call_void_func_byval_struct_kernel_no_frame_pointer_elim:
184define amdgpu_kernel void @call_void_func_byval_struct_kernel_no_frame_pointer_elim() #2 {
185entry:
186 %arg0 = alloca %struct.ByValStruct, align 4
187 %arg1 = alloca %struct.ByValStruct, align 4
188 %tmp = bitcast %struct.ByValStruct* %arg0 to i8*
189 call void @llvm.lifetime.start.p0i8(i64 32, i8* %tmp)
190 %tmp1 = bitcast %struct.ByValStruct* %arg1 to i8*
191 call void @llvm.lifetime.start.p0i8(i64 32, i8* %tmp1)
192 %arrayidx = getelementptr inbounds %struct.ByValStruct, %struct.ByValStruct* %arg0, i32 0, i32 0, i32 0
193 store volatile i32 9, i32* %arrayidx, align 4
194 %arrayidx2 = getelementptr inbounds %struct.ByValStruct, %struct.ByValStruct* %arg1, i32 0, i32 0, i32 0
195 store volatile i32 13, i32* %arrayidx2, align 4
196 call void @void_func_byval_struct(%struct.ByValStruct* byval nonnull align 4 %arg0, %struct.ByValStruct* byval nonnull align 4 %arg1)
197 call void @llvm.lifetime.end.p0i8(i64 32, i8* %tmp1)
198 call void @llvm.lifetime.end.p0i8(i64 32, i8* %tmp)
199 ret void
200}
201
202declare void @external_void_func_void() #0
203
204declare void @llvm.lifetime.start.p0i8(i64, i8* nocapture) #3
205declare void @llvm.lifetime.end.p0i8(i64, i8* nocapture) #3
206
207attributes #0 = { nounwind }
208attributes #1 = { noinline norecurse nounwind }
209attributes #2 = { nounwind norecurse "no-frame-pointer-elim"="true" }