Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(169)

Side by Side Diff: runtime/vm/constants_arm.h

Issue 2481873005: clang-format runtime/vm (Closed)
Patch Set: Merge Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « runtime/vm/constant_propagator.cc ('k') | runtime/vm/constants_arm64.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #ifndef RUNTIME_VM_CONSTANTS_ARM_H_ 5 #ifndef RUNTIME_VM_CONSTANTS_ARM_H_
6 #define RUNTIME_VM_CONSTANTS_ARM_H_ 6 #define RUNTIME_VM_CONSTANTS_ARM_H_
7 7
8 #include "platform/globals.h" 8 #include "platform/globals.h"
9 #include "platform/assert.h" 9 #include "platform/assert.h"
10 10
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
54 // R12: Volatile 54 // R12: Volatile
55 // R13: Stack pointer 55 // R13: Stack pointer
56 // R14: Link register 56 // R14: Link register
57 // R15: Program counter 57 // R15: Program counter
58 // Stack alignment: 4 bytes always, 4 bytes at public interfaces 58 // Stack alignment: 4 bytes always, 4 bytes at public interfaces
59 59
60 // iOS passes floating point arguments in registers (hardfp) 60 // iOS passes floating point arguments in registers (hardfp)
61 61
62 62
63 enum Register { 63 enum Register {
64 R0 = 0, 64 R0 = 0,
65 R1 = 1, 65 R1 = 1,
66 R2 = 2, 66 R2 = 2,
67 R3 = 3, 67 R3 = 3,
68 R4 = 4, 68 R4 = 4,
69 R5 = 5, // PP 69 R5 = 5, // PP
70 R6 = 6, // CTX 70 R6 = 6, // CTX
71 R7 = 7, // iOS FP 71 R7 = 7, // iOS FP
72 R8 = 8, 72 R8 = 8,
73 R9 = 9, 73 R9 = 9,
74 R10 = 10, // THR 74 R10 = 10, // THR
75 R11 = 11, // Linux FP 75 R11 = 11, // Linux FP
76 R12 = 12, // IP aka TMP 76 R12 = 12, // IP aka TMP
77 R13 = 13, // SP 77 R13 = 13, // SP
78 R14 = 14, // LR 78 R14 = 14, // LR
79 R15 = 15, // PC 79 R15 = 15, // PC
80 kNumberOfCpuRegisters = 16, 80 kNumberOfCpuRegisters = 16,
81 kNoRegister = -1, // Signals an illegal register. 81 kNoRegister = -1, // Signals an illegal register.
82 82
83 // Aliases. 83 // Aliases.
84 #if defined(TARGET_ABI_IOS) 84 #if defined(TARGET_ABI_IOS)
85 FP = R7, 85 FP = R7,
86 NOTFP = R11, 86 NOTFP = R11,
87 #elif defined(TARGET_ABI_EABI) 87 #elif defined(TARGET_ABI_EABI)
88 FP = R11, 88 FP = R11,
89 NOTFP = R7, 89 NOTFP = R7,
90 #else 90 #else
91 #error Unknown ABI 91 #error Unknown ABI
92 #endif 92 #endif
93 IP = R12, 93 IP = R12,
94 SP = R13, 94 SP = R13,
95 LR = R14, 95 LR = R14,
96 PC = R15, 96 PC = R15,
97 }; 97 };
98 98
99 99
100 // Values for single-precision floating point registers. 100 // Values for single-precision floating point registers.
101 enum SRegister { 101 enum SRegister {
102 kNoSRegister = -1, 102 kNoSRegister = -1,
103 S0 = 0, 103 S0 = 0,
104 S1 = 1, 104 S1 = 1,
105 S2 = 2, 105 S2 = 2,
106 S3 = 3, 106 S3 = 3,
107 S4 = 4, 107 S4 = 4,
108 S5 = 5, 108 S5 = 5,
109 S6 = 6, 109 S6 = 6,
110 S7 = 7, 110 S7 = 7,
111 S8 = 8, 111 S8 = 8,
112 S9 = 9, 112 S9 = 9,
113 S10 = 10, 113 S10 = 10,
114 S11 = 11, 114 S11 = 11,
115 S12 = 12, 115 S12 = 12,
116 S13 = 13, 116 S13 = 13,
117 S14 = 14, 117 S14 = 14,
118 S15 = 15, 118 S15 = 15,
119 S16 = 16, 119 S16 = 16,
120 S17 = 17, 120 S17 = 17,
121 S18 = 18, 121 S18 = 18,
122 S19 = 19, 122 S19 = 19,
123 S20 = 20, 123 S20 = 20,
124 S21 = 21, 124 S21 = 21,
125 S22 = 22, 125 S22 = 22,
126 S23 = 23, 126 S23 = 23,
127 S24 = 24, 127 S24 = 24,
128 S25 = 25, 128 S25 = 25,
129 S26 = 26, 129 S26 = 26,
130 S27 = 27, 130 S27 = 27,
131 S28 = 28, 131 S28 = 28,
132 S29 = 29, 132 S29 = 29,
133 S30 = 30, 133 S30 = 30,
134 S31 = 31, 134 S31 = 31,
135 kNumberOfSRegisters = 32, 135 kNumberOfSRegisters = 32,
136 }; 136 };
137 137
138 138
139 // Values for double-precision floating point registers. 139 // Values for double-precision floating point registers.
140 enum DRegister { 140 enum DRegister {
141 kNoDRegister = -1, 141 kNoDRegister = -1,
142 D0 = 0, 142 D0 = 0,
143 D1 = 1, 143 D1 = 1,
144 D2 = 2, 144 D2 = 2,
145 D3 = 3, 145 D3 = 3,
146 D4 = 4, 146 D4 = 4,
147 D5 = 5, 147 D5 = 5,
148 D6 = 6, 148 D6 = 6,
149 D7 = 7, 149 D7 = 7,
150 D8 = 8, 150 D8 = 8,
151 D9 = 9, 151 D9 = 9,
152 D10 = 10, 152 D10 = 10,
153 D11 = 11, 153 D11 = 11,
154 D12 = 12, 154 D12 = 12,
155 D13 = 13, 155 D13 = 13,
156 D14 = 14, 156 D14 = 14,
157 D15 = 15, 157 D15 = 15,
158 #if defined(VFPv3_D16) 158 #if defined(VFPv3_D16)
159 kNumberOfDRegisters = 16, 159 kNumberOfDRegisters = 16,
160 // Leaving these defined, but marking them as kNoDRegister to avoid polluting 160 // Leaving these defined, but marking them as kNoDRegister to avoid polluting
161 // other parts of the code with #ifdef's. Instead, query kNumberOfDRegisters 161 // other parts of the code with #ifdef's. Instead, query kNumberOfDRegisters
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
194 D30 = 30, 194 D30 = 30,
195 D31 = 31, 195 D31 = 31,
196 kNumberOfDRegisters = 32, 196 kNumberOfDRegisters = 32,
197 #endif 197 #endif
198 kNumberOfOverlappingDRegisters = 16, 198 kNumberOfOverlappingDRegisters = 16,
199 }; 199 };
200 200
201 201
202 enum QRegister { 202 enum QRegister {
203 kNoQRegister = -1, 203 kNoQRegister = -1,
204 Q0 = 0, 204 Q0 = 0,
205 Q1 = 1, 205 Q1 = 1,
206 Q2 = 2, 206 Q2 = 2,
207 Q3 = 3, 207 Q3 = 3,
208 Q4 = 4, 208 Q4 = 4,
209 Q5 = 5, 209 Q5 = 5,
210 Q6 = 6, 210 Q6 = 6,
211 Q7 = 7, 211 Q7 = 7,
212 #if defined(VFPv3_D16) 212 #if defined(VFPv3_D16)
213 kNumberOfQRegisters = 8, 213 kNumberOfQRegisters = 8,
214 Q8 = kNoQRegister, 214 Q8 = kNoQRegister,
215 Q9 = kNoQRegister, 215 Q9 = kNoQRegister,
216 Q10 = kNoQRegister, 216 Q10 = kNoQRegister,
217 Q11 = kNoQRegister, 217 Q11 = kNoQRegister,
218 Q12 = kNoQRegister, 218 Q12 = kNoQRegister,
219 Q13 = kNoQRegister, 219 Q13 = kNoQRegister,
220 Q14 = kNoQRegister, 220 Q14 = kNoQRegister,
221 Q15 = kNoQRegister, 221 Q15 = kNoQRegister,
222 #else 222 #else
223 Q8 = 8, 223 Q8 = 8,
224 Q9 = 9, 224 Q9 = 9,
225 Q10 = 10, 225 Q10 = 10,
226 Q11 = 11, 226 Q11 = 11,
227 Q12 = 12, 227 Q12 = 12,
228 Q13 = 13, 228 Q13 = 13,
229 Q14 = 14, 229 Q14 = 14,
230 Q15 = 15, 230 Q15 = 15,
231 kNumberOfQRegisters = 16, 231 kNumberOfQRegisters = 16,
232 #endif 232 #endif
233 }; 233 };
234 234
(...skipping 18 matching lines...) Expand all
253 253
254 static inline SRegister OddSRegisterOf(DRegister d) { 254 static inline SRegister OddSRegisterOf(DRegister d) {
255 #if defined(VFPv3_D32) 255 #if defined(VFPv3_D32)
256 ASSERT(d < D16); 256 ASSERT(d < D16);
257 #endif 257 #endif
258 return static_cast<SRegister>((d * 2) + 1); 258 return static_cast<SRegister>((d * 2) + 1);
259 } 259 }
260 260
261 261
262 // Register aliases for floating point scratch registers. 262 // Register aliases for floating point scratch registers.
263 const QRegister QTMP = Q7; // Overlaps with DTMP, STMP. 263 const QRegister QTMP = Q7; // Overlaps with DTMP, STMP.
264 const DRegister DTMP = EvenDRegisterOf(QTMP); // Overlaps with STMP. 264 const DRegister DTMP = EvenDRegisterOf(QTMP); // Overlaps with STMP.
265 const SRegister STMP = EvenSRegisterOf(DTMP); 265 const SRegister STMP = EvenSRegisterOf(DTMP);
266 266
267 // Architecture independent aliases. 267 // Architecture independent aliases.
268 typedef QRegister FpuRegister; 268 typedef QRegister FpuRegister;
269 269
270 const FpuRegister FpuTMP = QTMP; 270 const FpuRegister FpuTMP = QTMP;
271 const int kNumberOfFpuRegisters = kNumberOfQRegisters; 271 const int kNumberOfFpuRegisters = kNumberOfQRegisters;
272 const FpuRegister kNoFpuRegister = kNoQRegister; 272 const FpuRegister kNoFpuRegister = kNoQRegister;
273 273
274 // Register aliases. 274 // Register aliases.
275 const Register TMP = IP; // Used as scratch register by assembler. 275 const Register TMP = IP; // Used as scratch register by assembler.
276 const Register TMP2 = kNoRegister; // There is no second assembler temporary. 276 const Register TMP2 = kNoRegister; // There is no second assembler temporary.
277 const Register CTX = R6; // Location of current context at method entry. 277 const Register CTX = R6; // Location of current context at method entry.
278 const Register PP = R5; // Caches object pool pointer in generated code. 278 const Register PP = R5; // Caches object pool pointer in generated code.
279 const Register SPREG = SP; // Stack pointer register. 279 const Register SPREG = SP; // Stack pointer register.
280 const Register FPREG = FP; // Frame pointer register. 280 const Register FPREG = FP; // Frame pointer register.
281 const Register LRREG = LR; // Link register. 281 const Register LRREG = LR; // Link register.
282 const Register ICREG = R9; // IC data register. 282 const Register ICREG = R9; // IC data register.
283 const Register ARGS_DESC_REG = R4; 283 const Register ARGS_DESC_REG = R4;
284 const Register CODE_REG = R6; 284 const Register CODE_REG = R6;
285 const Register THR = R10; // Caches current thread in generated code. 285 const Register THR = R10; // Caches current thread in generated code.
286 const Register CALLEE_SAVED_TEMP = R8; 286 const Register CALLEE_SAVED_TEMP = R8;
287 287
288 // R15 encodes APSR in the vmrs instruction. 288 // R15 encodes APSR in the vmrs instruction.
(...skipping 11 matching lines...) Expand all
300 // List of registers used in load/store multiple. 300 // List of registers used in load/store multiple.
301 typedef uint16_t RegList; 301 typedef uint16_t RegList;
302 const RegList kAllCpuRegistersList = 0xFFFF; 302 const RegList kAllCpuRegistersList = 0xFFFF;
303 303
304 304
305 // C++ ABI call registers. 305 // C++ ABI call registers.
306 const RegList kAbiArgumentCpuRegs = 306 const RegList kAbiArgumentCpuRegs =
307 (1 << R0) | (1 << R1) | (1 << R2) | (1 << R3); 307 (1 << R0) | (1 << R1) | (1 << R2) | (1 << R3);
308 #if defined(TARGET_ABI_IOS) 308 #if defined(TARGET_ABI_IOS)
309 const RegList kAbiPreservedCpuRegs = 309 const RegList kAbiPreservedCpuRegs =
310 (1 << R4) | (1 << R5) | (1 << R6) | (1 << R8) | 310 (1 << R4) | (1 << R5) | (1 << R6) | (1 << R8) | (1 << R10) | (1 << R11);
311 (1 << R10) | (1 << R11);
312 const int kAbiPreservedCpuRegCount = 6; 311 const int kAbiPreservedCpuRegCount = 6;
313 #elif defined(TARGET_ABI_EABI) 312 #elif defined(TARGET_ABI_EABI)
314 const RegList kAbiPreservedCpuRegs = 313 const RegList kAbiPreservedCpuRegs = (1 << R4) | (1 << R5) | (1 << R6) |
315 (1 << R4) | (1 << R5) | (1 << R6) | (1 << R7) | 314 (1 << R7) | (1 << R8) | (1 << R9) |
316 (1 << R8) | (1 << R9) | (1 << R10); 315 (1 << R10);
317 const int kAbiPreservedCpuRegCount = 7; 316 const int kAbiPreservedCpuRegCount = 7;
318 #else 317 #else
319 #error Unknown ABI 318 #error Unknown ABI
320 #endif 319 #endif
321 const QRegister kAbiFirstPreservedFpuReg = Q4; 320 const QRegister kAbiFirstPreservedFpuReg = Q4;
322 const QRegister kAbiLastPreservedFpuReg = Q7; 321 const QRegister kAbiLastPreservedFpuReg = Q7;
323 const int kAbiPreservedFpuRegCount = 4; 322 const int kAbiPreservedFpuRegCount = 4;
324 323
325 const RegList kReservedCpuRegisters = 324 const RegList kReservedCpuRegisters = (1 << SPREG) | (1 << FPREG) | (1 << TMP) |
326 (1 << SPREG) | 325 (1 << PP) | (1 << THR) | (1 << PC);
327 (1 << FPREG) |
328 (1 << TMP) |
329 (1 << PP) |
330 (1 << THR) |
331 (1 << PC);
332 // CPU registers available to Dart allocator. 326 // CPU registers available to Dart allocator.
333 const RegList kDartAvailableCpuRegs = 327 const RegList kDartAvailableCpuRegs =
334 kAllCpuRegistersList & ~kReservedCpuRegisters; 328 kAllCpuRegistersList & ~kReservedCpuRegisters;
335 // Registers available to Dart that are not preserved by runtime calls. 329 // Registers available to Dart that are not preserved by runtime calls.
336 const RegList kDartVolatileCpuRegs = 330 const RegList kDartVolatileCpuRegs =
337 kDartAvailableCpuRegs & ~kAbiPreservedCpuRegs; 331 kDartAvailableCpuRegs & ~kAbiPreservedCpuRegs;
338 #if defined(TARGET_ABI_IOS) 332 #if defined(TARGET_ABI_IOS)
339 const int kDartVolatileCpuRegCount = 6; 333 const int kDartVolatileCpuRegCount = 6;
340 #elif defined(TARGET_ABI_EABI) 334 #elif defined(TARGET_ABI_EABI)
341 const int kDartVolatileCpuRegCount = 5; 335 const int kDartVolatileCpuRegCount = 5;
342 #endif 336 #endif
343 const QRegister kDartFirstVolatileFpuReg = Q0; 337 const QRegister kDartFirstVolatileFpuReg = Q0;
344 const QRegister kDartLastVolatileFpuReg = Q3; 338 const QRegister kDartLastVolatileFpuReg = Q3;
345 const int kDartVolatileFpuRegCount = 4; 339 const int kDartVolatileFpuRegCount = 4;
346 340
347 341
348 // Values for the condition field as defined in section A3.2. 342 // Values for the condition field as defined in section A3.2.
349 enum Condition { 343 enum Condition {
350 kNoCondition = -1, 344 kNoCondition = -1,
351 EQ = 0, // equal 345 EQ = 0, // equal
352 NE = 1, // not equal 346 NE = 1, // not equal
353 CS = 2, // carry set/unsigned higher or same 347 CS = 2, // carry set/unsigned higher or same
354 CC = 3, // carry clear/unsigned lower 348 CC = 3, // carry clear/unsigned lower
355 MI = 4, // minus/negative 349 MI = 4, // minus/negative
356 PL = 5, // plus/positive or zero 350 PL = 5, // plus/positive or zero
357 VS = 6, // overflow 351 VS = 6, // overflow
358 VC = 7, // no overflow 352 VC = 7, // no overflow
359 HI = 8, // unsigned higher 353 HI = 8, // unsigned higher
360 LS = 9, // unsigned lower or same 354 LS = 9, // unsigned lower or same
361 GE = 10, // signed greater than or equal 355 GE = 10, // signed greater than or equal
362 LT = 11, // signed less than 356 LT = 11, // signed less than
363 GT = 12, // signed greater than 357 GT = 12, // signed greater than
364 LE = 13, // signed less than or equal 358 LE = 13, // signed less than or equal
365 AL = 14, // always (unconditional) 359 AL = 14, // always (unconditional)
366 kSpecialCondition = 15, // special condition (refer to section A3.2.1) 360 kSpecialCondition = 15, // special condition (refer to section A3.2.1)
367 kMaxCondition = 16, 361 kMaxCondition = 16,
368 }; 362 };
369 363
370 364
371 // Opcodes for Data-processing instructions (instructions with a type 0 and 1) 365 // Opcodes for Data-processing instructions (instructions with a type 0 and 1)
372 // as defined in section A3.4 366 // as defined in section A3.4
373 enum Opcode { 367 enum Opcode {
374 kNoOperand = -1, 368 kNoOperand = -1,
375 AND = 0, // Logical AND 369 AND = 0, // Logical AND
376 EOR = 1, // Logical Exclusive OR 370 EOR = 1, // Logical Exclusive OR
377 SUB = 2, // Subtract 371 SUB = 2, // Subtract
378 RSB = 3, // Reverse Subtract 372 RSB = 3, // Reverse Subtract
379 ADD = 4, // Add 373 ADD = 4, // Add
380 ADC = 5, // Add with Carry 374 ADC = 5, // Add with Carry
381 SBC = 6, // Subtract with Carry 375 SBC = 6, // Subtract with Carry
382 RSC = 7, // Reverse Subtract with Carry 376 RSC = 7, // Reverse Subtract with Carry
383 TST = 8, // Test 377 TST = 8, // Test
384 TEQ = 9, // Test Equivalence 378 TEQ = 9, // Test Equivalence
385 CMP = 10, // Compare 379 CMP = 10, // Compare
386 CMN = 11, // Compare Negated 380 CMN = 11, // Compare Negated
387 ORR = 12, // Logical (inclusive) OR 381 ORR = 12, // Logical (inclusive) OR
388 MOV = 13, // Move 382 MOV = 13, // Move
389 BIC = 14, // Bit Clear 383 BIC = 14, // Bit Clear
390 MVN = 15, // Move Not 384 MVN = 15, // Move Not
391 kMaxOperand = 16 385 kMaxOperand = 16
392 }; 386 };
393 387
394 388
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after
488 // Example: Test whether the instruction at ptr sets the condition code bits. 482 // Example: Test whether the instruction at ptr sets the condition code bits.
489 // 483 //
490 // bool InstructionSetsConditionCodes(byte* ptr) { 484 // bool InstructionSetsConditionCodes(byte* ptr) {
491 // Instr* instr = Instr::At(ptr); 485 // Instr* instr = Instr::At(ptr);
492 // int type = instr->TypeField(); 486 // int type = instr->TypeField();
493 // return ((type == 0) || (type == 1)) && instr->HasS(); 487 // return ((type == 0) || (type == 1)) && instr->HasS();
494 // } 488 // }
495 // 489 //
496 class Instr { 490 class Instr {
497 public: 491 public:
498 enum { 492 enum { kInstrSize = 4, kInstrSizeLog2 = 2, kPCReadOffset = 8 };
499 kInstrSize = 4,
500 kInstrSizeLog2 = 2,
501 kPCReadOffset = 8
502 };
503 493
504 static const int32_t kNopInstruction = // nop 494 static const int32_t kNopInstruction = // nop
505 ((AL << kConditionShift) | (0x32 << 20) | (0xf << 12)); 495 ((AL << kConditionShift) | (0x32 << 20) | (0xf << 12));
506 496
507 static const int32_t kBreakPointCode = 0xdeb0; // For breakpoint. 497 static const int32_t kBreakPointCode = 0xdeb0; // For breakpoint.
508 static const int32_t kStopMessageCode = 0xdeb1; // For Stop(message). 498 static const int32_t kStopMessageCode = 0xdeb1; // For Stop(message).
509 static const int32_t kSimulatorBreakCode = 0xdeb2; // For breakpoint in sim. 499 static const int32_t kSimulatorBreakCode = 0xdeb2; // For breakpoint in sim.
510 static const int32_t kSimulatorRedirectCode = 0xca11; // For redirection. 500 static const int32_t kSimulatorRedirectCode = 0xca11; // For redirection.
511 501
512 // Breakpoint instruction filling assembler code buffers in debug mode. 502 // Breakpoint instruction filling assembler code buffers in debug mode.
513 static const int32_t kBreakPointInstruction = // bkpt(0xdeb0) 503 static const int32_t kBreakPointInstruction = // bkpt(0xdeb0)
514 ((AL << kConditionShift) | (0x12 << 20) | (0xdeb << 8) | (0x7 << 4)); 504 ((AL << kConditionShift) | (0x12 << 20) | (0xdeb << 8) | (0x7 << 4));
515 505
516 // Breakpoint instruction used by the simulator. 506 // Breakpoint instruction used by the simulator.
517 // Should be distinct from kBreakPointInstruction and from a typical user 507 // Should be distinct from kBreakPointInstruction and from a typical user
518 // breakpoint inserted in generated code for debugging, e.g. bkpt(0). 508 // breakpoint inserted in generated code for debugging, e.g. bkpt(0).
519 static const int32_t kSimulatorBreakpointInstruction = 509 static const int32_t kSimulatorBreakpointInstruction =
520 // svc #kBreakpointSvcCode 510 // svc #kBreakpointSvcCode
521 ((AL << kConditionShift) | (0xf << 24) | kSimulatorBreakCode); 511 ((AL << kConditionShift) | (0xf << 24) | kSimulatorBreakCode);
522 512
523 // Runtime call redirection instruction used by the simulator. 513 // Runtime call redirection instruction used by the simulator.
524 static const int32_t kSimulatorRedirectInstruction = 514 static const int32_t kSimulatorRedirectInstruction =
525 ((AL << kConditionShift) | (0xf << 24) | kSimulatorRedirectCode); 515 ((AL << kConditionShift) | (0xf << 24) | kSimulatorRedirectCode);
526 516
527 // Get the raw instruction bits. 517 // Get the raw instruction bits.
528 inline int32_t InstructionBits() const { 518 inline int32_t InstructionBits() const {
529 return *reinterpret_cast<const int32_t*>(this); 519 return *reinterpret_cast<const int32_t*>(this);
530 } 520 }
531 521
532 // Set the raw instruction bits to value. 522 // Set the raw instruction bits to value.
533 inline void SetInstructionBits(int32_t value) { 523 inline void SetInstructionBits(int32_t value) {
534 *reinterpret_cast<int32_t*>(this) = value; 524 *reinterpret_cast<int32_t*>(this) = value;
535 } 525 }
536 526
537 // Read one particular bit out of the instruction bits. 527 // Read one particular bit out of the instruction bits.
538 inline int Bit(int nr) const { 528 inline int Bit(int nr) const { return (InstructionBits() >> nr) & 1; }
539 return (InstructionBits() >> nr) & 1;
540 }
541 529
542 // Read a bit field out of the instruction bits. 530 // Read a bit field out of the instruction bits.
543 inline int Bits(int shift, int count) const { 531 inline int Bits(int shift, int count) const {
544 return (InstructionBits() >> shift) & ((1 << count) - 1); 532 return (InstructionBits() >> shift) & ((1 << count) - 1);
545 } 533 }
546 534
547 535
548 // Accessors for the different named fields used in the ARM encoding. 536 // Accessors for the different named fields used in the ARM encoding.
549 // The naming of these accessor corresponds to figure A3-1. 537 // The naming of these accessor corresponds to figure A3-1.
550 // Generally applicable fields 538 // Generally applicable fields
551 inline Condition ConditionField() const { 539 inline Condition ConditionField() const {
552 return static_cast<Condition>(Bits(kConditionShift, kConditionBits)); 540 return static_cast<Condition>(Bits(kConditionShift, kConditionBits));
553 } 541 }
554 inline int TypeField() const { return Bits(kTypeShift, kTypeBits); } 542 inline int TypeField() const { return Bits(kTypeShift, kTypeBits); }
555 543
556 inline Register RnField() const { return static_cast<Register>( 544 inline Register RnField() const {
557 Bits(kRnShift, kRnBits)); } 545 return static_cast<Register>(Bits(kRnShift, kRnBits));
558 inline Register RdField() const { return static_cast<Register>( 546 }
559 Bits(kRdShift, kRdBits)); } 547 inline Register RdField() const {
548 return static_cast<Register>(Bits(kRdShift, kRdBits));
549 }
560 550
561 // Fields used in Data processing instructions 551 // Fields used in Data processing instructions
562 inline Opcode OpcodeField() const { 552 inline Opcode OpcodeField() const {
563 return static_cast<Opcode>(Bits(kOpcodeShift, kOpcodeBits)); 553 return static_cast<Opcode>(Bits(kOpcodeShift, kOpcodeBits));
564 } 554 }
565 inline int SField() const { return Bits(kSShift, kSBits); } 555 inline int SField() const { return Bits(kSShift, kSBits); }
566 // with register 556 // with register
567 inline Register RmField() const { 557 inline Register RmField() const {
568 return static_cast<Register>(Bits(kRmShift, kRmBits)); 558 return static_cast<Register>(Bits(kRmShift, kRmBits));
569 } 559 }
570 inline Shift ShiftField() const { return static_cast<Shift>( 560 inline Shift ShiftField() const {
571 Bits(kShiftShift, kShiftBits)); } 561 return static_cast<Shift>(Bits(kShiftShift, kShiftBits));
562 }
572 inline int RegShiftField() const { return Bit(4); } 563 inline int RegShiftField() const { return Bit(4); }
573 inline Register RsField() const { 564 inline Register RsField() const {
574 return static_cast<Register>(Bits(kRsShift, kRsBits)); 565 return static_cast<Register>(Bits(kRsShift, kRsBits));
575 } 566 }
576 inline int ShiftAmountField() const { return Bits(kShiftImmShift, 567 inline int ShiftAmountField() const {
577 kShiftImmBits); } 568 return Bits(kShiftImmShift, kShiftImmBits);
569 }
578 // with immediate 570 // with immediate
579 inline int RotateField() const { return Bits(kRotateShift, kRotateBits); } 571 inline int RotateField() const { return Bits(kRotateShift, kRotateBits); }
580 inline int Immed8Field() const { return Bits(kImmed8Shift, kImmed8Bits); } 572 inline int Immed8Field() const { return Bits(kImmed8Shift, kImmed8Bits); }
581 573
582 // Fields used in Load/Store instructions 574 // Fields used in Load/Store instructions
583 inline int PUField() const { return Bits(23, 2); } 575 inline int PUField() const { return Bits(23, 2); }
584 inline int BField() const { return Bit(22); } 576 inline int BField() const { return Bit(22); }
585 inline int WField() const { return Bit(21); } 577 inline int WField() const { return Bit(21); }
586 inline int LField() const { return Bit(20); } 578 inline int LField() const { return Bit(20); }
587 // with register uses same fields as Data processing instructions above 579 // with register uses same fields as Data processing instructions above
588 // with immediate 580 // with immediate
589 inline int Offset12Field() const { return Bits(kOffset12Shift, 581 inline int Offset12Field() const {
590 kOffset12Bits); } 582 return Bits(kOffset12Shift, kOffset12Bits);
583 }
591 // multiple 584 // multiple
592 inline int RlistField() const { return Bits(0, 16); } 585 inline int RlistField() const { return Bits(0, 16); }
593 // extra loads and stores 586 // extra loads and stores
594 inline int SignField() const { return Bit(6); } 587 inline int SignField() const { return Bit(6); }
595 inline int HField() const { return Bit(5); } 588 inline int HField() const { return Bit(5); }
596 inline int ImmedHField() const { return Bits(8, 4); } 589 inline int ImmedHField() const { return Bits(8, 4); }
597 inline int ImmedLField() const { return Bits(0, 4); } 590 inline int ImmedLField() const { return Bits(0, 4); }
598 591
599 // Fields used in Branch instructions 592 // Fields used in Branch instructions
600 inline int LinkField() const { return Bits(kLinkShift, kLinkBits); } 593 inline int LinkField() const { return Bits(kLinkShift, kLinkBits); }
(...skipping 14 matching lines...) Expand all
615 608
616 // Field used in VFP float immediate move instruction 609 // Field used in VFP float immediate move instruction
617 inline float ImmFloatField() const { 610 inline float ImmFloatField() const {
618 uint32_t imm32 = (Bit(19) << 31) | (((1 << 5) - Bit(18)) << 25) | 611 uint32_t imm32 = (Bit(19) << 31) | (((1 << 5) - Bit(18)) << 25) |
619 (Bits(16, 2) << 23) | (Bits(0, 4) << 19); 612 (Bits(16, 2) << 23) | (Bits(0, 4) << 19);
620 return bit_cast<float, uint32_t>(imm32); 613 return bit_cast<float, uint32_t>(imm32);
621 } 614 }
622 615
623 // Field used in VFP double immediate move instruction 616 // Field used in VFP double immediate move instruction
624 inline double ImmDoubleField() const { 617 inline double ImmDoubleField() const {
625 uint64_t imm64 = (Bit(19)*(1LL << 63)) | (((1LL << 8) - Bit(18)) << 54) | 618 uint64_t imm64 = (Bit(19) * (1LL << 63)) | (((1LL << 8) - Bit(18)) << 54) |
626 (Bits(16, 2)*(1LL << 52)) | (Bits(0, 4)*(1LL << 48)); 619 (Bits(16, 2) * (1LL << 52)) | (Bits(0, 4) * (1LL << 48));
627 return bit_cast<double, uint64_t>(imm64); 620 return bit_cast<double, uint64_t>(imm64);
628 } 621 }
629 622
630 inline Register DivRdField() const { 623 inline Register DivRdField() const {
631 return static_cast<Register>(Bits(kDivRdShift, kDivRdBits)); 624 return static_cast<Register>(Bits(kDivRdShift, kDivRdBits));
632 } 625 }
633 inline Register DivRmField() const { 626 inline Register DivRmField() const {
634 return static_cast<Register>(Bits(kDivRmShift, kDivRmBits)); 627 return static_cast<Register>(Bits(kDivRmShift, kDivRmBits));
635 } 628 }
636 inline Register DivRnField() const { 629 inline Register DivRnField() const {
637 return static_cast<Register>(Bits(kDivRnShift, kDivRnBits)); 630 return static_cast<Register>(Bits(kDivRnShift, kDivRnBits));
638 } 631 }
639 632
640 // Test for data processing instructions of type 0 or 1. 633 // Test for data processing instructions of type 0 or 1.
641 // See "ARM Architecture Reference Manual ARMv7-A and ARMv7-R edition", 634 // See "ARM Architecture Reference Manual ARMv7-A and ARMv7-R edition",
642 // section A5.1 "ARM instruction set encoding". 635 // section A5.1 "ARM instruction set encoding".
643 inline bool IsDataProcessing() const { 636 inline bool IsDataProcessing() const {
644 ASSERT(ConditionField() != kSpecialCondition); 637 ASSERT(ConditionField() != kSpecialCondition);
645 ASSERT(Bits(26, 2) == 0); // Type 0 or 1. 638 ASSERT(Bits(26, 2) == 0); // Type 0 or 1.
646 return ((Bits(20, 5) & 0x19) != 0x10) && 639 return ((Bits(20, 5) & 0x19) != 0x10) &&
647 ((Bit(25) == 1) || // Data processing immediate. 640 ((Bit(25) == 1) || // Data processing immediate.
648 (Bit(4) == 0) || // Data processing register. 641 (Bit(4) == 0) || // Data processing register.
649 (Bit(7) == 0)); // Data processing register-shifted register. 642 (Bit(7) == 0)); // Data processing register-shifted register.
650 } 643 }
651 644
652 // Tests for special encodings of type 0 instructions (extra loads and stores, 645 // Tests for special encodings of type 0 instructions (extra loads and stores,
653 // as well as multiplications, synchronization primitives, and miscellaneous). 646 // as well as multiplications, synchronization primitives, and miscellaneous).
654 // Can only be called for a type 0 or 1 instruction. 647 // Can only be called for a type 0 or 1 instruction.
655 inline bool IsMiscellaneous() const { 648 inline bool IsMiscellaneous() const {
656 ASSERT(Bits(26, 2) == 0); // Type 0 or 1. 649 ASSERT(Bits(26, 2) == 0); // Type 0 or 1.
657 return ((Bit(25) == 0) && ((Bits(20, 5) & 0x19) == 0x10) && (Bit(7) == 0)); 650 return ((Bit(25) == 0) && ((Bits(20, 5) & 0x19) == 0x10) && (Bit(7) == 0));
658 } 651 }
659 inline bool IsMultiplyOrSyncPrimitive() const { 652 inline bool IsMultiplyOrSyncPrimitive() const {
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
699 return static_cast<QRegister>(bits >> 1); 692 return static_cast<QRegister>(bits >> 1);
700 } 693 }
701 inline QRegister QmField() const { 694 inline QRegister QmField() const {
702 const intptr_t bits = Bits(kRmShift, kRmBits) + (Bit(5) << 4); 695 const intptr_t bits = Bits(kRmShift, kRmBits) + (Bit(5) << 4);
703 return static_cast<QRegister>(bits >> 1); 696 return static_cast<QRegister>(bits >> 1);
704 } 697 }
705 698
706 inline bool IsDivision() const { 699 inline bool IsDivision() const {
707 ASSERT(ConditionField() != kSpecialCondition); 700 ASSERT(ConditionField() != kSpecialCondition);
708 ASSERT(TypeField() == 3); 701 ASSERT(TypeField() == 3);
709 return ((Bit(4) == 1) && (Bits(5, 3) == 0) && 702 return ((Bit(4) == 1) && (Bits(5, 3) == 0) && (Bit(20) == 1) &&
710 (Bit(20) == 1) && (Bits(22, 3) == 4)); 703 (Bits(22, 3) == 4));
711 } 704 }
712 705
713 // Test for VFP data processing or single transfer instructions of type 7. 706 // Test for VFP data processing or single transfer instructions of type 7.
714 inline bool IsVFPDataProcessingOrSingleTransfer() const { 707 inline bool IsVFPDataProcessingOrSingleTransfer() const {
715 ASSERT(ConditionField() != kSpecialCondition); 708 ASSERT(ConditionField() != kSpecialCondition);
716 ASSERT(TypeField() == 7); 709 ASSERT(TypeField() == 7);
717 return ((Bit(24) == 0) && (Bits(9, 3) == 5)); 710 return ((Bit(24) == 0) && (Bits(9, 3) == 5));
718 // Bit(4) == 0: Data Processing 711 // Bit(4) == 0: Data Processing
719 // Bit(4) == 1: 8, 16, or 32-bit Transfer between ARM Core and VFP 712 // Bit(4) == 1: 8, 16, or 32-bit Transfer between ARM Core and VFP
720 } 713 }
(...skipping 25 matching lines...) Expand all
746 ASSERT(ConditionField() == kSpecialCondition); 739 ASSERT(ConditionField() == kSpecialCondition);
747 return (Bits(25, 3) == 1); 740 return (Bits(25, 3) == 1);
748 } 741 }
749 742
750 inline bool IsSIMDLoadStore() const { 743 inline bool IsSIMDLoadStore() const {
751 ASSERT(ConditionField() == kSpecialCondition); 744 ASSERT(ConditionField() == kSpecialCondition);
752 return (Bits(24, 4) == 4) && (Bit(20) == 0); 745 return (Bits(24, 4) == 4) && (Bit(20) == 0);
753 } 746 }
754 747
755 // Special accessors that test for existence of a value. 748 // Special accessors that test for existence of a value.
756 inline bool HasS() const { return SField() == 1; } 749 inline bool HasS() const { return SField() == 1; }
757 inline bool HasB() const { return BField() == 1; } 750 inline bool HasB() const { return BField() == 1; }
758 inline bool HasW() const { return WField() == 1; } 751 inline bool HasW() const { return WField() == 1; }
759 inline bool HasL() const { return LField() == 1; } 752 inline bool HasL() const { return LField() == 1; }
760 inline bool HasSign() const { return SignField() == 1; } 753 inline bool HasSign() const { return SignField() == 1; }
761 inline bool HasH() const { return HField() == 1; } 754 inline bool HasH() const { return HField() == 1; }
762 inline bool HasLink() const { return LinkField() == 1; } 755 inline bool HasLink() const { return LinkField() == 1; }
763 756
764 // Instructions are read out of a code stream. The only way to get a 757 // Instructions are read out of a code stream. The only way to get a
765 // reference to an instruction is to convert a pointer. There is no way 758 // reference to an instruction is to convert a pointer. There is no way
766 // to allocate or create instances of class Instr. 759 // to allocate or create instances of class Instr.
767 // Use the At(pc) function to create references to Instr. 760 // Use the At(pc) function to create references to Instr.
768 static Instr* At(uword pc) { return reinterpret_cast<Instr*>(pc); } 761 static Instr* At(uword pc) { return reinterpret_cast<Instr*>(pc); }
769 762
770 private: 763 private:
771 DISALLOW_ALLOCATION(); 764 DISALLOW_ALLOCATION();
772 DISALLOW_IMPLICIT_CONSTRUCTORS(Instr); 765 DISALLOW_IMPLICIT_CONSTRUCTORS(Instr);
773 }; 766 };
774 767
775 } // namespace dart 768 } // namespace dart
776 769
777 #endif // RUNTIME_VM_CONSTANTS_ARM_H_ 770 #endif // RUNTIME_VM_CONSTANTS_ARM_H_
OLDNEW
« no previous file with comments | « runtime/vm/constant_propagator.cc ('k') | runtime/vm/constants_arm64.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698