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