• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2009 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef ART_COMPILER_UTILS_ARM_CONSTANTS_ARM_H_
18 #define ART_COMPILER_UTILS_ARM_CONSTANTS_ARM_H_
19 
20 #include <stdint.h>
21 
22 #include <iosfwd>
23 
24 #include "arch/arm/registers_arm.h"
25 #include "base/casts.h"
26 #include "base/logging.h"
27 #include "globals.h"
28 
29 namespace art {
30 namespace arm {
31 
32 // Defines constants and accessor classes to assemble, disassemble and
33 // simulate ARM instructions.
34 //
35 // Section references in the code refer to the "ARM Architecture
36 // Reference Manual ARMv7-A and ARMv7-R edition", issue C.b (24 July
37 // 2012).
38 //
39 // Constants for specific fields are defined in their respective named enums.
40 // General constants are in an anonymous enum in class Instr.
41 
42 // 4 bits option for the dmb instruction.
43 // Order and values follows those of the ARM Architecture Reference Manual.
44 enum DmbOptions {
45   SY = 0xf,
46   ST = 0xe,
47   ISH = 0xb,
48   ISHST = 0xa,
49   NSH = 0x7,
50   NSHST = 0x6
51 };
52 
53 enum ScaleFactor {
54   TIMES_1 = 0,
55   TIMES_2 = 1,
56   TIMES_4 = 2,
57   TIMES_8 = 3
58 };
59 
60 // Values for double-precision floating point registers.
61 enum DRegister {  // private marker to avoid generate-operator-out.py from processing.
62   D0  = 0,
63   D1  = 1,
64   D2  = 2,
65   D3  = 3,
66   D4  = 4,
67   D5  = 5,
68   D6  = 6,
69   D7  = 7,
70   D8  = 8,
71   D9  = 9,
72   D10 = 10,
73   D11 = 11,
74   D12 = 12,
75   D13 = 13,
76   D14 = 14,
77   D15 = 15,
78   D16 = 16,
79   D17 = 17,
80   D18 = 18,
81   D19 = 19,
82   D20 = 20,
83   D21 = 21,
84   D22 = 22,
85   D23 = 23,
86   D24 = 24,
87   D25 = 25,
88   D26 = 26,
89   D27 = 27,
90   D28 = 28,
91   D29 = 29,
92   D30 = 30,
93   D31 = 31,
94   kNumberOfDRegisters = 32,
95   kNumberOfOverlappingDRegisters = 16,
96   kNoDRegister = -1,
97 };
98 std::ostream& operator<<(std::ostream& os, const DRegister& rhs);
99 
100 
101 // Values for the condition field as defined in Table A8-1 "Condition
102 // codes" (refer to Section A8.3 "Conditional execution").
103 enum Condition {  // private marker to avoid generate-operator-out.py from processing.
104   kNoCondition = -1,
105   //           Meaning (integer)                      | Meaning (floating-point)
106   //           ---------------------------------------+-----------------------------------------
107   EQ = 0,   // Equal                                  | Equal
108   NE = 1,   // Not equal                              | Not equal, or unordered
109   CS = 2,   // Carry set                              | Greater than, equal, or unordered
110   CC = 3,   // Carry clear                            | Less than
111   MI = 4,   // Minus, negative                        | Less than
112   PL = 5,   // Plus, positive or zero                 | Greater than, equal, or unordered
113   VS = 6,   // Overflow                               | Unordered (i.e. at least one NaN operand)
114   VC = 7,   // No overflow                            | Not unordered
115   HI = 8,   // Unsigned higher                        | Greater than, or unordered
116   LS = 9,   // Unsigned lower or same                 | Less than or equal
117   GE = 10,  // Signed greater than or equal           | Greater than or equal
118   LT = 11,  // Signed less than                       | Less than, or unordered
119   GT = 12,  // Signed greater than                    | Greater than
120   LE = 13,  // Signed less than or equal              | Less than, equal, or unordered
121   AL = 14,  // Always (unconditional)                 | Always (unconditional)
122   kSpecialCondition = 15,  // Special condition (refer to Section A8.3 "Conditional execution").
123   kMaxCondition = 16,
124 
125   HS = CS,  // HS (unsigned higher or same) is a synonym for CS.
126   LO = CC   // LO (unsigned lower) is a synonym for CC.
127 };
128 std::ostream& operator<<(std::ostream& os, const Condition& rhs);
129 
130 
131 // Opcodes for Data-processing instructions (instructions with a type 0 and 1)
132 // as defined in section A3.4
133 enum Opcode {
134   kNoOperand = -1,
135   AND = 0,   // Logical AND
136   EOR = 1,   // Logical Exclusive OR
137   SUB = 2,   // Subtract
138   RSB = 3,   // Reverse Subtract
139   ADD = 4,   // Add
140   ADC = 5,   // Add with Carry
141   SBC = 6,   // Subtract with Carry
142   RSC = 7,   // Reverse Subtract with Carry
143   TST = 8,   // Test
144   TEQ = 9,   // Test Equivalence
145   CMP = 10,  // Compare
146   CMN = 11,  // Compare Negated
147   ORR = 12,  // Logical (inclusive) OR
148   MOV = 13,  // Move
149   BIC = 14,  // Bit Clear
150   MVN = 15,  // Move Not
151   ORN = 16,  // Logical OR NOT.
152   kMaxOperand = 17
153 };
154 std::ostream& operator<<(std::ostream& os, const Opcode& rhs);
155 
156 // Shifter types for Data-processing operands as defined in section A5.1.2.
157 enum Shift {
158   kNoShift = -1,
159   LSL = 0,  // Logical shift left
160   LSR = 1,  // Logical shift right
161   ASR = 2,  // Arithmetic shift right
162   ROR = 3,  // Rotate right
163   RRX = 4,  // Rotate right with extend.
164   kMaxShift
165 };
166 std::ostream& operator<<(std::ostream& os, const Shift& rhs);
167 
168 // Constants used for the decoding or encoding of the individual fields of
169 // instructions. Based on the "Figure 3-1 ARM instruction set summary".
170 enum InstructionFields {  // private marker to avoid generate-operator-out.py from processing.
171   kConditionShift = 28,
172   kConditionBits = 4,
173   kTypeShift = 25,
174   kTypeBits = 3,
175   kLinkShift = 24,
176   kLinkBits = 1,
177   kUShift = 23,
178   kUBits = 1,
179   kOpcodeShift = 21,
180   kOpcodeBits = 4,
181   kSShift = 20,
182   kSBits = 1,
183   kRnShift = 16,
184   kRnBits = 4,
185   kRdShift = 12,
186   kRdBits = 4,
187   kRsShift = 8,
188   kRsBits = 4,
189   kRmShift = 0,
190   kRmBits = 4,
191 
192   // Immediate instruction fields encoding.
193   kRotateShift = 8,
194   kRotateBits = 4,
195   kImmed8Shift = 0,
196   kImmed8Bits = 8,
197 
198   // Shift instruction register fields encodings.
199   kShiftImmShift = 7,
200   kShiftRegisterShift = 8,
201   kShiftImmBits = 5,
202   kShiftShift = 5,
203   kShiftBits = 2,
204 
205   // Load/store instruction offset field encoding.
206   kOffset12Shift = 0,
207   kOffset12Bits = 12,
208   kOffset12Mask = 0x00000fff,
209 
210   // Mul instruction register fields encodings.
211   kMulRdShift = 16,
212   kMulRdBits = 4,
213   kMulRnShift = 12,
214   kMulRnBits = 4,
215 
216   kBranchOffsetMask = 0x00ffffff
217 };
218 
219 // Size (in bytes) of registers.
220 const int kRegisterSize = 4;
221 
222 // List of registers used in load/store multiple.
223 typedef uint16_t RegList;
224 
225 // The class Instr enables access to individual fields defined in the ARM
226 // architecture instruction set encoding as described in figure A3-1.
227 //
228 // Example: Test whether the instruction at ptr does set the condition code
229 // bits.
230 //
231 // bool InstructionSetsConditionCodes(uint8_t* ptr) {
232 //   Instr* instr = Instr::At(ptr);
233 //   int type = instr->TypeField();
234 //   return ((type == 0) || (type == 1)) && instr->HasS();
235 // }
236 //
237 class Instr {
238  public:
239   enum {
240     kInstrSize = 4,
241     kInstrSizeLog2 = 2,
242     kPCReadOffset = 8
243   };
244 
IsBreakPoint()245   bool IsBreakPoint() {
246     return IsBkpt();
247   }
248 
249   // Get the raw instruction bits.
InstructionBits()250   int32_t InstructionBits() const {
251     return *reinterpret_cast<const int32_t*>(this);
252   }
253 
254   // Set the raw instruction bits to value.
SetInstructionBits(int32_t value)255   void SetInstructionBits(int32_t value) {
256     *reinterpret_cast<int32_t*>(this) = value;
257   }
258 
259   // Read one particular bit out of the instruction bits.
Bit(int nr)260   int Bit(int nr) const {
261     return (InstructionBits() >> nr) & 1;
262   }
263 
264   // Read a bit field out of the instruction bits.
Bits(int shift,int count)265   int Bits(int shift, int count) const {
266     return (InstructionBits() >> shift) & ((1 << count) - 1);
267   }
268 
269 
270   // Accessors for the different named fields used in the ARM encoding.
271   // The naming of these accessor corresponds to figure A3-1.
272   // Generally applicable fields
ConditionField()273   Condition ConditionField() const {
274     return static_cast<Condition>(Bits(kConditionShift, kConditionBits));
275   }
TypeField()276   int TypeField() const { return Bits(kTypeShift, kTypeBits); }
277 
RnField()278   Register RnField() const { return static_cast<Register>(
279                                         Bits(kRnShift, kRnBits)); }
RdField()280   Register RdField() const { return static_cast<Register>(
281                                         Bits(kRdShift, kRdBits)); }
282 
283   // Fields used in Data processing instructions
OpcodeField()284   Opcode OpcodeField() const {
285     return static_cast<Opcode>(Bits(kOpcodeShift, kOpcodeBits));
286   }
SField()287   int SField() const { return Bits(kSShift, kSBits); }
288   // with register
RmField()289   Register RmField() const {
290     return static_cast<Register>(Bits(kRmShift, kRmBits));
291   }
ShiftField()292   Shift ShiftField() const { return static_cast<Shift>(
293                                         Bits(kShiftShift, kShiftBits)); }
RegShiftField()294   int RegShiftField() const { return Bit(4); }
RsField()295   Register RsField() const {
296     return static_cast<Register>(Bits(kRsShift, kRsBits));
297   }
ShiftAmountField()298   int ShiftAmountField() const { return Bits(kShiftImmShift,
299                                                     kShiftImmBits); }
300   // with immediate
RotateField()301   int RotateField() const { return Bits(kRotateShift, kRotateBits); }
Immed8Field()302   int Immed8Field() const { return Bits(kImmed8Shift, kImmed8Bits); }
303 
304   // Fields used in Load/Store instructions
PUField()305   int PUField() const { return Bits(23, 2); }
BField()306   int  BField() const { return Bit(22); }
WField()307   int  WField() const { return Bit(21); }
LField()308   int  LField() const { return Bit(20); }
309   // with register uses same fields as Data processing instructions above
310   // with immediate
Offset12Field()311   int Offset12Field() const { return Bits(kOffset12Shift,
312                                                  kOffset12Bits); }
313   // multiple
RlistField()314   int RlistField() const { return Bits(0, 16); }
315   // extra loads and stores
SignField()316   int SignField() const { return Bit(6); }
HField()317   int HField() const { return Bit(5); }
ImmedHField()318   int ImmedHField() const { return Bits(8, 4); }
ImmedLField()319   int ImmedLField() const { return Bits(0, 4); }
320 
321   // Fields used in Branch instructions
LinkField()322   int LinkField() const { return Bits(kLinkShift, kLinkBits); }
SImmed24Field()323   int SImmed24Field() const { return ((InstructionBits() << 8) >> 8); }
324 
325   // Fields used in Supervisor Call instructions
SvcField()326   uint32_t SvcField() const { return Bits(0, 24); }
327 
328   // Field used in Breakpoint instruction
BkptField()329   uint16_t BkptField() const {
330     return ((Bits(8, 12) << 4) | Bits(0, 4));
331   }
332 
333   // Field used in 16-bit immediate move instructions
MovwField()334   uint16_t MovwField() const {
335     return ((Bits(16, 4) << 12) | Bits(0, 12));
336   }
337 
338   // Field used in VFP float immediate move instruction
ImmFloatField()339   float ImmFloatField() const {
340     uint32_t imm32 = (Bit(19) << 31) | (((1 << 5) - Bit(18)) << 25) |
341                      (Bits(16, 2) << 23) | (Bits(0, 4) << 19);
342     return bit_cast<float, uint32_t>(imm32);
343   }
344 
345   // Field used in VFP double immediate move instruction
ImmDoubleField()346   double ImmDoubleField() const {
347     uint64_t imm64 = (Bit(19)*(1LL << 63)) | (((1LL << 8) - Bit(18)) << 54) |
348                      (Bits(16, 2)*(1LL << 52)) | (Bits(0, 4)*(1LL << 48));
349     return bit_cast<double, uint64_t>(imm64);
350   }
351 
352   // Test for data processing instructions of type 0 or 1.
353   // See "ARM Architecture Reference Manual ARMv7-A and ARMv7-R edition",
354   // section A5.1 "ARM instruction set encoding".
IsDataProcessing()355   bool IsDataProcessing() const {
356     CHECK_NE(ConditionField(), kSpecialCondition);
357     CHECK_EQ(Bits(26, 2), 0);  // Type 0 or 1.
358     return ((Bits(20, 5) & 0x19) != 0x10) &&
359       ((Bit(25) == 1) ||  // Data processing immediate.
360        (Bit(4) == 0) ||  // Data processing register.
361        (Bit(7) == 0));  // Data processing register-shifted register.
362   }
363 
364   // Tests for special encodings of type 0 instructions (extra loads and stores,
365   // as well as multiplications, synchronization primitives, and miscellaneous).
366   // Can only be called for a type 0 or 1 instruction.
IsMiscellaneous()367   bool IsMiscellaneous() const {
368     CHECK_EQ(Bits(26, 2), 0);  // Type 0 or 1.
369     return ((Bit(25) == 0) && ((Bits(20, 5) & 0x19) == 0x10) && (Bit(7) == 0));
370   }
IsMultiplyOrSyncPrimitive()371   bool IsMultiplyOrSyncPrimitive() const {
372     CHECK_EQ(Bits(26, 2), 0);  // Type 0 or 1.
373     return ((Bit(25) == 0) && (Bits(4, 4) == 9));
374   }
375 
376   // Test for Supervisor Call instruction.
IsSvc()377   bool IsSvc() const {
378     return ((InstructionBits() & 0xff000000) == 0xef000000);
379   }
380 
381   // Test for Breakpoint instruction.
IsBkpt()382   bool IsBkpt() const {
383     return ((InstructionBits() & 0xfff000f0) == 0xe1200070);
384   }
385 
386   // VFP register fields.
SnField()387   SRegister SnField() const {
388     return static_cast<SRegister>((Bits(kRnShift, kRnBits) << 1) + Bit(7));
389   }
SdField()390   SRegister SdField() const {
391     return static_cast<SRegister>((Bits(kRdShift, kRdBits) << 1) + Bit(22));
392   }
SmField()393   SRegister SmField() const {
394     return static_cast<SRegister>((Bits(kRmShift, kRmBits) << 1) + Bit(5));
395   }
DnField()396   DRegister DnField() const {
397     return static_cast<DRegister>(Bits(kRnShift, kRnBits) + (Bit(7) << 4));
398   }
DdField()399   DRegister DdField() const {
400     return static_cast<DRegister>(Bits(kRdShift, kRdBits) + (Bit(22) << 4));
401   }
DmField()402   DRegister DmField() const {
403     return static_cast<DRegister>(Bits(kRmShift, kRmBits) + (Bit(5) << 4));
404   }
405 
406   // Test for VFP data processing or single transfer instructions of type 7.
IsVFPDataProcessingOrSingleTransfer()407   bool IsVFPDataProcessingOrSingleTransfer() const {
408     CHECK_NE(ConditionField(), kSpecialCondition);
409     CHECK_EQ(TypeField(), 7);
410     return ((Bit(24) == 0) && (Bits(9, 3) == 5));
411     // Bit(4) == 0: Data Processing
412     // Bit(4) == 1: 8, 16, or 32-bit Transfer between ARM Core and VFP
413   }
414 
415   // Test for VFP 64-bit transfer instructions of type 6.
IsVFPDoubleTransfer()416   bool IsVFPDoubleTransfer() const {
417     CHECK_NE(ConditionField(), kSpecialCondition);
418     CHECK_EQ(TypeField(), 6);
419     return ((Bits(21, 4) == 2) && (Bits(9, 3) == 5) &&
420             ((Bits(4, 4) & 0xd) == 1));
421   }
422 
423   // Test for VFP load and store instructions of type 6.
IsVFPLoadStore()424   bool IsVFPLoadStore() const {
425     CHECK_NE(ConditionField(), kSpecialCondition);
426     CHECK_EQ(TypeField(), 6);
427     return ((Bits(20, 5) & 0x12) == 0x10) && (Bits(9, 3) == 5);
428   }
429 
430   // Special accessors that test for existence of a value.
HasS()431   bool HasS() const { return SField() == 1; }
HasB()432   bool HasB() const { return BField() == 1; }
HasW()433   bool HasW() const { return WField() == 1; }
HasL()434   bool HasL() const { return LField() == 1; }
HasSign()435   bool HasSign() const { return SignField() == 1; }
HasH()436   bool HasH() const { return HField() == 1; }
HasLink()437   bool HasLink() const { return LinkField() == 1; }
438 
439   // Instructions are read out of a code stream. The only way to get a
440   // reference to an instruction is to convert a pointer. There is no way
441   // to allocate or create instances of class Instr.
442   // Use the At(pc) function to create references to Instr.
At(uintptr_t pc)443   static Instr* At(uintptr_t pc) { return reinterpret_cast<Instr*>(pc); }
Next()444   Instr* Next() { return this + kInstrSize; }
445 
446  private:
447   // We need to prevent the creation of instances of class Instr.
448   DISALLOW_IMPLICIT_CONSTRUCTORS(Instr);
449 };
450 
451 }  // namespace arm
452 }  // namespace art
453 
454 #endif  // ART_COMPILER_UTILS_ARM_CONSTANTS_ARM_H_
455