blob: 0ad25f0cae4d4ec37a5109b41afdfb3f8884010a [file] [log] [blame]
Tom Stellard75aadc22012-12-11 21:25:42 +00001//===- SIMachineFunctionInfo.h - SIMachineFunctionInfo interface -*- C++ -*-==//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10/// \file
11//
12//===----------------------------------------------------------------------===//
13
Matt Arsenault6b6a2c32016-03-11 08:00:27 +000014#ifndef LLVM_LIB_TARGET_AMDGPU_SIMACHINEFUNCTIONINFO_H
15#define LLVM_LIB_TARGET_AMDGPU_SIMACHINEFUNCTIONINFO_H
Tom Stellard75aadc22012-12-11 21:25:42 +000016
Vincent Lejeuneace6f732013-04-01 21:47:53 +000017#include "AMDGPUMachineFunction.h"
Tom Stellard96468902014-09-24 01:33:17 +000018#include "SIRegisterInfo.h"
Tom Stellardc149dc02013-11-27 21:23:35 +000019#include <map>
Tom Stellard75aadc22012-12-11 21:25:42 +000020
21namespace llvm {
22
Tom Stellardc149dc02013-11-27 21:23:35 +000023class MachineRegisterInfo;
24
Tom Stellard75aadc22012-12-11 21:25:42 +000025/// This class keeps track of the SPI_SP_INPUT_ADDR config register, which
26/// tells the hardware which interpolation parameters to load.
Matt Arsenault6b6a2c32016-03-11 08:00:27 +000027class SIMachineFunctionInfo final : public AMDGPUMachineFunction {
Matt Arsenault26f8f3d2015-11-30 21:16:03 +000028 // FIXME: This should be removed and getPreloadedValue moved here.
29 friend struct SIRegisterInfo;
Craig Topper5656db42014-04-29 07:57:24 +000030 void anchor() override;
Tom Stellard96468902014-09-24 01:33:17 +000031
32 unsigned TIDReg;
Matt Arsenault26f8f3d2015-11-30 21:16:03 +000033
34 // Registers that may be reserved for spilling purposes. These may be the same
35 // as the input registers.
Matt Arsenault49affb82015-11-25 20:55:12 +000036 unsigned ScratchRSrcReg;
Matt Arsenault26f8f3d2015-11-30 21:16:03 +000037 unsigned ScratchWaveOffsetReg;
38
39 // Input registers setup for the HSA ABI.
40 // User SGPRs in allocation order.
41 unsigned PrivateSegmentBufferUserSGPR;
42 unsigned DispatchPtrUserSGPR;
43 unsigned QueuePtrUserSGPR;
44 unsigned KernargSegmentPtrUserSGPR;
45 unsigned DispatchIDUserSGPR;
46 unsigned FlatScratchInitUserSGPR;
47 unsigned PrivateSegmentSizeUserSGPR;
48 unsigned GridWorkGroupCountXUserSGPR;
49 unsigned GridWorkGroupCountYUserSGPR;
50 unsigned GridWorkGroupCountZUserSGPR;
51
52 // System SGPRs in allocation order.
53 unsigned WorkGroupIDXSystemSGPR;
54 unsigned WorkGroupIDYSystemSGPR;
55 unsigned WorkGroupIDZSystemSGPR;
56 unsigned WorkGroupInfoSystemSGPR;
57 unsigned PrivateSegmentWaveByteOffsetSystemSGPR;
Matt Arsenault49affb82015-11-25 20:55:12 +000058
Marek Olsakfccabaf2016-01-13 11:45:36 +000059 // Graphics info.
60 unsigned PSInputAddr;
Marek Olsak8e9cc632016-01-13 17:23:09 +000061 bool ReturnsVoid;
Marek Olsakfccabaf2016-01-13 11:45:36 +000062
Tom Stellard79a1fd72016-04-14 16:27:07 +000063 unsigned MaximumWorkGroupSize;
64
Konstantin Zhuravlyov29ddd2b2016-05-24 18:37:18 +000065 // Number of reserved VGPRs for debugger usage.
66 unsigned DebuggerReservedVGPRCount;
Konstantin Zhuravlyovf2f3d142016-06-25 03:11:28 +000067 // Stack object indices for work group IDs.
68 int DebuggerWorkGroupIDStackObjectIndices[3];
69 // Stack object indices for work item IDs.
70 int DebuggerWorkItemIDStackObjectIndices[3];
Konstantin Zhuravlyov71515e52016-04-26 17:24:40 +000071
Matt Arsenault49affb82015-11-25 20:55:12 +000072public:
73 // FIXME: Make private
74 unsigned LDSWaveSpillSize;
Marek Olsakfccabaf2016-01-13 11:45:36 +000075 unsigned PSInputEna;
Matt Arsenault49affb82015-11-25 20:55:12 +000076 std::map<unsigned, unsigned> LaneVGPRs;
77 unsigned ScratchOffsetReg;
78 unsigned NumUserSGPRs;
Matt Arsenault26f8f3d2015-11-30 21:16:03 +000079 unsigned NumSystemSGPRs;
Matt Arsenault49affb82015-11-25 20:55:12 +000080
81private:
Matt Arsenault5b22dfa2015-11-05 05:27:10 +000082 bool HasSpilledSGPRs;
Tom Stellard42fb60e2015-01-14 15:42:31 +000083 bool HasSpilledVGPRs;
Matt Arsenault296b8492016-02-12 06:31:30 +000084 bool HasNonSpillStackObjects;
85 bool HasFlatInstructions;
Tom Stellard96468902014-09-24 01:33:17 +000086
Matt Arsenault26f8f3d2015-11-30 21:16:03 +000087 // Feature bits required for inputs passed in user SGPRs.
88 bool PrivateSegmentBuffer : 1;
Matt Arsenault49affb82015-11-25 20:55:12 +000089 bool DispatchPtr : 1;
90 bool QueuePtr : 1;
91 bool DispatchID : 1;
92 bool KernargSegmentPtr : 1;
93 bool FlatScratchInit : 1;
94 bool GridWorkgroupCountX : 1;
95 bool GridWorkgroupCountY : 1;
96 bool GridWorkgroupCountZ : 1;
Tom Stellardc149dc02013-11-27 21:23:35 +000097
Matt Arsenault26f8f3d2015-11-30 21:16:03 +000098 // Feature bits required for inputs passed in system SGPRs.
Matt Arsenault49affb82015-11-25 20:55:12 +000099 bool WorkGroupIDX : 1; // Always initialized.
100 bool WorkGroupIDY : 1;
101 bool WorkGroupIDZ : 1;
102 bool WorkGroupInfo : 1;
Matt Arsenault26f8f3d2015-11-30 21:16:03 +0000103 bool PrivateSegmentWaveByteOffset : 1;
Matt Arsenault49affb82015-11-25 20:55:12 +0000104
105 bool WorkItemIDX : 1; // Always initialized.
106 bool WorkItemIDY : 1;
107 bool WorkItemIDZ : 1;
108
Matt Arsenault26f8f3d2015-11-30 21:16:03 +0000109
110 MCPhysReg getNextUserSGPR() const {
111 assert(NumSystemSGPRs == 0 && "System SGPRs must be added after user SGPRs");
112 return AMDGPU::SGPR0 + NumUserSGPRs;
113 }
114
115 MCPhysReg getNextSystemSGPR() const {
116 return AMDGPU::SGPR0 + NumUserSGPRs + NumSystemSGPRs;
117 }
118
Matt Arsenault49affb82015-11-25 20:55:12 +0000119public:
Tom Stellardc149dc02013-11-27 21:23:35 +0000120 struct SpilledReg {
121 unsigned VGPR;
122 int Lane;
123 SpilledReg(unsigned R, int L) : VGPR (R), Lane (L) { }
Tom Stellard649b5db2016-03-04 18:31:18 +0000124 SpilledReg() : VGPR(AMDGPU::NoRegister), Lane(-1) { }
Tom Stellardc149dc02013-11-27 21:23:35 +0000125 bool hasLane() { return Lane != -1;}
Tom Stellard649b5db2016-03-04 18:31:18 +0000126 bool hasReg() { return VGPR != AMDGPU::NoRegister;}
Tom Stellardc149dc02013-11-27 21:23:35 +0000127 };
128
Tom Stellardc149dc02013-11-27 21:23:35 +0000129 // SIMachineFunctionInfo definition
130
Tom Stellard75aadc22012-12-11 21:25:42 +0000131 SIMachineFunctionInfo(const MachineFunction &MF);
Tom Stellardc5cf2f02014-08-21 20:40:54 +0000132 SpilledReg getSpilledReg(MachineFunction *MF, unsigned FrameIndex,
133 unsigned SubIdx);
Tom Stellard96468902014-09-24 01:33:17 +0000134 bool hasCalculatedTID() const { return TIDReg != AMDGPU::NoRegister; };
135 unsigned getTIDReg() const { return TIDReg; };
136 void setTIDReg(unsigned Reg) { TIDReg = Reg; }
Matt Arsenault5b22dfa2015-11-05 05:27:10 +0000137
Matt Arsenault26f8f3d2015-11-30 21:16:03 +0000138 // Add user SGPRs.
139 unsigned addPrivateSegmentBuffer(const SIRegisterInfo &TRI);
140 unsigned addDispatchPtr(const SIRegisterInfo &TRI);
141 unsigned addQueuePtr(const SIRegisterInfo &TRI);
142 unsigned addKernargSegmentPtr(const SIRegisterInfo &TRI);
Matt Arsenault296b8492016-02-12 06:31:30 +0000143 unsigned addFlatScratchInit(const SIRegisterInfo &TRI);
Matt Arsenault26f8f3d2015-11-30 21:16:03 +0000144
145 // Add system SGPRs.
146 unsigned addWorkGroupIDX() {
147 WorkGroupIDXSystemSGPR = getNextSystemSGPR();
148 NumSystemSGPRs += 1;
149 return WorkGroupIDXSystemSGPR;
150 }
151
152 unsigned addWorkGroupIDY() {
153 WorkGroupIDYSystemSGPR = getNextSystemSGPR();
154 NumSystemSGPRs += 1;
155 return WorkGroupIDYSystemSGPR;
156 }
157
158 unsigned addWorkGroupIDZ() {
159 WorkGroupIDZSystemSGPR = getNextSystemSGPR();
160 NumSystemSGPRs += 1;
161 return WorkGroupIDZSystemSGPR;
162 }
163
164 unsigned addWorkGroupInfo() {
165 WorkGroupInfoSystemSGPR = getNextSystemSGPR();
166 NumSystemSGPRs += 1;
167 return WorkGroupInfoSystemSGPR;
168 }
169
170 unsigned addPrivateSegmentWaveByteOffset() {
171 PrivateSegmentWaveByteOffsetSystemSGPR = getNextSystemSGPR();
172 NumSystemSGPRs += 1;
173 return PrivateSegmentWaveByteOffsetSystemSGPR;
174 }
175
Tom Stellardf110f8f2016-04-14 16:27:03 +0000176 void setPrivateSegmentWaveByteOffset(unsigned Reg) {
177 PrivateSegmentWaveByteOffsetSystemSGPR = Reg;
178 }
179
Matt Arsenault26f8f3d2015-11-30 21:16:03 +0000180 bool hasPrivateSegmentBuffer() const {
181 return PrivateSegmentBuffer;
182 }
183
Matt Arsenault49affb82015-11-25 20:55:12 +0000184 bool hasDispatchPtr() const {
185 return DispatchPtr;
186 }
187
188 bool hasQueuePtr() const {
189 return QueuePtr;
190 }
191
192 bool hasDispatchID() const {
193 return DispatchID;
194 }
195
196 bool hasKernargSegmentPtr() const {
197 return KernargSegmentPtr;
198 }
199
200 bool hasFlatScratchInit() const {
201 return FlatScratchInit;
202 }
203
204 bool hasGridWorkgroupCountX() const {
205 return GridWorkgroupCountX;
206 }
207
208 bool hasGridWorkgroupCountY() const {
209 return GridWorkgroupCountY;
210 }
211
212 bool hasGridWorkgroupCountZ() const {
213 return GridWorkgroupCountZ;
214 }
215
216 bool hasWorkGroupIDX() const {
217 return WorkGroupIDX;
218 }
219
220 bool hasWorkGroupIDY() const {
221 return WorkGroupIDY;
222 }
223
224 bool hasWorkGroupIDZ() const {
225 return WorkGroupIDZ;
226 }
227
228 bool hasWorkGroupInfo() const {
229 return WorkGroupInfo;
230 }
231
Matt Arsenault26f8f3d2015-11-30 21:16:03 +0000232 bool hasPrivateSegmentWaveByteOffset() const {
233 return PrivateSegmentWaveByteOffset;
234 }
235
Matt Arsenault49affb82015-11-25 20:55:12 +0000236 bool hasWorkItemIDX() const {
237 return WorkItemIDX;
238 }
239
240 bool hasWorkItemIDY() const {
241 return WorkItemIDY;
242 }
243
244 bool hasWorkItemIDZ() const {
245 return WorkItemIDZ;
246 }
247
Matt Arsenault26f8f3d2015-11-30 21:16:03 +0000248 unsigned getNumUserSGPRs() const {
249 return NumUserSGPRs;
250 }
251
252 unsigned getNumPreloadedSGPRs() const {
253 return NumUserSGPRs + NumSystemSGPRs;
254 }
255
256 unsigned getPrivateSegmentWaveByteOffsetSystemSGPR() const {
257 return PrivateSegmentWaveByteOffsetSystemSGPR;
258 }
259
Matt Arsenault49affb82015-11-25 20:55:12 +0000260 /// \brief Returns the physical register reserved for use as the resource
261 /// descriptor for scratch accesses.
262 unsigned getScratchRSrcReg() const {
263 return ScratchRSrcReg;
264 }
265
Matt Arsenault26f8f3d2015-11-30 21:16:03 +0000266 void setScratchRSrcReg(unsigned Reg) {
267 assert(Reg != AMDGPU::NoRegister && "Should never be unset");
268 ScratchRSrcReg = Reg;
269 }
270
271 unsigned getScratchWaveOffsetReg() const {
272 return ScratchWaveOffsetReg;
273 }
274
275 void setScratchWaveOffsetReg(unsigned Reg) {
276 assert(Reg != AMDGPU::NoRegister && "Should never be unset");
277 ScratchWaveOffsetReg = Reg;
278 }
Matt Arsenault49affb82015-11-25 20:55:12 +0000279
Matt Arsenault99c14522016-04-25 19:27:24 +0000280 unsigned getQueuePtrUserSGPR() const {
281 return QueuePtrUserSGPR;
282 }
283
Matt Arsenault5b22dfa2015-11-05 05:27:10 +0000284 bool hasSpilledSGPRs() const {
285 return HasSpilledSGPRs;
286 }
287
288 void setHasSpilledSGPRs(bool Spill = true) {
289 HasSpilledSGPRs = Spill;
290 }
291
292 bool hasSpilledVGPRs() const {
293 return HasSpilledVGPRs;
294 }
295
296 void setHasSpilledVGPRs(bool Spill = true) {
297 HasSpilledVGPRs = Spill;
298 }
Tom Stellard96468902014-09-24 01:33:17 +0000299
Matt Arsenault296b8492016-02-12 06:31:30 +0000300 bool hasNonSpillStackObjects() const {
301 return HasNonSpillStackObjects;
302 }
303
304 void setHasNonSpillStackObjects(bool StackObject = true) {
305 HasNonSpillStackObjects = StackObject;
306 }
307
308 bool hasFlatInstructions() const {
309 return HasFlatInstructions;
310 }
311
312 void setHasFlatInstructions(bool UseFlat = true) {
313 HasFlatInstructions = UseFlat;
314 }
315
Marek Olsakfccabaf2016-01-13 11:45:36 +0000316 unsigned getPSInputAddr() const {
317 return PSInputAddr;
318 }
319
320 bool isPSInputAllocated(unsigned Index) const {
321 return PSInputAddr & (1 << Index);
322 }
323
324 void markPSInputAllocated(unsigned Index) {
325 PSInputAddr |= 1 << Index;
326 }
327
Marek Olsak8e9cc632016-01-13 17:23:09 +0000328 bool returnsVoid() const {
329 return ReturnsVoid;
330 }
331
332 void setIfReturnsVoid(bool Value) {
333 ReturnsVoid = Value;
334 }
335
Konstantin Zhuravlyov29ddd2b2016-05-24 18:37:18 +0000336 /// \returns Number of reserved VGPRs for debugger usage.
337 unsigned getDebuggerReservedVGPRCount() const {
338 return DebuggerReservedVGPRCount;
Konstantin Zhuravlyov71515e52016-04-26 17:24:40 +0000339 }
340
Konstantin Zhuravlyovf2f3d142016-06-25 03:11:28 +0000341 /// \returns Stack object index for \p Dim's work group ID.
342 int getDebuggerWorkGroupIDStackObjectIndex(unsigned Dim) const {
343 assert(Dim < 3);
344 return DebuggerWorkGroupIDStackObjectIndices[Dim];
345 }
346
347 /// \brief Sets stack object index for \p Dim's work group ID to \p ObjectIdx.
348 void setDebuggerWorkGroupIDStackObjectIndex(unsigned Dim, int ObjectIdx) {
349 assert(Dim < 3);
350 DebuggerWorkGroupIDStackObjectIndices[Dim] = ObjectIdx;
351 }
352
353 /// \returns Stack object index for \p Dim's work item ID.
354 int getDebuggerWorkItemIDStackObjectIndex(unsigned Dim) const {
355 assert(Dim < 3);
356 return DebuggerWorkItemIDStackObjectIndices[Dim];
357 }
358
359 /// \brief Sets stack object index for \p Dim's work item ID to \p ObjectIdx.
360 void setDebuggerWorkItemIDStackObjectIndex(unsigned Dim, int ObjectIdx) {
361 assert(Dim < 3);
362 DebuggerWorkItemIDStackObjectIndices[Dim] = ObjectIdx;
363 }
364
365 /// \returns SGPR used for \p Dim's work group ID.
366 unsigned getWorkGroupIDSGPR(unsigned Dim) const {
367 switch (Dim) {
368 case 0:
369 assert(hasWorkGroupIDX());
370 return WorkGroupIDXSystemSGPR;
371 case 1:
372 assert(hasWorkGroupIDY());
373 return WorkGroupIDYSystemSGPR;
374 case 2:
375 assert(hasWorkGroupIDZ());
376 return WorkGroupIDZSystemSGPR;
377 }
378 llvm_unreachable("unexpected dimension");
379 }
380
381 /// \returns VGPR used for \p Dim' work item ID.
382 unsigned getWorkItemIDVGPR(unsigned Dim) const {
383 switch (Dim) {
384 case 0:
385 assert(hasWorkItemIDX());
386 return AMDGPU::VGPR0;
387 case 1:
388 assert(hasWorkItemIDY());
389 return AMDGPU::VGPR1;
390 case 2:
391 assert(hasWorkItemIDZ());
392 return AMDGPU::VGPR2;
393 }
394 llvm_unreachable("unexpected dimension");
395 }
396
Tom Stellard96468902014-09-24 01:33:17 +0000397 unsigned getMaximumWorkGroupSize(const MachineFunction &MF) const;
Tom Stellard75aadc22012-12-11 21:25:42 +0000398};
399
400} // End namespace llvm
401
Benjamin Kramera7c40ef2014-08-13 16:26:38 +0000402#endif