1 //===- subzero/src/IceRegistersARM32.h - Register information ---*- C++ -*-===//
2 //
3 //                        The Subzero Code Generator
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 /// \brief Declares the registers and their encodings for ARM32.
12 ///
13 //===----------------------------------------------------------------------===//
14 
15 #ifndef SUBZERO_SRC_ICEREGISTERSARM32_H
16 #define SUBZERO_SRC_ICEREGISTERSARM32_H
17 
18 #include "IceDefs.h"
19 #include "IceInstARM32.def"
20 #include "IceOperand.h" // RC_Target
21 #include "IceTypes.h"
22 
23 namespace Ice {
24 namespace ARM32 {
25 namespace RegARM32 {
26 
27 /// An enum of every register. The enum value may not match the encoding used
28 /// to binary encode register operands in instructions.
29 enum AllRegisters {
30 #define X(val, encode, name, cc_arg, scratch, preserved, stackptr, frameptr,   \
31           isGPR, isInt, isI64Pair, isFP32, isFP64, isVec128, alias_init)       \
32   val,
33   REGARM32_TABLE
34 #undef X
35       Reg_NUM,
36 #define X(val, init) val init,
37   REGARM32_TABLE_BOUNDS
38 #undef X
39 };
40 
41 /// An enum of GPR Registers. The enum value does match the encoding used to
42 /// binary encode register operands in instructions.
43 enum GPRRegister {
44 #define X(val, encode, name, cc_arg, scratch, preserved, stackptr, frameptr,   \
45           isGPR, isInt, isI64Pair, isFP32, isFP64, isVec128, alias_init)       \
46   Encoded_##val = encode,
47   REGARM32_GPR_TABLE
48 #undef X
49       Encoded_Not_GPR = -1
50 };
51 
52 /// An enum of FP32 S-Registers. The enum value does match the encoding used
53 /// to binary encode register operands in instructions.
54 enum SRegister {
55 #define X(val, encode, name, cc_arg, scratch, preserved, stackptr, frameptr,   \
56           isGPR, isInt, isI64Pair, isFP32, isFP64, isVec128, alias_init)       \
57   Encoded_##val = encode,
58   REGARM32_FP32_TABLE
59 #undef X
60       Encoded_Not_SReg = -1
61 };
62 
63 /// An enum of FP64 D-Registers. The enum value does match the encoding used
64 /// to binary encode register operands in instructions.
65 enum DRegister {
66 #define X(val, encode, name, cc_arg, scratch, preserved, stackptr, frameptr,   \
67           isGPR, isInt, isI64Pair, isFP32, isFP64, isVec128, alias_init)       \
68   Encoded_##val = encode,
69   REGARM32_FP64_TABLE
70 #undef X
71       Encoded_Not_DReg = -1
72 };
73 
74 /// An enum of 128-bit Q-Registers. The enum value does match the encoding
75 /// used to binary encode register operands in instructions.
76 enum QRegister {
77 #define X(val, encode, name, cc_arg, scratch, preserved, stackptr, frameptr,   \
78           isGPR, isInt, isI64Pair, isFP32, isFP64, isVec128, alias_init)       \
79   Encoded_##val = encode,
80   REGARM32_VEC128_TABLE
81 #undef X
82       Encoded_Not_QReg = -1
83 };
84 
85 extern struct RegTableType {
86   const char *Name;
87   unsigned Encoding : 10;
88   unsigned CCArg : 6;
89   unsigned Scratch : 1;
90   unsigned Preserved : 1;
91   unsigned StackPtr : 1;
92   unsigned FramePtr : 1;
93   unsigned IsGPR : 1;
94   unsigned IsInt : 1;
95   unsigned IsI64Pair : 1;
96   unsigned IsFP32 : 1;
97   unsigned IsFP64 : 1;
98   unsigned IsVec128 : 1;
99 #define NUM_ALIASES_BITS 3
100   SizeT NumAliases : (NUM_ALIASES_BITS + 1);
101   uint16_t Aliases[1 << NUM_ALIASES_BITS];
102 #undef NUM_ALIASES_BITS
103 } RegTable[Reg_NUM];
104 
assertValidRegNum(RegNumT RegNum)105 static inline void assertValidRegNum(RegNumT RegNum) {
106   (void)RegNum;
107   assert(RegNum.hasValue());
108 }
109 
isGPRegister(RegNumT RegNum)110 static inline bool isGPRegister(RegNumT RegNum) {
111   RegNum.assertIsValid();
112   return RegTable[RegNum].IsGPR;
113 }
114 
getNumGPRegs()115 static constexpr inline SizeT getNumGPRegs() {
116   return 0
117 #define X(val, encode, name, cc_arg, scratch, preserved, stackptr, frameptr,   \
118           isGPR, isInt, isI64Pair, isFP32, isFP64, isVec128, alias_init)       \
119   +(isGPR)
120       REGARM32_TABLE
121 #undef X
122       ;
123 }
124 
getEncodedGPR(RegNumT RegNum)125 static inline GPRRegister getEncodedGPR(RegNumT RegNum) {
126   RegNum.assertIsValid();
127   return GPRRegister(RegTable[RegNum].Encoding);
128 }
129 
getNumGPRs()130 static constexpr inline SizeT getNumGPRs() {
131   return 0
132 #define X(val, encode, name, cc_arg, scratch, preserved, stackptr, frameptr,   \
133           isGPR, isInt, isI64Pair, isFP32, isFP64, isVec128, alias_init)       \
134   +(isGPR)
135       REGARM32_TABLE
136 #undef X
137       ;
138 }
139 
isGPR(RegNumT RegNum)140 static inline bool isGPR(RegNumT RegNum) {
141   RegNum.assertIsValid();
142   return RegTable[RegNum].IsGPR;
143 }
144 
getI64PairFirstGPRNum(RegNumT RegNum)145 static inline GPRRegister getI64PairFirstGPRNum(RegNumT RegNum) {
146   RegNum.assertIsValid();
147   return GPRRegister(RegTable[RegNum].Encoding);
148 }
149 
getI64PairSecondGPRNum(RegNumT RegNum)150 static inline GPRRegister getI64PairSecondGPRNum(RegNumT RegNum) {
151   RegNum.assertIsValid();
152   return GPRRegister(RegTable[RegNum].Encoding + 1);
153 }
154 
isI64RegisterPair(RegNumT RegNum)155 static inline bool isI64RegisterPair(RegNumT RegNum) {
156   RegNum.assertIsValid();
157   return RegTable[RegNum].IsI64Pair;
158 }
159 
isEncodedSReg(RegNumT RegNum)160 static inline bool isEncodedSReg(RegNumT RegNum) {
161   RegNum.assertIsValid();
162   return RegTable[RegNum].IsFP32;
163 }
164 
getNumSRegs()165 static constexpr inline SizeT getNumSRegs() {
166   return 0
167 #define X(val, encode, name, cc_arg, scratch, preserved, stackptr, frameptr,   \
168           isGPR, isInt, isI64Pair, isFP32, isFP64, isVec128, alias_init)       \
169   +(isFP32)
170       REGARM32_TABLE
171 #undef X
172       ;
173 }
174 
getEncodedSReg(RegNumT RegNum)175 static inline SRegister getEncodedSReg(RegNumT RegNum) {
176   RegNum.assertIsValid();
177   return SRegister(RegTable[RegNum].Encoding);
178 }
179 
isEncodedDReg(RegNumT RegNum)180 static inline bool isEncodedDReg(RegNumT RegNum) {
181   RegNum.assertIsValid();
182   return RegTable[RegNum].IsFP64;
183 }
184 
getNumDRegs()185 static constexpr inline SizeT getNumDRegs() {
186   return 0
187 #define X(val, encode, name, cc_arg, scratch, preserved, stackptr, frameptr,   \
188           isGPR, isInt, isI64Pair, isFP32, isFP64, isVec128, alias_init)       \
189   +(isFP64)
190       REGARM32_TABLE
191 #undef X
192       ;
193 }
194 
getEncodedDReg(RegNumT RegNum)195 static inline DRegister getEncodedDReg(RegNumT RegNum) {
196   RegNum.assertIsValid();
197   return DRegister(RegTable[RegNum].Encoding);
198 }
199 
isEncodedQReg(RegNumT RegNum)200 static inline bool isEncodedQReg(RegNumT RegNum) {
201   RegNum.assertIsValid();
202   return RegTable[RegNum].IsVec128;
203 }
204 
getEncodedQReg(RegNumT RegNum)205 static inline QRegister getEncodedQReg(RegNumT RegNum) {
206   assert(isEncodedQReg(RegNum));
207   return QRegister(RegTable[RegNum].Encoding);
208 }
209 
getRegName(RegNumT RegNum)210 static inline const char *getRegName(RegNumT RegNum) {
211   RegNum.assertIsValid();
212   return RegTable[RegNum].Name;
213 }
214 
215 // Extend enum RegClass with ARM32-specific register classes.
216 enum RegClassARM32 : uint8_t {
217   RCARM32_QtoS = RC_Target, // Denotes Q registers that are aliased by S
218                             // registers.
219   RCARM32_NUM
220 };
221 
222 } // end of namespace RegARM32
223 } // end of namespace ARM32
224 } // end of namespace Ice
225 
226 #endif // SUBZERO_SRC_ICEREGISTERSARM32_H
227