OLD | NEW |
---|---|
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 VM_CONSTANTS_MIPS_H_ | 5 #ifndef VM_CONSTANTS_MIPS_H_ |
6 #define VM_CONSTANTS_MIPS_H_ | 6 #define VM_CONSTANTS_MIPS_H_ |
7 | 7 |
8 #include "platform/assert.h" | 8 #include "platform/assert.h" |
9 #include "vm/allocation.h" | |
10 #include "vm/bitfield.h" | |
9 | 11 |
10 namespace dart { | 12 namespace dart { |
11 | 13 |
12 enum Register { | 14 enum Register { |
13 R0 = 0, | 15 R0 = 0, |
14 R1 = 1, | 16 R1 = 1, |
15 kFirstFreeCpuRegister = 2, | 17 kFirstFreeCpuRegister = 2, |
16 R2 = 2, | 18 R2 = 2, |
17 R3 = 3, | 19 R3 = 3, |
18 R4 = 4, | 20 R4 = 4, |
(...skipping 19 matching lines...) Expand all Loading... | |
38 R23 = 23, | 40 R23 = 23, |
39 R24 = 24, | 41 R24 = 24, |
40 R25 = 25, | 42 R25 = 25, |
41 R26 = 26, | 43 R26 = 26, |
42 R27 = 27, | 44 R27 = 27, |
43 R28 = 28, | 45 R28 = 28, |
44 R29 = 29, | 46 R29 = 29, |
45 R30 = 30, | 47 R30 = 30, |
46 R31 = 31, | 48 R31 = 31, |
47 kNumberOfCpuRegisters = 32, | 49 kNumberOfCpuRegisters = 32, |
50 IMM = 32, // Positive value is easier to encode than kNoRegister in bitfield. | |
48 kNoRegister = -1, | 51 kNoRegister = -1, |
49 | 52 |
50 // Register aliases. | 53 // Register aliases. |
51 ZR = R0, | 54 ZR = R0, |
52 AT = R1, | 55 AT = R1, |
53 | 56 |
54 V0 = R2, | 57 V0 = R2, |
55 V1 = R3, | 58 V1 = R3, |
56 | 59 |
57 A0 = R4, | 60 A0 = R4, |
(...skipping 171 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
229 const int kDartVolatileCpuRegCount = 14; | 232 const int kDartVolatileCpuRegCount = 14; |
230 const Register kDartFirstVolatileCpuReg = R2; | 233 const Register kDartFirstVolatileCpuReg = R2; |
231 const Register kDartLastVolatileCpuReg = R15; | 234 const Register kDartLastVolatileCpuReg = R15; |
232 | 235 |
233 // FPU registers 0 - 19 are not preserved across calls. | 236 // FPU registers 0 - 19 are not preserved across calls. |
234 const FRegister kDartFirstVolatileFpuReg = F0; | 237 const FRegister kDartFirstVolatileFpuReg = F0; |
235 const FRegister kDartLastVolatileFpuReg = F19; | 238 const FRegister kDartLastVolatileFpuReg = F19; |
236 const int kDartVolatileFpuRegCount = 20; | 239 const int kDartVolatileFpuRegCount = 20; |
237 | 240 |
238 | 241 |
239 // Values for the condition field. | 242 // Values for the condition field in the status register. |
240 // There is no condition field on MIPS, but Conditions are used and passed | 243 // There is no dedicated status register on MIPS, but Condition values are used |
241 // around by the intermediate language, so we need them here, too. | 244 // and passed around by the intermediate language, so we need them here, too. |
242 enum Condition { | 245 // We delay code generation of a comparison that would result in a traditional |
246 // condition code in the status register by keeping both register operands and | |
247 // the relational operator between them as the Condition. | |
248 enum RelationOperator { | |
249 AL, // always | |
250 NV, // never | |
243 EQ, // equal | 251 EQ, // equal |
244 NE, // not equal | 252 NE, // not equal |
245 GT, // greater than | 253 GT, // greater than |
246 GE, // greater equal | 254 GE, // greater equal |
247 LT, // less than | 255 LT, // less than |
248 LE, // less equal | 256 LE, // less equal |
249 VS, // overflow | 257 UGT, // unsigned greater than |
258 UGE, // unsigned greater equal | |
259 ULT, // unsigned less than | |
260 ULE, // unsigned less equal | |
261 }; | |
262 | |
263 | |
264 class Condition : public ValueObject { | |
zra
2014/12/19 17:49:47
Should this go in assembler_mips.h?
regis
2014/12/22 20:17:34
Done.
| |
265 public: | |
266 enum Bits { | |
267 kLeftPos = 0, | |
268 kLeftSize = 6, | |
269 kRightPos = kLeftPos + kLeftSize, | |
270 kRightSize = 6, | |
271 kRelOpPos = kRightPos + kRightSize, | |
272 kRelOpSize = 4, | |
273 kImmPos = kRelOpPos + kRelOpSize, | |
274 kImmSize = 16, | |
275 }; | |
276 | |
277 class LeftBits : public BitField<Register, kLeftPos, kLeftSize> {}; | |
278 class RightBits : public BitField<Register, kRightPos, kRightSize> {}; | |
279 class RelOpBits : public BitField<RelationOperator, kRelOpPos, kRelOpSize> {}; | |
280 class ImmBits : public BitField<uint16_t, kImmPos, kImmSize> {}; | |
281 | |
282 Register left() const { return LeftBits::decode(bits_); } | |
283 Register right() const { return RightBits::decode(bits_); } | |
284 RelationOperator rel_op() const { return RelOpBits::decode(bits_); } | |
285 int16_t imm() const { return static_cast<int16_t>(ImmBits::decode(bits_)); } | |
286 | |
287 static bool IsValidImm(int32_t value) { | |
288 // We want both value and value + 1 to fit in an int16_t. | |
289 return (-0x08000 <= value) && (value < 0x7fff); | |
290 } | |
291 | |
292 void set_rel_op(RelationOperator value) { | |
293 ASSERT(IsValidRelOp(value)); | |
294 bits_ = RelOpBits::update(value, bits_); | |
295 } | |
296 | |
297 // Uninitialized condition. | |
298 Condition() : ValueObject(), bits_(0) { } | |
299 | |
300 // Copy constructor. | |
301 Condition(const Condition& other) : ValueObject(), bits_(other.bits_) { } | |
302 | |
303 // Copy assignment operator. | |
304 Condition& operator=(const Condition& other) { | |
305 bits_ = other.bits_; | |
306 return *this; | |
307 } | |
308 | |
309 Condition(Register left, | |
310 Register right, | |
311 RelationOperator rel_op, | |
312 int16_t imm = 0) { | |
313 // At most one constant, ZR or immediate. | |
314 ASSERT(!(((left == ZR) || (left == IMM)) && | |
315 ((right == ZR) || (right == IMM)))); | |
316 // Non-zero immediate value is only allowed for IMM. | |
317 ASSERT((imm != 0) == ((left == IMM) || (right == IMM))); | |
318 set_left(left); | |
319 set_right(right); | |
320 set_rel_op(rel_op); | |
321 set_imm(imm); | |
322 } | |
323 | |
324 private: | |
325 static bool IsValidRelOp(RelationOperator value) { | |
326 return (AL <= value) && (value <= ULE); | |
327 } | |
328 | |
329 static bool IsValidRegister(Register value) { | |
330 return (ZR <= value) && (value <= IMM) && (value != AT); | |
331 } | |
332 | |
333 void set_left(Register value) { | |
334 ASSERT(IsValidRegister(value)); | |
335 bits_ = LeftBits::update(value, bits_); | |
336 } | |
337 | |
338 void set_right(Register value) { | |
339 ASSERT(IsValidRegister(value)); | |
340 bits_ = RightBits::update(value, bits_); | |
341 } | |
342 | |
343 void set_imm(int16_t value) { | |
344 ASSERT(IsValidImm(value)); | |
345 bits_ = ImmBits::update(static_cast<uint16_t>(value), bits_); | |
346 } | |
347 | |
348 uword bits_; | |
250 }; | 349 }; |
251 | 350 |
252 | 351 |
253 // Constants used for the decoding or encoding of the individual fields of | 352 // Constants used for the decoding or encoding of the individual fields of |
254 // instructions. Based on the "Table 4.25 CPU Instruction Format Fields". | 353 // instructions. Based on the "Table 4.25 CPU Instruction Format Fields". |
255 enum InstructionFields { | 354 enum InstructionFields { |
256 kOpcodeShift = 26, | 355 kOpcodeShift = 26, |
257 kOpcodeBits = 6, | 356 kOpcodeBits = 6, |
258 kRsShift = 21, | 357 kRsShift = 21, |
259 kRsBits = 5, | 358 kRsBits = 5, |
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
354 SLLV = 4, | 453 SLLV = 4, |
355 SRLV = 6, | 454 SRLV = 6, |
356 SRAV = 7, | 455 SRAV = 7, |
357 JR = 8, | 456 JR = 8, |
358 JALR = 9, | 457 JALR = 9, |
359 MOVZ = 10, | 458 MOVZ = 10, |
360 MOVN = 11, | 459 MOVN = 11, |
361 SYSCALL = 12, | 460 SYSCALL = 12, |
362 BREAK = 13, | 461 BREAK = 13, |
363 SYNC = 15, | 462 SYNC = 15, |
364 MFHI =16, | 463 MFHI = 16, |
365 MTHI = 17, | 464 MTHI = 17, |
366 MFLO = 18, | 465 MFLO = 18, |
367 MTLO = 19, | 466 MTLO = 19, |
368 MULT = 24, | 467 MULT = 24, |
369 MULTU = 25, | 468 MULTU = 25, |
370 DIV = 26, | 469 DIV = 26, |
371 DIVU = 27, | 470 DIVU = 27, |
372 ADD = 32, | 471 ADD = 32, |
373 ADDU = 33, | 472 ADDU = 33, |
374 SUB = 34, | 473 SUB = 34, |
(...skipping 258 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
633 #endif // defined(DEBUG) | 732 #endif // defined(DEBUG) |
634 | 733 |
635 private: | 734 private: |
636 DISALLOW_ALLOCATION(); | 735 DISALLOW_ALLOCATION(); |
637 DISALLOW_IMPLICIT_CONSTRUCTORS(Instr); | 736 DISALLOW_IMPLICIT_CONSTRUCTORS(Instr); |
638 }; | 737 }; |
639 | 738 |
640 } // namespace dart | 739 } // namespace dart |
641 | 740 |
642 #endif // VM_CONSTANTS_MIPS_H_ | 741 #endif // VM_CONSTANTS_MIPS_H_ |
OLD | NEW |