blob: 90795ea99a85c1eb3a8f90d4732cf1343b5e70b1 [file] [log] [blame]
Che-Liang Chiou3278c422010-11-08 03:00:52 +00001//===- PTXMachineFuctionInfo.h - PTX machine function 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// This file declares PTX-specific per-machine-function information.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef PTX_MACHINE_FUNCTION_INFO_H
15#define PTX_MACHINE_FUNCTION_INFO_H
16
17#include "PTX.h"
Justin Holewinski27f08fc2011-09-23 14:18:22 +000018#include "PTXParamManager.h"
Justin Holewinski297984d2011-09-22 16:45:40 +000019#include "PTXRegisterInfo.h"
20#include "llvm/ADT/DenseMap.h"
Justin Holewinskie0aef2d2011-06-16 17:50:00 +000021#include "llvm/ADT/DenseSet.h"
Justin Holewinski297984d2011-09-22 16:45:40 +000022#include "llvm/ADT/StringExtras.h"
Che-Liang Chiou3278c422010-11-08 03:00:52 +000023#include "llvm/CodeGen/MachineFunction.h"
Justin Holewinski5422a0f2011-09-22 16:45:46 +000024#include "llvm/Support/Debug.h"
25#include "llvm/Support/raw_ostream.h"
Che-Liang Chiou3278c422010-11-08 03:00:52 +000026
27namespace llvm {
Justin Holewinski5422a0f2011-09-22 16:45:46 +000028
Che-Liang Chiou3278c422010-11-08 03:00:52 +000029/// PTXMachineFunctionInfo - This class is derived from MachineFunction and
30/// contains private PTX target-specific information for each MachineFunction.
31///
32class PTXMachineFunctionInfo : public MachineFunctionInfo {
33private:
34 bool is_kernel;
Justin Holewinski5422a0f2011-09-22 16:45:46 +000035 DenseSet<unsigned> reg_local_var;
36 DenseSet<unsigned> reg_arg;
37 DenseSet<unsigned> reg_ret;
Justin Holewinski4bdd4ed2011-08-09 17:36:31 +000038 std::vector<unsigned> call_params;
Che-Liang Chiou3278c422010-11-08 03:00:52 +000039 bool _isDoneAddArg;
40
Justin Holewinski297984d2011-09-22 16:45:40 +000041 typedef std::vector<unsigned> RegisterList;
42 typedef DenseMap<const TargetRegisterClass*, RegisterList> RegisterMap;
43 typedef DenseMap<unsigned, std::string> RegisterNameMap;
44
45 RegisterMap usedRegs;
46 RegisterNameMap regNames;
47
Justin Holewinski5422a0f2011-09-22 16:45:46 +000048 SmallVector<unsigned, 8> argParams;
49
50 unsigned retParamSize;
51
Justin Holewinski27f08fc2011-09-23 14:18:22 +000052 PTXParamManager ParamManager;
53
Che-Liang Chiou3278c422010-11-08 03:00:52 +000054public:
55 PTXMachineFunctionInfo(MachineFunction &MF)
56 : is_kernel(false), reg_ret(PTX::NoRegister), _isDoneAddArg(false) {
Justin Holewinski297984d2011-09-22 16:45:40 +000057 usedRegs[PTX::RegPredRegisterClass] = RegisterList();
58 usedRegs[PTX::RegI16RegisterClass] = RegisterList();
59 usedRegs[PTX::RegI32RegisterClass] = RegisterList();
60 usedRegs[PTX::RegI64RegisterClass] = RegisterList();
61 usedRegs[PTX::RegF32RegisterClass] = RegisterList();
62 usedRegs[PTX::RegF64RegisterClass] = RegisterList();
Justin Holewinski5422a0f2011-09-22 16:45:46 +000063
64 retParamSize = 0;
Che-Liang Chiou3278c422010-11-08 03:00:52 +000065 }
66
Justin Holewinski27f08fc2011-09-23 14:18:22 +000067 PTXParamManager& getParamManager() { return ParamManager; }
68 const PTXParamManager& getParamManager() const { return ParamManager; }
69
Che-Liang Chiou3278c422010-11-08 03:00:52 +000070 void setKernel(bool _is_kernel=true) { is_kernel = _is_kernel; }
71
Justin Holewinski5422a0f2011-09-22 16:45:46 +000072
73 void addLocalVarReg(unsigned reg) { reg_local_var.insert(reg); }
74
Che-Liang Chiou3278c422010-11-08 03:00:52 +000075
76 void doneAddArg(void) {
Che-Liang Chiou3278c422010-11-08 03:00:52 +000077 _isDoneAddArg = true;
78 }
Che-Liang Chiou5efde182011-04-21 10:56:58 +000079 void doneAddLocalVar(void) {}
Che-Liang Chiou3278c422010-11-08 03:00:52 +000080
Che-Liang Chiou3278c422010-11-08 03:00:52 +000081 bool isKernel() const { return is_kernel; }
82
Justin Holewinski5422a0f2011-09-22 16:45:46 +000083 typedef DenseSet<unsigned>::const_iterator reg_iterator;
84 //typedef DenseSet<unsigned>::const_reverse_iterator reg_reverse_iterator;
85 typedef DenseSet<unsigned>::const_iterator ret_iterator;
Justin Holewinski4bdd4ed2011-08-09 17:36:31 +000086 typedef std::vector<unsigned>::const_iterator param_iterator;
Justin Holewinski5422a0f2011-09-22 16:45:46 +000087 typedef SmallVector<unsigned, 8>::const_iterator argparam_iterator;
Che-Liang Chiou3278c422010-11-08 03:00:52 +000088
Che-Liang Chiouf48817c2011-03-02 07:36:48 +000089 bool argRegEmpty() const { return reg_arg.empty(); }
90 int getNumArg() const { return reg_arg.size(); }
Che-Liang Chiou3278c422010-11-08 03:00:52 +000091 reg_iterator argRegBegin() const { return reg_arg.begin(); }
92 reg_iterator argRegEnd() const { return reg_arg.end(); }
Justin Holewinski5422a0f2011-09-22 16:45:46 +000093 argparam_iterator argParamBegin() const { return argParams.begin(); }
94 argparam_iterator argParamEnd() const { return argParams.end(); }
95 //reg_reverse_iterator argRegReverseBegin() const { return reg_arg.rbegin(); }
96 //reg_reverse_iterator argRegReverseEnd() const { return reg_arg.rend(); }
Che-Liang Chiou3278c422010-11-08 03:00:52 +000097
Che-Liang Chiouf48817c2011-03-02 07:36:48 +000098 bool localVarRegEmpty() const { return reg_local_var.empty(); }
Che-Liang Chiou3278c422010-11-08 03:00:52 +000099 reg_iterator localVarRegBegin() const { return reg_local_var.begin(); }
100 reg_iterator localVarRegEnd() const { return reg_local_var.end(); }
101
Justin Holewinskie0aef2d2011-06-16 17:50:00 +0000102 bool retRegEmpty() const { return reg_ret.empty(); }
103 int getNumRet() const { return reg_ret.size(); }
104 ret_iterator retRegBegin() const { return reg_ret.begin(); }
105 ret_iterator retRegEnd() const { return reg_ret.end(); }
Che-Liang Chiou3278c422010-11-08 03:00:52 +0000106
Justin Holewinski4bdd4ed2011-08-09 17:36:31 +0000107 param_iterator paramBegin() const { return call_params.begin(); }
108 param_iterator paramEnd() const { return call_params.end(); }
109 unsigned getNextParam(unsigned size) {
110 call_params.push_back(size);
111 return call_params.size()-1;
112 }
113
Che-Liang Chiou3278c422010-11-08 03:00:52 +0000114 bool isArgReg(unsigned reg) const {
Che-Liang Chiou4a17cad2011-04-21 10:16:20 +0000115 return std::find(reg_arg.begin(), reg_arg.end(), reg) != reg_arg.end();
Che-Liang Chiou3278c422010-11-08 03:00:52 +0000116 }
117
Justin Holewinski5422a0f2011-09-22 16:45:46 +0000118 /*bool isRetReg(unsigned reg) const {
Justin Holewinskie0aef2d2011-06-16 17:50:00 +0000119 return std::find(reg_ret.begin(), reg_ret.end(), reg) != reg_ret.end();
Justin Holewinski5422a0f2011-09-22 16:45:46 +0000120 }*/
Justin Holewinskie0aef2d2011-06-16 17:50:00 +0000121
Che-Liang Chiou3278c422010-11-08 03:00:52 +0000122 bool isLocalVarReg(unsigned reg) const {
Che-Liang Chiou4a17cad2011-04-21 10:16:20 +0000123 return std::find(reg_local_var.begin(), reg_local_var.end(), reg)
124 != reg_local_var.end();
Che-Liang Chiou3278c422010-11-08 03:00:52 +0000125 }
Justin Holewinski297984d2011-09-22 16:45:40 +0000126
Justin Holewinski5422a0f2011-09-22 16:45:46 +0000127 void addRetReg(unsigned Reg) {
128 if (!reg_ret.count(Reg)) {
129 reg_ret.insert(Reg);
130 std::string name;
131 name = "%ret";
132 name += utostr(reg_ret.size() - 1);
133 regNames[Reg] = name;
134 }
135 }
Justin Holewinski297984d2011-09-22 16:45:40 +0000136
Justin Holewinski5422a0f2011-09-22 16:45:46 +0000137 void setRetParamSize(unsigned SizeInBits) {
138 retParamSize = SizeInBits;
139 }
140
141 unsigned getRetParamSize() const {
142 return retParamSize;
143 }
144
145 void addArgReg(unsigned Reg) {
146 reg_arg.insert(Reg);
147 std::string name;
148 name = "%param";
149 name += utostr(reg_arg.size() - 1);
150 regNames[Reg] = name;
151 }
152
153 void addArgParam(unsigned SizeInBits) {
154 argParams.push_back(SizeInBits);
155 }
156
157 void addVirtualRegister(const TargetRegisterClass *TRC, unsigned Reg) {
Justin Holewinski297984d2011-09-22 16:45:40 +0000158 std::string name;
159
Justin Holewinski5422a0f2011-09-22 16:45:46 +0000160 if (!reg_ret.count(Reg) && !reg_arg.count(Reg)) {
161 usedRegs[TRC].push_back(Reg);
162 if (TRC == PTX::RegPredRegisterClass)
163 name = "%p";
164 else if (TRC == PTX::RegI16RegisterClass)
165 name = "%rh";
166 else if (TRC == PTX::RegI32RegisterClass)
167 name = "%r";
168 else if (TRC == PTX::RegI64RegisterClass)
169 name = "%rd";
170 else if (TRC == PTX::RegF32RegisterClass)
171 name = "%f";
172 else if (TRC == PTX::RegF64RegisterClass)
173 name = "%fd";
174 else
175 llvm_unreachable("Invalid register class");
Justin Holewinski297984d2011-09-22 16:45:40 +0000176
Justin Holewinski5422a0f2011-09-22 16:45:46 +0000177 name += utostr(usedRegs[TRC].size() - 1);
178 regNames[Reg] = name;
179 }
Justin Holewinski297984d2011-09-22 16:45:40 +0000180 }
181
182 std::string getRegisterName(unsigned Reg) const {
183 if (regNames.count(Reg))
184 return regNames.lookup(Reg);
Justin Holewinski5422a0f2011-09-22 16:45:46 +0000185 else if (Reg == PTX::NoRegister)
186 return "%noreg";
Justin Holewinski297984d2011-09-22 16:45:40 +0000187 else
188 llvm_unreachable("Register not in register name map");
189 }
190
191 unsigned getNumRegistersForClass(const TargetRegisterClass *TRC) const {
192 return usedRegs.lookup(TRC).size();
193 }
194
Che-Liang Chiou3278c422010-11-08 03:00:52 +0000195}; // class PTXMachineFunctionInfo
196} // namespace llvm
197
198#endif // PTX_MACHINE_FUNCTION_INFO_H