]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/llvm/lib/Target/AMDGPU/AMDGPUArgumentUsageInfo.h
Merge clang 7.0.1 and several follow-up changes
[FreeBSD/FreeBSD.git] / contrib / llvm / lib / Target / AMDGPU / AMDGPUArgumentUsageInfo.h
1 //==- AMDGPUArgumentrUsageInfo.h - Function Arg Usage Info -------*- 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 #ifndef LLVM_LIB_TARGET_AMDGPU_AMDGPUARGUMENTUSAGEINFO_H
11 #define LLVM_LIB_TARGET_AMDGPU_AMDGPUARGUMENTUSAGEINFO_H
12
13 #include "llvm/ADT/DenseMap.h"
14 #include "llvm/IR/Function.h"
15 #include "llvm/Pass.h"
16
17 namespace llvm {
18
19 class Function;
20 class raw_ostream;
21 class GCNSubtarget;
22 class TargetMachine;
23 class TargetRegisterClass;
24 class TargetRegisterInfo;
25
26 struct ArgDescriptor {
27 private:
28   friend struct AMDGPUFunctionArgInfo;
29   friend class AMDGPUArgumentUsageInfo;
30
31   union {
32     unsigned Register;
33     unsigned StackOffset;
34   };
35
36   bool IsStack : 1;
37   bool IsSet : 1;
38
39   ArgDescriptor(unsigned Val = 0, bool IsStack = false, bool IsSet = false)
40     : Register(Val), IsStack(IsStack), IsSet(IsSet) {}
41 public:
42   static ArgDescriptor createRegister(unsigned Reg) {
43     return ArgDescriptor(Reg, false, true);
44   }
45
46   static ArgDescriptor createStack(unsigned Reg) {
47     return ArgDescriptor(Reg, true, true);
48   }
49
50   bool isSet() const {
51     return IsSet;
52   }
53
54   explicit operator bool() const {
55     return isSet();
56   }
57
58   bool isRegister() const {
59     return !IsStack;
60   }
61
62   unsigned getRegister() const {
63     assert(!IsStack);
64     return Register;
65   }
66
67   unsigned getStackOffset() const {
68     assert(IsStack);
69     return StackOffset;
70   }
71
72   void print(raw_ostream &OS, const TargetRegisterInfo *TRI = nullptr) const;
73 };
74
75 inline raw_ostream &operator<<(raw_ostream &OS, const ArgDescriptor &Arg) {
76   Arg.print(OS);
77   return OS;
78 }
79
80 struct AMDGPUFunctionArgInfo {
81   enum PreloadedValue {
82     // SGPRS:
83     PRIVATE_SEGMENT_BUFFER = 0,
84     DISPATCH_PTR        =  1,
85     QUEUE_PTR           =  2,
86     KERNARG_SEGMENT_PTR =  3,
87     DISPATCH_ID         =  4,
88     FLAT_SCRATCH_INIT   =  5,
89     WORKGROUP_ID_X      = 10,
90     WORKGROUP_ID_Y      = 11,
91     WORKGROUP_ID_Z      = 12,
92     PRIVATE_SEGMENT_WAVE_BYTE_OFFSET = 14,
93     IMPLICIT_BUFFER_PTR = 15,
94     IMPLICIT_ARG_PTR = 16,
95
96     // VGPRS:
97     WORKITEM_ID_X       = 17,
98     WORKITEM_ID_Y       = 18,
99     WORKITEM_ID_Z       = 19,
100     FIRST_VGPR_VALUE    = WORKITEM_ID_X
101   };
102
103   // Kernel input registers setup for the HSA ABI in allocation order.
104
105   // User SGPRs in kernels
106   // XXX - Can these require argument spills?
107   ArgDescriptor PrivateSegmentBuffer;
108   ArgDescriptor DispatchPtr;
109   ArgDescriptor QueuePtr;
110   ArgDescriptor KernargSegmentPtr;
111   ArgDescriptor DispatchID;
112   ArgDescriptor FlatScratchInit;
113   ArgDescriptor PrivateSegmentSize;
114
115   // System SGPRs in kernels.
116   ArgDescriptor WorkGroupIDX;
117   ArgDescriptor WorkGroupIDY;
118   ArgDescriptor WorkGroupIDZ;
119   ArgDescriptor WorkGroupInfo;
120   ArgDescriptor PrivateSegmentWaveByteOffset;
121
122   // Pointer with offset from kernargsegmentptr to where special ABI arguments
123   // are passed to callable functions.
124   ArgDescriptor ImplicitArgPtr;
125
126   // Input registers for non-HSA ABI
127   ArgDescriptor ImplicitBufferPtr = 0;
128
129   // VGPRs inputs. These are always v0, v1 and v2 for entry functions.
130   ArgDescriptor WorkItemIDX;
131   ArgDescriptor WorkItemIDY;
132   ArgDescriptor WorkItemIDZ;
133
134   std::pair<const ArgDescriptor *, const TargetRegisterClass *>
135   getPreloadedValue(PreloadedValue Value) const;
136 };
137
138 class AMDGPUArgumentUsageInfo : public ImmutablePass {
139 private:
140   static const AMDGPUFunctionArgInfo ExternFunctionInfo;
141   DenseMap<const Function *, AMDGPUFunctionArgInfo> ArgInfoMap;
142
143 public:
144   static char ID;
145
146   AMDGPUArgumentUsageInfo() : ImmutablePass(ID) { }
147
148   void getAnalysisUsage(AnalysisUsage &AU) const override {
149     AU.setPreservesAll();
150   }
151
152   bool doInitialization(Module &M) override;
153   bool doFinalization(Module &M) override;
154
155   void print(raw_ostream &OS, const Module *M = nullptr) const override;
156
157   void setFuncArgInfo(const Function &F, const AMDGPUFunctionArgInfo &ArgInfo) {
158     ArgInfoMap[&F] = ArgInfo;
159   }
160
161   const AMDGPUFunctionArgInfo &lookupFuncArgInfo(const Function &F) const {
162     auto I = ArgInfoMap.find(&F);
163     if (I == ArgInfoMap.end()) {
164       assert(F.isDeclaration());
165       return ExternFunctionInfo;
166     }
167
168     return I->second;
169   }
170 };
171
172 } // end namespace llvm
173
174 #endif