blob: 2060064423e481893f3405dc2ee0d47af466a937 [file] [log] [blame]
Elliott Hughes2faa5f12012-01-30 14:42:07 -08001/*
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 */
Carl Shapiroa2e18e12011-06-21 18:57:55 -070016
Ian Rogers166db042013-07-26 12:05:57 -070017#ifndef ART_COMPILER_UTILS_ARM_CONSTANTS_ARM_H_
18#define ART_COMPILER_UTILS_ARM_CONSTANTS_ARM_H_
Carl Shapiroa2e18e12011-06-21 18:57:55 -070019
20#include <stdint.h>
Elliott Hughes07ed66b2012-12-12 18:34:25 -080021
Ian Rogersb033c752011-07-20 12:22:35 -070022#include <iosfwd>
Elliott Hughes07ed66b2012-12-12 18:34:25 -080023
Ian Rogers166db042013-07-26 12:05:57 -070024#include "arch/arm/registers_arm.h"
Elliott Hughes1aa246d2012-12-13 09:29:36 -080025#include "base/casts.h"
Elliott Hughes07ed66b2012-12-12 18:34:25 -080026#include "base/logging.h"
Brian Carlstrom578bbdc2011-07-21 14:07:47 -070027#include "globals.h"
Carl Shapiroa2e18e12011-06-21 18:57:55 -070028
29namespace art {
Ian Rogers2c8f6532011-09-02 17:16:34 -070030namespace arm {
Carl Shapiroa2e18e12011-06-21 18:57:55 -070031
32// Defines constants and accessor classes to assemble, disassemble and
33// simulate ARM instructions.
34//
Roland Levillain4fa13f62015-07-06 18:11:54 +010035// 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).
Carl Shapiroa2e18e12011-06-21 18:57:55 -070038//
39// Constants for specific fields are defined in their respective named enums.
40// General constants are in an anonymous enum in class Instr.
41
Nicolas Geoffray19a19cf2014-10-22 16:07:05 +010042// 4 bits option for the dmb instruction.
43// Order and values follows those of the ARM Architecture Reference Manual.
44enum DmbOptions {
45 SY = 0xf,
46 ST = 0xe,
47 ISH = 0xb,
48 ISHST = 0xa,
49 NSH = 0x7,
50 NSHST = 0x6
51};
Carl Shapiroa2e18e12011-06-21 18:57:55 -070052
Carl Shapiroa2e18e12011-06-21 18:57:55 -070053enum ScaleFactor {
54 TIMES_1 = 0,
55 TIMES_2 = 1,
56 TIMES_4 = 2,
57 TIMES_8 = 3
58};
59
Carl Shapiroa2e18e12011-06-21 18:57:55 -070060// Values for double-precision floating point registers.
Ian Rogers6a3c1fc2014-10-31 00:33:20 -070061enum 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,
Carl Shapiroa2e18e12011-06-21 18:57:55 -070072 D10 = 10,
73 D11 = 11,
74 D12 = 12,
75 D13 = 13,
76 D14 = 14,
77 D15 = 15,
Carl Shapiroa2e18e12011-06-21 18:57:55 -070078 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,
Carl Shapiroa2e18e12011-06-21 18:57:55 -070095 kNumberOfOverlappingDRegisters = 16,
96 kNoDRegister = -1,
97};
Elliott Hughes1f359b02011-07-17 14:27:17 -070098std::ostream& operator<<(std::ostream& os, const DRegister& rhs);
Carl Shapiroa2e18e12011-06-21 18:57:55 -070099
100
Roland Levillain4fa13f62015-07-06 18:11:54 +0100101// Values for the condition field as defined in Table A8-1 "Condition
102// codes" (refer to Section A8.3 "Conditional execution").
Ian Rogers6a3c1fc2014-10-31 00:33:20 -0700103enum Condition { // private marker to avoid generate-operator-out.py from processing.
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700104 kNoCondition = -1,
Roland Levillain4fa13f62015-07-06 18:11:54 +0100105 // 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").
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700123 kMaxCondition = 16,
Roland Levillain4fa13f62015-07-06 18:11:54 +0100124
125 HS = CS, // HS (unsigned higher or same) is a synonym for CS.
126 LO = CC // LO (unsigned lower) is a synonym for CC.
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700127};
Elliott Hughes1f359b02011-07-17 14:27:17 -0700128std::ostream& operator<<(std::ostream& os, const Condition& rhs);
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700129
130
131// Opcodes for Data-processing instructions (instructions with a type 0 and 1)
132// as defined in section A3.4
133enum Opcode {
134 kNoOperand = -1,
Ian Rogers6a3c1fc2014-10-31 00:33:20 -0700135 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
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700145 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
Vladimir Markod2b4ca22015-09-14 15:13:26 +0100151 ORN = 16, // Logical OR NOT.
152 kMaxOperand = 17
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700153};
Ian Rogers6a3c1fc2014-10-31 00:33:20 -0700154std::ostream& operator<<(std::ostream& os, const Opcode& rhs);
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700155
156// Shifter types for Data-processing operands as defined in section A5.1.2.
157enum 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
Dave Allison65fcc2c2014-04-28 13:45:27 -0700163 RRX = 4, // Rotate right with extend.
164 kMaxShift
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700165};
Ian Rogers6a3c1fc2014-10-31 00:33:20 -0700166std::ostream& operator<<(std::ostream& os, const Shift& rhs);
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700167
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700168// Constants used for the decoding or encoding of the individual fields of
169// instructions. Based on the "Figure 3-1 ARM instruction set summary".
Ian Rogers6a3c1fc2014-10-31 00:33:20 -0700170enum InstructionFields { // private marker to avoid generate-operator-out.py from processing.
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700171 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
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700219// Size (in bytes) of registers.
220const int kRegisterSize = 4;
221
222// List of registers used in load/store multiple.
223typedef uint16_t RegList;
224
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700225// 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//
Ian Rogers13735952014-10-08 12:43:28 -0700231// bool InstructionSetsConditionCodes(uint8_t* ptr) {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700232// Instr* instr = Instr::At(ptr);
233// int type = instr->TypeField();
234// return ((type == 0) || (type == 1)) && instr->HasS();
235// }
236//
237class Instr {
238 public:
239 enum {
240 kInstrSize = 4,
241 kInstrSizeLog2 = 2,
242 kPCReadOffset = 8
243 };
244
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700245 bool IsBreakPoint() {
246 return IsBkpt();
247 }
248
249 // Get the raw instruction bits.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700250 int32_t InstructionBits() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700251 return *reinterpret_cast<const int32_t*>(this);
252 }
253
254 // Set the raw instruction bits to value.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700255 void SetInstructionBits(int32_t value) {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700256 *reinterpret_cast<int32_t*>(this) = value;
257 }
258
259 // Read one particular bit out of the instruction bits.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700260 int Bit(int nr) const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700261 return (InstructionBits() >> nr) & 1;
262 }
263
264 // Read a bit field out of the instruction bits.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700265 int Bits(int shift, int count) const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700266 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
Ian Rogersdd7624d2014-03-14 17:43:00 -0700273 Condition ConditionField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700274 return static_cast<Condition>(Bits(kConditionShift, kConditionBits));
275 }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700276 int TypeField() const { return Bits(kTypeShift, kTypeBits); }
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700277
Ian Rogersdd7624d2014-03-14 17:43:00 -0700278 Register RnField() const { return static_cast<Register>(
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700279 Bits(kRnShift, kRnBits)); }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700280 Register RdField() const { return static_cast<Register>(
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700281 Bits(kRdShift, kRdBits)); }
282
283 // Fields used in Data processing instructions
Ian Rogersdd7624d2014-03-14 17:43:00 -0700284 Opcode OpcodeField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700285 return static_cast<Opcode>(Bits(kOpcodeShift, kOpcodeBits));
286 }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700287 int SField() const { return Bits(kSShift, kSBits); }
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700288 // with register
Ian Rogersdd7624d2014-03-14 17:43:00 -0700289 Register RmField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700290 return static_cast<Register>(Bits(kRmShift, kRmBits));
291 }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700292 Shift ShiftField() const { return static_cast<Shift>(
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700293 Bits(kShiftShift, kShiftBits)); }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700294 int RegShiftField() const { return Bit(4); }
295 Register RsField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700296 return static_cast<Register>(Bits(kRsShift, kRsBits));
297 }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700298 int ShiftAmountField() const { return Bits(kShiftImmShift,
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700299 kShiftImmBits); }
300 // with immediate
Ian Rogersdd7624d2014-03-14 17:43:00 -0700301 int RotateField() const { return Bits(kRotateShift, kRotateBits); }
302 int Immed8Field() const { return Bits(kImmed8Shift, kImmed8Bits); }
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700303
304 // Fields used in Load/Store instructions
Ian Rogersdd7624d2014-03-14 17:43:00 -0700305 int PUField() const { return Bits(23, 2); }
306 int BField() const { return Bit(22); }
307 int WField() const { return Bit(21); }
308 int LField() const { return Bit(20); }
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700309 // with register uses same fields as Data processing instructions above
310 // with immediate
Ian Rogersdd7624d2014-03-14 17:43:00 -0700311 int Offset12Field() const { return Bits(kOffset12Shift,
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700312 kOffset12Bits); }
313 // multiple
Ian Rogersdd7624d2014-03-14 17:43:00 -0700314 int RlistField() const { return Bits(0, 16); }
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700315 // extra loads and stores
Ian Rogersdd7624d2014-03-14 17:43:00 -0700316 int SignField() const { return Bit(6); }
317 int HField() const { return Bit(5); }
318 int ImmedHField() const { return Bits(8, 4); }
319 int ImmedLField() const { return Bits(0, 4); }
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700320
321 // Fields used in Branch instructions
Ian Rogersdd7624d2014-03-14 17:43:00 -0700322 int LinkField() const { return Bits(kLinkShift, kLinkBits); }
323 int SImmed24Field() const { return ((InstructionBits() << 8) >> 8); }
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700324
325 // Fields used in Supervisor Call instructions
Ian Rogersdd7624d2014-03-14 17:43:00 -0700326 uint32_t SvcField() const { return Bits(0, 24); }
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700327
328 // Field used in Breakpoint instruction
Ian Rogersdd7624d2014-03-14 17:43:00 -0700329 uint16_t BkptField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700330 return ((Bits(8, 12) << 4) | Bits(0, 4));
331 }
332
333 // Field used in 16-bit immediate move instructions
Ian Rogersdd7624d2014-03-14 17:43:00 -0700334 uint16_t MovwField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700335 return ((Bits(16, 4) << 12) | Bits(0, 12));
336 }
337
338 // Field used in VFP float immediate move instruction
Ian Rogersdd7624d2014-03-14 17:43:00 -0700339 float ImmFloatField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700340 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
Ian Rogersdd7624d2014-03-14 17:43:00 -0700346 double ImmDoubleField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700347 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".
Ian Rogersdd7624d2014-03-14 17:43:00 -0700355 bool IsDataProcessing() const {
Ian Rogersb033c752011-07-20 12:22:35 -0700356 CHECK_NE(ConditionField(), kSpecialCondition);
357 CHECK_EQ(Bits(26, 2), 0); // Type 0 or 1.
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700358 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.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700367 bool IsMiscellaneous() const {
Ian Rogersb033c752011-07-20 12:22:35 -0700368 CHECK_EQ(Bits(26, 2), 0); // Type 0 or 1.
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700369 return ((Bit(25) == 0) && ((Bits(20, 5) & 0x19) == 0x10) && (Bit(7) == 0));
370 }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700371 bool IsMultiplyOrSyncPrimitive() const {
Ian Rogersb033c752011-07-20 12:22:35 -0700372 CHECK_EQ(Bits(26, 2), 0); // Type 0 or 1.
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700373 return ((Bit(25) == 0) && (Bits(4, 4) == 9));
374 }
375
376 // Test for Supervisor Call instruction.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700377 bool IsSvc() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700378 return ((InstructionBits() & 0xff000000) == 0xef000000);
379 }
380
381 // Test for Breakpoint instruction.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700382 bool IsBkpt() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700383 return ((InstructionBits() & 0xfff000f0) == 0xe1200070);
384 }
385
386 // VFP register fields.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700387 SRegister SnField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700388 return static_cast<SRegister>((Bits(kRnShift, kRnBits) << 1) + Bit(7));
389 }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700390 SRegister SdField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700391 return static_cast<SRegister>((Bits(kRdShift, kRdBits) << 1) + Bit(22));
392 }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700393 SRegister SmField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700394 return static_cast<SRegister>((Bits(kRmShift, kRmBits) << 1) + Bit(5));
395 }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700396 DRegister DnField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700397 return static_cast<DRegister>(Bits(kRnShift, kRnBits) + (Bit(7) << 4));
398 }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700399 DRegister DdField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700400 return static_cast<DRegister>(Bits(kRdShift, kRdBits) + (Bit(22) << 4));
401 }
Ian Rogersdd7624d2014-03-14 17:43:00 -0700402 DRegister DmField() const {
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700403 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.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700407 bool IsVFPDataProcessingOrSingleTransfer() const {
Ian Rogersb033c752011-07-20 12:22:35 -0700408 CHECK_NE(ConditionField(), kSpecialCondition);
409 CHECK_EQ(TypeField(), 7);
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700410 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.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700416 bool IsVFPDoubleTransfer() const {
Ian Rogersb033c752011-07-20 12:22:35 -0700417 CHECK_NE(ConditionField(), kSpecialCondition);
418 CHECK_EQ(TypeField(), 6);
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700419 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.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700424 bool IsVFPLoadStore() const {
Ian Rogersb033c752011-07-20 12:22:35 -0700425 CHECK_NE(ConditionField(), kSpecialCondition);
426 CHECK_EQ(TypeField(), 6);
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700427 return ((Bits(20, 5) & 0x12) == 0x10) && (Bits(9, 3) == 5);
428 }
429
430 // Special accessors that test for existence of a value.
Ian Rogersdd7624d2014-03-14 17:43:00 -0700431 bool HasS() const { return SField() == 1; }
432 bool HasB() const { return BField() == 1; }
433 bool HasW() const { return WField() == 1; }
434 bool HasL() const { return LField() == 1; }
435 bool HasSign() const { return SignField() == 1; }
436 bool HasH() const { return HField() == 1; }
437 bool HasLink() const { return LinkField() == 1; }
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700438
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.
Ian Rogers13735952014-10-08 12:43:28 -0700443 static Instr* At(uintptr_t pc) { return reinterpret_cast<Instr*>(pc); }
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700444 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
Ian Rogers2c8f6532011-09-02 17:16:34 -0700451} // namespace arm
Carl Shapiroa2e18e12011-06-21 18:57:55 -0700452} // namespace art
453
Ian Rogers166db042013-07-26 12:05:57 -0700454#endif // ART_COMPILER_UTILS_ARM_CONSTANTS_ARM_H_