1// Copyright 2012 the V8 project authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#ifndef  V8_MIPS_CONSTANTS_H_
6#define  V8_MIPS_CONSTANTS_H_
7
8#include "src/base/logging.h"
9#include "src/base/macros.h"
10#include "src/globals.h"
11
12// UNIMPLEMENTED_ macro for MIPS.
13#ifdef DEBUG
14#define UNIMPLEMENTED_MIPS()                                                  \
15  v8::internal::PrintF("%s, \tline %d: \tfunction %s not implemented. \n",    \
16                       __FILE__, __LINE__, __func__)
17#else
18#define UNIMPLEMENTED_MIPS()
19#endif
20
21#define UNSUPPORTED_MIPS() v8::internal::PrintF("Unsupported instruction.\n")
22
23enum ArchVariants {
24  kMips64r2,
25  kMips64r6
26};
27
28
29#ifdef _MIPS_ARCH_MIPS64R2
30  static const ArchVariants kArchVariant = kMips64r2;
31#elif  _MIPS_ARCH_MIPS64R6
32  static const ArchVariants kArchVariant = kMips64r6;
33#else
34  static const ArchVariants kArchVariant = kMips64r2;
35#endif
36
37
38  enum Endianness { kLittle, kBig };
39
40#if defined(V8_TARGET_LITTLE_ENDIAN)
41  static const Endianness kArchEndian = kLittle;
42#elif defined(V8_TARGET_BIG_ENDIAN)
43  static const Endianness kArchEndian = kBig;
44#else
45#error Unknown endianness
46#endif
47
48
49// TODO(plind): consider renaming these ...
50#if(defined(__mips_hard_float) && __mips_hard_float != 0)
51// Use floating-point coprocessor instructions. This flag is raised when
52// -mhard-float is passed to the compiler.
53const bool IsMipsSoftFloatABI = false;
54#elif(defined(__mips_soft_float) && __mips_soft_float != 0)
55// This flag is raised when -msoft-float is passed to the compiler.
56// Although FPU is a base requirement for v8, soft-float ABI is used
57// on soft-float systems with FPU kernel emulation.
58const bool IsMipsSoftFloatABI = true;
59#else
60const bool IsMipsSoftFloatABI = true;
61#endif
62
63#if defined(V8_TARGET_LITTLE_ENDIAN)
64const uint32_t kMipsLwrOffset = 0;
65const uint32_t kMipsLwlOffset = 3;
66const uint32_t kMipsSwrOffset = 0;
67const uint32_t kMipsSwlOffset = 3;
68const uint32_t kMipsLdrOffset = 0;
69const uint32_t kMipsLdlOffset = 7;
70const uint32_t kMipsSdrOffset = 0;
71const uint32_t kMipsSdlOffset = 7;
72#elif defined(V8_TARGET_BIG_ENDIAN)
73const uint32_t kMipsLwrOffset = 3;
74const uint32_t kMipsLwlOffset = 0;
75const uint32_t kMipsSwrOffset = 3;
76const uint32_t kMipsSwlOffset = 0;
77const uint32_t kMipsLdrOffset = 7;
78const uint32_t kMipsLdlOffset = 0;
79const uint32_t kMipsSdrOffset = 7;
80const uint32_t kMipsSdlOffset = 0;
81#else
82#error Unknown endianness
83#endif
84
85#ifndef __STDC_FORMAT_MACROS
86#define __STDC_FORMAT_MACROS
87#endif
88#include <inttypes.h>
89
90
91// Defines constants and accessor classes to assemble, disassemble and
92// simulate MIPS32 instructions.
93//
94// See: MIPS32 Architecture For Programmers
95//      Volume II: The MIPS32 Instruction Set
96// Try www.cs.cornell.edu/courses/cs3410/2008fa/MIPS_Vol2.pdf.
97
98namespace v8 {
99namespace internal {
100
101// -----------------------------------------------------------------------------
102// Registers and FPURegisters.
103
104// Number of general purpose registers.
105const int kNumRegisters = 32;
106const int kInvalidRegister = -1;
107
108// Number of registers with HI, LO, and pc.
109const int kNumSimuRegisters = 35;
110
111// In the simulator, the PC register is simulated as the 34th register.
112const int kPCRegister = 34;
113
114// Number coprocessor registers.
115const int kNumFPURegisters = 32;
116const int kInvalidFPURegister = -1;
117
118// FPU (coprocessor 1) control registers. Currently only FCSR is implemented.
119const int kFCSRRegister = 31;
120const int kInvalidFPUControlRegister = -1;
121const uint32_t kFPUInvalidResult = static_cast<uint32_t>(1 << 31) - 1;
122const int32_t kFPUInvalidResultNegative = static_cast<int32_t>(1 << 31);
123const uint64_t kFPU64InvalidResult =
124    static_cast<uint64_t>(static_cast<uint64_t>(1) << 63) - 1;
125const int64_t kFPU64InvalidResultNegative =
126    static_cast<int64_t>(static_cast<uint64_t>(1) << 63);
127
128// FCSR constants.
129const uint32_t kFCSRInexactFlagBit = 2;
130const uint32_t kFCSRUnderflowFlagBit = 3;
131const uint32_t kFCSROverflowFlagBit = 4;
132const uint32_t kFCSRDivideByZeroFlagBit = 5;
133const uint32_t kFCSRInvalidOpFlagBit = 6;
134const uint32_t kFCSRNaN2008FlagBit = 18;
135
136const uint32_t kFCSRInexactFlagMask = 1 << kFCSRInexactFlagBit;
137const uint32_t kFCSRUnderflowFlagMask = 1 << kFCSRUnderflowFlagBit;
138const uint32_t kFCSROverflowFlagMask = 1 << kFCSROverflowFlagBit;
139const uint32_t kFCSRDivideByZeroFlagMask = 1 << kFCSRDivideByZeroFlagBit;
140const uint32_t kFCSRInvalidOpFlagMask = 1 << kFCSRInvalidOpFlagBit;
141const uint32_t kFCSRNaN2008FlagMask = 1 << kFCSRNaN2008FlagBit;
142
143const uint32_t kFCSRFlagMask =
144    kFCSRInexactFlagMask |
145    kFCSRUnderflowFlagMask |
146    kFCSROverflowFlagMask |
147    kFCSRDivideByZeroFlagMask |
148    kFCSRInvalidOpFlagMask;
149
150const uint32_t kFCSRExceptionFlagMask = kFCSRFlagMask ^ kFCSRInexactFlagMask;
151
152// 'pref' instruction hints
153const int32_t kPrefHintLoad = 0;
154const int32_t kPrefHintStore = 1;
155const int32_t kPrefHintLoadStreamed = 4;
156const int32_t kPrefHintStoreStreamed = 5;
157const int32_t kPrefHintLoadRetained = 6;
158const int32_t kPrefHintStoreRetained = 7;
159const int32_t kPrefHintWritebackInvalidate = 25;
160const int32_t kPrefHintPrepareForStore = 30;
161
162// Helper functions for converting between register numbers and names.
163class Registers {
164 public:
165  // Return the name of the register.
166  static const char* Name(int reg);
167
168  // Lookup the register number for the name provided.
169  static int Number(const char* name);
170
171  struct RegisterAlias {
172    int reg;
173    const char* name;
174  };
175
176  static const int64_t kMaxValue = 0x7fffffffffffffffl;
177  static const int64_t kMinValue = 0x8000000000000000l;
178
179 private:
180  static const char* names_[kNumSimuRegisters];
181  static const RegisterAlias aliases_[];
182};
183
184// Helper functions for converting between register numbers and names.
185class FPURegisters {
186 public:
187  // Return the name of the register.
188  static const char* Name(int reg);
189
190  // Lookup the register number for the name provided.
191  static int Number(const char* name);
192
193  struct RegisterAlias {
194    int creg;
195    const char* name;
196  };
197
198 private:
199  static const char* names_[kNumFPURegisters];
200  static const RegisterAlias aliases_[];
201};
202
203
204// -----------------------------------------------------------------------------
205// Instructions encoding constants.
206
207// On MIPS all instructions are 32 bits.
208typedef int32_t Instr;
209
210// Special Software Interrupt codes when used in the presence of the MIPS
211// simulator.
212enum SoftwareInterruptCodes {
213  // Transition to C code.
214  call_rt_redirected = 0xfffff
215};
216
217// On MIPS Simulator breakpoints can have different codes:
218// - Breaks between 0 and kMaxWatchpointCode are treated as simple watchpoints,
219//   the simulator will run through them and print the registers.
220// - Breaks between kMaxWatchpointCode and kMaxStopCode are treated as stop()
221//   instructions (see Assembler::stop()).
222// - Breaks larger than kMaxStopCode are simple breaks, dropping you into the
223//   debugger.
224const uint32_t kMaxWatchpointCode = 31;
225const uint32_t kMaxStopCode = 127;
226STATIC_ASSERT(kMaxWatchpointCode < kMaxStopCode);
227
228
229// ----- Fields offset and length.
230const int kOpcodeShift   = 26;
231const int kOpcodeBits    = 6;
232const int kRsShift       = 21;
233const int kRsBits        = 5;
234const int kRtShift       = 16;
235const int kRtBits        = 5;
236const int kRdShift       = 11;
237const int kRdBits        = 5;
238const int kSaShift       = 6;
239const int kSaBits        = 5;
240const int kLsaSaBits = 2;
241const int kFunctionShift = 0;
242const int kFunctionBits  = 6;
243const int kLuiShift      = 16;
244const int kBp2Shift = 6;
245const int kBp2Bits = 2;
246const int kBp3Shift = 6;
247const int kBp3Bits = 3;
248
249const int kImm16Shift = 0;
250const int kImm16Bits  = 16;
251const int kImm18Shift = 0;
252const int kImm18Bits = 18;
253const int kImm19Shift = 0;
254const int kImm19Bits = 19;
255const int kImm21Shift = 0;
256const int kImm21Bits  = 21;
257const int kImm26Shift = 0;
258const int kImm26Bits  = 26;
259const int kImm28Shift = 0;
260const int kImm28Bits  = 28;
261const int kImm32Shift = 0;
262const int kImm32Bits  = 32;
263
264// In branches and jumps immediate fields point to words, not bytes,
265// and are therefore shifted by 2.
266const int kImmFieldShift = 2;
267
268const int kFrBits        = 5;
269const int kFrShift       = 21;
270const int kFsShift       = 11;
271const int kFsBits        = 5;
272const int kFtShift       = 16;
273const int kFtBits        = 5;
274const int kFdShift       = 6;
275const int kFdBits        = 5;
276const int kFCccShift     = 8;
277const int kFCccBits      = 3;
278const int kFBccShift     = 18;
279const int kFBccBits      = 3;
280const int kFBtrueShift   = 16;
281const int kFBtrueBits    = 1;
282
283// ----- Miscellaneous useful masks.
284// Instruction bit masks.
285const int  kOpcodeMask   = ((1 << kOpcodeBits) - 1) << kOpcodeShift;
286const int  kImm16Mask    = ((1 << kImm16Bits) - 1) << kImm16Shift;
287const int kImm18Mask = ((1 << kImm18Bits) - 1) << kImm18Shift;
288const int kImm19Mask = ((1 << kImm19Bits) - 1) << kImm19Shift;
289const int kImm21Mask = ((1 << kImm21Bits) - 1) << kImm21Shift;
290const int  kImm26Mask    = ((1 << kImm26Bits) - 1) << kImm26Shift;
291const int  kImm28Mask    = ((1 << kImm28Bits) - 1) << kImm28Shift;
292const int  kRsFieldMask  = ((1 << kRsBits) - 1) << kRsShift;
293const int  kRtFieldMask  = ((1 << kRtBits) - 1) << kRtShift;
294const int  kRdFieldMask  = ((1 << kRdBits) - 1) << kRdShift;
295const int  kSaFieldMask  = ((1 << kSaBits) - 1) << kSaShift;
296const int  kFunctionFieldMask = ((1 << kFunctionBits) - 1) << kFunctionShift;
297// Misc masks.
298const int  kHiMask       =   0xffff << 16;
299const int  kLoMask       =   0xffff;
300const int  kSignMask     =   0x80000000;
301const int  kJumpAddrMask = (1 << (kImm26Bits + kImmFieldShift)) - 1;
302const int64_t  kHi16MaskOf64 =   (int64_t)0xffff << 48;
303const int64_t  kSe16MaskOf64 =   (int64_t)0xffff << 32;
304const int64_t  kTh16MaskOf64 =   (int64_t)0xffff << 16;
305const int32_t kJalRawMark = 0x00000000;
306const int32_t kJRawMark = 0xf0000000;
307const int32_t kJumpRawMask = 0xf0000000;
308
309// ----- MIPS Opcodes and Function Fields.
310// We use this presentation to stay close to the table representation in
311// MIPS32 Architecture For Programmers, Volume II: The MIPS32 Instruction Set.
312enum Opcode : uint32_t {
313  SPECIAL = 0U << kOpcodeShift,
314  REGIMM = 1U << kOpcodeShift,
315
316  J = ((0U << 3) + 2) << kOpcodeShift,
317  JAL = ((0U << 3) + 3) << kOpcodeShift,
318  BEQ = ((0U << 3) + 4) << kOpcodeShift,
319  BNE = ((0U << 3) + 5) << kOpcodeShift,
320  BLEZ = ((0U << 3) + 6) << kOpcodeShift,
321  BGTZ = ((0U << 3) + 7) << kOpcodeShift,
322
323  ADDI = ((1U << 3) + 0) << kOpcodeShift,
324  ADDIU = ((1U << 3) + 1) << kOpcodeShift,
325  SLTI = ((1U << 3) + 2) << kOpcodeShift,
326  SLTIU = ((1U << 3) + 3) << kOpcodeShift,
327  ANDI = ((1U << 3) + 4) << kOpcodeShift,
328  ORI = ((1U << 3) + 5) << kOpcodeShift,
329  XORI = ((1U << 3) + 6) << kOpcodeShift,
330  LUI = ((1U << 3) + 7) << kOpcodeShift,  // LUI/AUI family.
331  DAUI = ((3U << 3) + 5) << kOpcodeShift,
332
333  BEQC = ((2U << 3) + 0) << kOpcodeShift,
334  COP1 = ((2U << 3) + 1) << kOpcodeShift,  // Coprocessor 1 class.
335  BEQL = ((2U << 3) + 4) << kOpcodeShift,
336  BNEL = ((2U << 3) + 5) << kOpcodeShift,
337  BLEZL = ((2U << 3) + 6) << kOpcodeShift,
338  BGTZL = ((2U << 3) + 7) << kOpcodeShift,
339
340  DADDI = ((3U << 3) + 0) << kOpcodeShift,  // This is also BNEC.
341  DADDIU = ((3U << 3) + 1) << kOpcodeShift,
342  LDL = ((3U << 3) + 2) << kOpcodeShift,
343  LDR = ((3U << 3) + 3) << kOpcodeShift,
344  SPECIAL2 = ((3U << 3) + 4) << kOpcodeShift,
345  SPECIAL3 = ((3U << 3) + 7) << kOpcodeShift,
346
347  LB = ((4U << 3) + 0) << kOpcodeShift,
348  LH = ((4U << 3) + 1) << kOpcodeShift,
349  LWL = ((4U << 3) + 2) << kOpcodeShift,
350  LW = ((4U << 3) + 3) << kOpcodeShift,
351  LBU = ((4U << 3) + 4) << kOpcodeShift,
352  LHU = ((4U << 3) + 5) << kOpcodeShift,
353  LWR = ((4U << 3) + 6) << kOpcodeShift,
354  LWU = ((4U << 3) + 7) << kOpcodeShift,
355
356  SB = ((5U << 3) + 0) << kOpcodeShift,
357  SH = ((5U << 3) + 1) << kOpcodeShift,
358  SWL = ((5U << 3) + 2) << kOpcodeShift,
359  SW = ((5U << 3) + 3) << kOpcodeShift,
360  SDL = ((5U << 3) + 4) << kOpcodeShift,
361  SDR = ((5U << 3) + 5) << kOpcodeShift,
362  SWR = ((5U << 3) + 6) << kOpcodeShift,
363
364  LWC1 = ((6U << 3) + 1) << kOpcodeShift,
365  BC = ((6U << 3) + 2) << kOpcodeShift,
366  LLD = ((6U << 3) + 4) << kOpcodeShift,
367  LDC1 = ((6U << 3) + 5) << kOpcodeShift,
368  POP66 = ((6U << 3) + 6) << kOpcodeShift,
369  LD = ((6U << 3) + 7) << kOpcodeShift,
370
371  PREF = ((6U << 3) + 3) << kOpcodeShift,
372
373  SWC1 = ((7U << 3) + 1) << kOpcodeShift,
374  BALC = ((7U << 3) + 2) << kOpcodeShift,
375  PCREL = ((7U << 3) + 3) << kOpcodeShift,
376  SCD = ((7U << 3) + 4) << kOpcodeShift,
377  SDC1 = ((7U << 3) + 5) << kOpcodeShift,
378  POP76 = ((7U << 3) + 6) << kOpcodeShift,
379  SD = ((7U << 3) + 7) << kOpcodeShift,
380
381  COP1X = ((1U << 4) + 3) << kOpcodeShift,
382
383  // New r6 instruction.
384  POP06 = BLEZ,   // bgeuc/bleuc, blezalc, bgezalc
385  POP07 = BGTZ,   // bltuc/bgtuc, bgtzalc, bltzalc
386  POP10 = ADDI,   // beqzalc, bovc, beqc
387  POP26 = BLEZL,  // bgezc, blezc, bgec/blec
388  POP27 = BGTZL,  // bgtzc, bltzc, bltc/bgtc
389  POP30 = DADDI,  // bnezalc, bnvc, bnec
390};
391
392enum SecondaryField : uint32_t {
393  // SPECIAL Encoding of Function Field.
394  SLL = ((0U << 3) + 0),
395  MOVCI = ((0U << 3) + 1),
396  SRL = ((0U << 3) + 2),
397  SRA = ((0U << 3) + 3),
398  SLLV = ((0U << 3) + 4),
399  LSA = ((0U << 3) + 5),
400  SRLV = ((0U << 3) + 6),
401  SRAV = ((0U << 3) + 7),
402
403  JR = ((1U << 3) + 0),
404  JALR = ((1U << 3) + 1),
405  MOVZ = ((1U << 3) + 2),
406  MOVN = ((1U << 3) + 3),
407  BREAK = ((1U << 3) + 5),
408  SYNC = ((1U << 3) + 7),
409
410  MFHI = ((2U << 3) + 0),
411  CLZ_R6 = ((2U << 3) + 0),
412  CLO_R6 = ((2U << 3) + 1),
413  MFLO = ((2U << 3) + 2),
414  DCLZ_R6 = ((2U << 3) + 2),
415  DCLO_R6 = ((2U << 3) + 3),
416  DSLLV = ((2U << 3) + 4),
417  DLSA = ((2U << 3) + 5),
418  DSRLV = ((2U << 3) + 6),
419  DSRAV = ((2U << 3) + 7),
420
421  MULT = ((3U << 3) + 0),
422  MULTU = ((3U << 3) + 1),
423  DIV = ((3U << 3) + 2),
424  DIVU = ((3U << 3) + 3),
425  DMULT = ((3U << 3) + 4),
426  DMULTU = ((3U << 3) + 5),
427  DDIV = ((3U << 3) + 6),
428  DDIVU = ((3U << 3) + 7),
429
430  ADD = ((4U << 3) + 0),
431  ADDU = ((4U << 3) + 1),
432  SUB = ((4U << 3) + 2),
433  SUBU = ((4U << 3) + 3),
434  AND = ((4U << 3) + 4),
435  OR = ((4U << 3) + 5),
436  XOR = ((4U << 3) + 6),
437  NOR = ((4U << 3) + 7),
438
439  SLT = ((5U << 3) + 2),
440  SLTU = ((5U << 3) + 3),
441  DADD = ((5U << 3) + 4),
442  DADDU = ((5U << 3) + 5),
443  DSUB = ((5U << 3) + 6),
444  DSUBU = ((5U << 3) + 7),
445
446  TGE = ((6U << 3) + 0),
447  TGEU = ((6U << 3) + 1),
448  TLT = ((6U << 3) + 2),
449  TLTU = ((6U << 3) + 3),
450  TEQ = ((6U << 3) + 4),
451  SELEQZ_S = ((6U << 3) + 5),
452  TNE = ((6U << 3) + 6),
453  SELNEZ_S = ((6U << 3) + 7),
454
455  DSLL = ((7U << 3) + 0),
456  DSRL = ((7U << 3) + 2),
457  DSRA = ((7U << 3) + 3),
458  DSLL32 = ((7U << 3) + 4),
459  DSRL32 = ((7U << 3) + 6),
460  DSRA32 = ((7U << 3) + 7),
461
462  // Multiply integers in r6.
463  MUL_MUH = ((3U << 3) + 0),      // MUL, MUH.
464  MUL_MUH_U = ((3U << 3) + 1),    // MUL_U, MUH_U.
465  D_MUL_MUH = ((7U << 2) + 0),    // DMUL, DMUH.
466  D_MUL_MUH_U = ((7U << 2) + 1),  // DMUL_U, DMUH_U.
467  RINT = ((3U << 3) + 2),
468
469  MUL_OP = ((0U << 3) + 2),
470  MUH_OP = ((0U << 3) + 3),
471  DIV_OP = ((0U << 3) + 2),
472  MOD_OP = ((0U << 3) + 3),
473
474  DIV_MOD = ((3U << 3) + 2),
475  DIV_MOD_U = ((3U << 3) + 3),
476  D_DIV_MOD = ((3U << 3) + 6),
477  D_DIV_MOD_U = ((3U << 3) + 7),
478
479  // drotr in special4?
480
481  // SPECIAL2 Encoding of Function Field.
482  MUL = ((0U << 3) + 2),
483  CLZ = ((4U << 3) + 0),
484  CLO = ((4U << 3) + 1),
485  DCLZ = ((4U << 3) + 4),
486  DCLO = ((4U << 3) + 5),
487
488  // SPECIAL3 Encoding of Function Field.
489  EXT = ((0U << 3) + 0),
490  DEXTM = ((0U << 3) + 1),
491  DEXTU = ((0U << 3) + 2),
492  DEXT = ((0U << 3) + 3),
493  INS = ((0U << 3) + 4),
494  DINSM = ((0U << 3) + 5),
495  DINSU = ((0U << 3) + 6),
496  DINS = ((0U << 3) + 7),
497
498  BSHFL = ((4U << 3) + 0),
499  DBSHFL = ((4U << 3) + 4),
500
501  // SPECIAL3 Encoding of sa Field.
502  BITSWAP = ((0U << 3) + 0),
503  ALIGN = ((0U << 3) + 2),
504  WSBH = ((0U << 3) + 2),
505  SEB = ((2U << 3) + 0),
506  SEH = ((3U << 3) + 0),
507
508  DBITSWAP = ((0U << 3) + 0),
509  DALIGN = ((0U << 3) + 1),
510  DBITSWAP_SA = ((0U << 3) + 0) << kSaShift,
511  DSBH = ((0U << 3) + 2),
512  DSHD = ((0U << 3) + 5),
513
514  // REGIMM  encoding of rt Field.
515  BLTZ = ((0U << 3) + 0) << 16,
516  BGEZ = ((0U << 3) + 1) << 16,
517  BLTZAL = ((2U << 3) + 0) << 16,
518  BGEZAL = ((2U << 3) + 1) << 16,
519  BGEZALL = ((2U << 3) + 3) << 16,
520  DAHI = ((0U << 3) + 6) << 16,
521  DATI = ((3U << 3) + 6) << 16,
522
523  // COP1 Encoding of rs Field.
524  MFC1 = ((0U << 3) + 0) << 21,
525  DMFC1 = ((0U << 3) + 1) << 21,
526  CFC1 = ((0U << 3) + 2) << 21,
527  MFHC1 = ((0U << 3) + 3) << 21,
528  MTC1 = ((0U << 3) + 4) << 21,
529  DMTC1 = ((0U << 3) + 5) << 21,
530  CTC1 = ((0U << 3) + 6) << 21,
531  MTHC1 = ((0U << 3) + 7) << 21,
532  BC1 = ((1U << 3) + 0) << 21,
533  S = ((2U << 3) + 0) << 21,
534  D = ((2U << 3) + 1) << 21,
535  W = ((2U << 3) + 4) << 21,
536  L = ((2U << 3) + 5) << 21,
537  PS = ((2U << 3) + 6) << 21,
538  // COP1 Encoding of Function Field When rs=S.
539
540  ADD_S = ((0U << 3) + 0),
541  SUB_S = ((0U << 3) + 1),
542  MUL_S = ((0U << 3) + 2),
543  DIV_S = ((0U << 3) + 3),
544  ABS_S = ((0U << 3) + 5),
545  SQRT_S = ((0U << 3) + 4),
546  MOV_S = ((0U << 3) + 6),
547  NEG_S = ((0U << 3) + 7),
548  ROUND_L_S = ((1U << 3) + 0),
549  TRUNC_L_S = ((1U << 3) + 1),
550  CEIL_L_S = ((1U << 3) + 2),
551  FLOOR_L_S = ((1U << 3) + 3),
552  ROUND_W_S = ((1U << 3) + 4),
553  TRUNC_W_S = ((1U << 3) + 5),
554  CEIL_W_S = ((1U << 3) + 6),
555  FLOOR_W_S = ((1U << 3) + 7),
556  RECIP_S = ((2U << 3) + 5),
557  RSQRT_S = ((2U << 3) + 6),
558  CLASS_S = ((3U << 3) + 3),
559  CVT_D_S = ((4U << 3) + 1),
560  CVT_W_S = ((4U << 3) + 4),
561  CVT_L_S = ((4U << 3) + 5),
562  CVT_PS_S = ((4U << 3) + 6),
563  // COP1 Encoding of Function Field When rs=D.
564  ADD_D = ((0U << 3) + 0),
565  SUB_D = ((0U << 3) + 1),
566  MUL_D = ((0U << 3) + 2),
567  DIV_D = ((0U << 3) + 3),
568  SQRT_D = ((0U << 3) + 4),
569  ABS_D = ((0U << 3) + 5),
570  MOV_D = ((0U << 3) + 6),
571  NEG_D = ((0U << 3) + 7),
572  ROUND_L_D = ((1U << 3) + 0),
573  TRUNC_L_D = ((1U << 3) + 1),
574  CEIL_L_D = ((1U << 3) + 2),
575  FLOOR_L_D = ((1U << 3) + 3),
576  ROUND_W_D = ((1U << 3) + 4),
577  TRUNC_W_D = ((1U << 3) + 5),
578  CEIL_W_D = ((1U << 3) + 6),
579  FLOOR_W_D = ((1U << 3) + 7),
580  RECIP_D = ((2U << 3) + 5),
581  RSQRT_D = ((2U << 3) + 6),
582  CLASS_D = ((3U << 3) + 3),
583  MIN = ((3U << 3) + 4),
584  MINA = ((3U << 3) + 5),
585  MAX = ((3U << 3) + 6),
586  MAXA = ((3U << 3) + 7),
587  CVT_S_D = ((4U << 3) + 0),
588  CVT_W_D = ((4U << 3) + 4),
589  CVT_L_D = ((4U << 3) + 5),
590  C_F_D = ((6U << 3) + 0),
591  C_UN_D = ((6U << 3) + 1),
592  C_EQ_D = ((6U << 3) + 2),
593  C_UEQ_D = ((6U << 3) + 3),
594  C_OLT_D = ((6U << 3) + 4),
595  C_ULT_D = ((6U << 3) + 5),
596  C_OLE_D = ((6U << 3) + 6),
597  C_ULE_D = ((6U << 3) + 7),
598
599  // COP1 Encoding of Function Field When rs=W or L.
600  CVT_S_W = ((4U << 3) + 0),
601  CVT_D_W = ((4U << 3) + 1),
602  CVT_S_L = ((4U << 3) + 0),
603  CVT_D_L = ((4U << 3) + 1),
604  BC1EQZ = ((2U << 2) + 1) << 21,
605  BC1NEZ = ((3U << 2) + 1) << 21,
606  // COP1 CMP positive predicates Bit 5..4 = 00.
607  CMP_AF = ((0U << 3) + 0),
608  CMP_UN = ((0U << 3) + 1),
609  CMP_EQ = ((0U << 3) + 2),
610  CMP_UEQ = ((0U << 3) + 3),
611  CMP_LT = ((0U << 3) + 4),
612  CMP_ULT = ((0U << 3) + 5),
613  CMP_LE = ((0U << 3) + 6),
614  CMP_ULE = ((0U << 3) + 7),
615  CMP_SAF = ((1U << 3) + 0),
616  CMP_SUN = ((1U << 3) + 1),
617  CMP_SEQ = ((1U << 3) + 2),
618  CMP_SUEQ = ((1U << 3) + 3),
619  CMP_SSLT = ((1U << 3) + 4),
620  CMP_SSULT = ((1U << 3) + 5),
621  CMP_SLE = ((1U << 3) + 6),
622  CMP_SULE = ((1U << 3) + 7),
623  // COP1 CMP negative predicates Bit 5..4 = 01.
624  CMP_AT = ((2U << 3) + 0),  // Reserved, not implemented.
625  CMP_OR = ((2U << 3) + 1),
626  CMP_UNE = ((2U << 3) + 2),
627  CMP_NE = ((2U << 3) + 3),
628  CMP_UGE = ((2U << 3) + 4),  // Reserved, not implemented.
629  CMP_OGE = ((2U << 3) + 5),  // Reserved, not implemented.
630  CMP_UGT = ((2U << 3) + 6),  // Reserved, not implemented.
631  CMP_OGT = ((2U << 3) + 7),  // Reserved, not implemented.
632  CMP_SAT = ((3U << 3) + 0),  // Reserved, not implemented.
633  CMP_SOR = ((3U << 3) + 1),
634  CMP_SUNE = ((3U << 3) + 2),
635  CMP_SNE = ((3U << 3) + 3),
636  CMP_SUGE = ((3U << 3) + 4),  // Reserved, not implemented.
637  CMP_SOGE = ((3U << 3) + 5),  // Reserved, not implemented.
638  CMP_SUGT = ((3U << 3) + 6),  // Reserved, not implemented.
639  CMP_SOGT = ((3U << 3) + 7),  // Reserved, not implemented.
640
641  SEL = ((2U << 3) + 0),
642  MOVF = ((2U << 3) + 1),      // Function field for MOVT.fmt and MOVF.fmt
643  MOVZ_C = ((2U << 3) + 2),    // COP1 on FPR registers.
644  MOVN_C = ((2U << 3) + 3),    // COP1 on FPR registers.
645  SELEQZ_C = ((2U << 3) + 4),  // COP1 on FPR registers.
646  SELNEZ_C = ((2U << 3) + 7),  // COP1 on FPR registers.
647
648  // COP1 Encoding of Function Field When rs=PS.
649  // COP1X Encoding of Function Field.
650  MADD_D = ((4U << 3) + 1),
651
652  // PCREL Encoding of rt Field.
653  ADDIUPC = ((0U << 2) + 0),
654  LWPC = ((0U << 2) + 1),
655  LWUPC = ((0U << 2) + 2),
656  LDPC = ((0U << 3) + 6),
657  // reserved ((1U << 3) + 6),
658  AUIPC = ((3U << 3) + 6),
659  ALUIPC = ((3U << 3) + 7),
660
661  // POP66 Encoding of rs Field.
662  JIC = ((0U << 5) + 0),
663
664  // POP76 Encoding of rs Field.
665  JIALC = ((0U << 5) + 0),
666
667  NULLSF = 0U
668};
669
670// ----- Emulated conditions.
671// On MIPS we use this enum to abstract from conditional branch instructions.
672// The 'U' prefix is used to specify unsigned comparisons.
673// Opposite conditions must be paired as odd/even numbers
674// because 'NegateCondition' function flips LSB to negate condition.
675enum Condition {
676  // Any value < 0 is considered no_condition.
677  kNoCondition = -1,
678  overflow = 0,
679  no_overflow = 1,
680  Uless = 2,
681  Ugreater_equal = 3,
682  Uless_equal = 4,
683  Ugreater = 5,
684  equal = 6,
685  not_equal = 7,  // Unordered or Not Equal.
686  negative = 8,
687  positive = 9,
688  parity_even = 10,
689  parity_odd = 11,
690  less = 12,
691  greater_equal = 13,
692  less_equal = 14,
693  greater = 15,
694  ueq = 16,  // Unordered or Equal.
695  ogl = 17,  // Ordered and Not Equal.
696  cc_always = 18,
697
698  // Aliases.
699  carry = Uless,
700  not_carry = Ugreater_equal,
701  zero = equal,
702  eq = equal,
703  not_zero = not_equal,
704  ne = not_equal,
705  nz = not_equal,
706  sign = negative,
707  not_sign = positive,
708  mi = negative,
709  pl = positive,
710  hi = Ugreater,
711  ls = Uless_equal,
712  ge = greater_equal,
713  lt = less,
714  gt = greater,
715  le = less_equal,
716  hs = Ugreater_equal,
717  lo = Uless,
718  al = cc_always,
719  ult = Uless,
720  uge = Ugreater_equal,
721  ule = Uless_equal,
722  ugt = Ugreater,
723  cc_default = kNoCondition
724};
725
726
727// Returns the equivalent of !cc.
728// Negation of the default kNoCondition (-1) results in a non-default
729// no_condition value (-2). As long as tests for no_condition check
730// for condition < 0, this will work as expected.
731inline Condition NegateCondition(Condition cc) {
732  DCHECK(cc != cc_always);
733  return static_cast<Condition>(cc ^ 1);
734}
735
736
737inline Condition NegateFpuCondition(Condition cc) {
738  DCHECK(cc != cc_always);
739  switch (cc) {
740    case ult:
741      return ge;
742    case ugt:
743      return le;
744    case uge:
745      return lt;
746    case ule:
747      return gt;
748    case lt:
749      return uge;
750    case gt:
751      return ule;
752    case ge:
753      return ult;
754    case le:
755      return ugt;
756    case eq:
757      return ne;
758    case ne:
759      return eq;
760    case ueq:
761      return ogl;
762    case ogl:
763      return ueq;
764    default:
765      return cc;
766  }
767}
768
769
770// Commute a condition such that {a cond b == b cond' a}.
771inline Condition CommuteCondition(Condition cc) {
772  switch (cc) {
773    case Uless:
774      return Ugreater;
775    case Ugreater:
776      return Uless;
777    case Ugreater_equal:
778      return Uless_equal;
779    case Uless_equal:
780      return Ugreater_equal;
781    case less:
782      return greater;
783    case greater:
784      return less;
785    case greater_equal:
786      return less_equal;
787    case less_equal:
788      return greater_equal;
789    default:
790      return cc;
791  }
792}
793
794
795// ----- Coprocessor conditions.
796enum FPUCondition {
797  kNoFPUCondition = -1,
798
799  F = 0x00,    // False.
800  UN = 0x01,   // Unordered.
801  EQ = 0x02,   // Equal.
802  UEQ = 0x03,  // Unordered or Equal.
803  OLT = 0x04,  // Ordered or Less Than, on Mips release < 6.
804  LT = 0x04,   // Ordered or Less Than, on Mips release >= 6.
805  ULT = 0x05,  // Unordered or Less Than.
806  OLE = 0x06,  // Ordered or Less Than or Equal, on Mips release < 6.
807  LE = 0x06,   // Ordered or Less Than or Equal, on Mips release >= 6.
808  ULE = 0x07,  // Unordered or Less Than or Equal.
809
810  // Following constants are available on Mips release >= 6 only.
811  ORD = 0x11,  // Ordered, on Mips release >= 6.
812  UNE = 0x12,  // Not equal, on Mips release >= 6.
813  NE = 0x13,   // Ordered Greater Than or Less Than. on Mips >= 6 only.
814};
815
816
817// FPU rounding modes.
818enum FPURoundingMode {
819  RN = 0 << 0,  // Round to Nearest.
820  RZ = 1 << 0,  // Round towards zero.
821  RP = 2 << 0,  // Round towards Plus Infinity.
822  RM = 3 << 0,  // Round towards Minus Infinity.
823
824  // Aliases.
825  kRoundToNearest = RN,
826  kRoundToZero = RZ,
827  kRoundToPlusInf = RP,
828  kRoundToMinusInf = RM,
829
830  mode_round = RN,
831  mode_ceil = RP,
832  mode_floor = RM,
833  mode_trunc = RZ
834};
835
836const uint32_t kFPURoundingModeMask = 3 << 0;
837
838enum CheckForInexactConversion {
839  kCheckForInexactConversion,
840  kDontCheckForInexactConversion
841};
842
843enum class MaxMinKind : int { kMin = 0, kMax = 1 };
844
845// -----------------------------------------------------------------------------
846// Hints.
847
848// Branch hints are not used on the MIPS.  They are defined so that they can
849// appear in shared function signatures, but will be ignored in MIPS
850// implementations.
851enum Hint {
852  no_hint = 0
853};
854
855
856inline Hint NegateHint(Hint hint) {
857  return no_hint;
858}
859
860
861// -----------------------------------------------------------------------------
862// Specific instructions, constants, and masks.
863// These constants are declared in assembler-mips.cc, as they use named
864// registers and other constants.
865
866// addiu(sp, sp, 4) aka Pop() operation or part of Pop(r)
867// operations as post-increment of sp.
868extern const Instr kPopInstruction;
869// addiu(sp, sp, -4) part of Push(r) operation as pre-decrement of sp.
870extern const Instr kPushInstruction;
871// sw(r, MemOperand(sp, 0))
872extern const Instr kPushRegPattern;
873// lw(r, MemOperand(sp, 0))
874extern const Instr kPopRegPattern;
875extern const Instr kLwRegFpOffsetPattern;
876extern const Instr kSwRegFpOffsetPattern;
877extern const Instr kLwRegFpNegOffsetPattern;
878extern const Instr kSwRegFpNegOffsetPattern;
879// A mask for the Rt register for push, pop, lw, sw instructions.
880extern const Instr kRtMask;
881extern const Instr kLwSwInstrTypeMask;
882extern const Instr kLwSwInstrArgumentMask;
883extern const Instr kLwSwOffsetMask;
884
885// Break 0xfffff, reserved for redirected real time call.
886const Instr rtCallRedirInstr = SPECIAL | BREAK | call_rt_redirected << 6;
887// A nop instruction. (Encoding of sll 0 0 0).
888const Instr nopInstr = 0;
889
890static constexpr uint64_t OpcodeToBitNumber(Opcode opcode) {
891  return 1ULL << (static_cast<uint32_t>(opcode) >> kOpcodeShift);
892}
893
894
895class Instruction {
896 public:
897  enum {
898    kInstrSize = 4,
899    kInstrSizeLog2 = 2,
900    // On MIPS PC cannot actually be directly accessed. We behave as if PC was
901    // always the value of the current instruction being executed.
902    kPCReadOffset = 0
903  };
904
905  // Get the raw instruction bits.
906  inline Instr InstructionBits() const {
907    return *reinterpret_cast<const Instr*>(this);
908  }
909
910  // Set the raw instruction bits to value.
911  inline void SetInstructionBits(Instr value) {
912    *reinterpret_cast<Instr*>(this) = value;
913  }
914
915  // Read one particular bit out of the instruction bits.
916  inline int Bit(int nr) const {
917    return (InstructionBits() >> nr) & 1;
918  }
919
920  // Read a bit field out of the instruction bits.
921  inline int Bits(int hi, int lo) const {
922    return (InstructionBits() >> lo) & ((2U << (hi - lo)) - 1);
923  }
924
925  // Instruction type.
926  enum Type {
927    kRegisterType,
928    kImmediateType,
929    kJumpType,
930    kUnsupported = -1
931  };
932
933  enum TypeChecks { NORMAL, EXTRA };
934
935  static constexpr uint64_t kOpcodeImmediateTypeMask =
936      OpcodeToBitNumber(REGIMM) | OpcodeToBitNumber(BEQ) |
937      OpcodeToBitNumber(BNE) | OpcodeToBitNumber(BLEZ) |
938      OpcodeToBitNumber(BGTZ) | OpcodeToBitNumber(ADDI) |
939      OpcodeToBitNumber(DADDI) | OpcodeToBitNumber(ADDIU) |
940      OpcodeToBitNumber(DADDIU) | OpcodeToBitNumber(SLTI) |
941      OpcodeToBitNumber(SLTIU) | OpcodeToBitNumber(ANDI) |
942      OpcodeToBitNumber(ORI) | OpcodeToBitNumber(XORI) |
943      OpcodeToBitNumber(LUI) | OpcodeToBitNumber(BEQL) |
944      OpcodeToBitNumber(BNEL) | OpcodeToBitNumber(BLEZL) |
945      OpcodeToBitNumber(BGTZL) | OpcodeToBitNumber(POP66) |
946      OpcodeToBitNumber(POP76) | OpcodeToBitNumber(LB) | OpcodeToBitNumber(LH) |
947      OpcodeToBitNumber(LWL) | OpcodeToBitNumber(LW) | OpcodeToBitNumber(LWU) |
948      OpcodeToBitNumber(LD) | OpcodeToBitNumber(LBU) | OpcodeToBitNumber(LHU) |
949      OpcodeToBitNumber(LDL) | OpcodeToBitNumber(LDR) | OpcodeToBitNumber(LWR) |
950      OpcodeToBitNumber(SDL) | OpcodeToBitNumber(SB) | OpcodeToBitNumber(SH) |
951      OpcodeToBitNumber(SWL) | OpcodeToBitNumber(SW) | OpcodeToBitNumber(SD) |
952      OpcodeToBitNumber(SWR) | OpcodeToBitNumber(SDR) |
953      OpcodeToBitNumber(LWC1) | OpcodeToBitNumber(LDC1) |
954      OpcodeToBitNumber(SWC1) | OpcodeToBitNumber(SDC1) |
955      OpcodeToBitNumber(PCREL) | OpcodeToBitNumber(DAUI) |
956      OpcodeToBitNumber(BC) | OpcodeToBitNumber(BALC);
957
958#define FunctionFieldToBitNumber(function) (1ULL << function)
959
960  // On r6, DCLZ_R6 aliases to existing MFLO.
961  static const uint64_t kFunctionFieldRegisterTypeMask =
962      FunctionFieldToBitNumber(JR) | FunctionFieldToBitNumber(JALR) |
963      FunctionFieldToBitNumber(BREAK) | FunctionFieldToBitNumber(SLL) |
964      FunctionFieldToBitNumber(DSLL) | FunctionFieldToBitNumber(DSLL32) |
965      FunctionFieldToBitNumber(SRL) | FunctionFieldToBitNumber(DSRL) |
966      FunctionFieldToBitNumber(DSRL32) | FunctionFieldToBitNumber(SRA) |
967      FunctionFieldToBitNumber(DSRA) | FunctionFieldToBitNumber(DSRA32) |
968      FunctionFieldToBitNumber(SLLV) | FunctionFieldToBitNumber(DSLLV) |
969      FunctionFieldToBitNumber(SRLV) | FunctionFieldToBitNumber(DSRLV) |
970      FunctionFieldToBitNumber(SRAV) | FunctionFieldToBitNumber(DSRAV) |
971      FunctionFieldToBitNumber(LSA) | FunctionFieldToBitNumber(DLSA) |
972      FunctionFieldToBitNumber(MFHI) | FunctionFieldToBitNumber(MFLO) |
973      FunctionFieldToBitNumber(MULT) | FunctionFieldToBitNumber(DMULT) |
974      FunctionFieldToBitNumber(MULTU) | FunctionFieldToBitNumber(DMULTU) |
975      FunctionFieldToBitNumber(DIV) | FunctionFieldToBitNumber(DDIV) |
976      FunctionFieldToBitNumber(DIVU) | FunctionFieldToBitNumber(DDIVU) |
977      FunctionFieldToBitNumber(ADD) | FunctionFieldToBitNumber(DADD) |
978      FunctionFieldToBitNumber(ADDU) | FunctionFieldToBitNumber(DADDU) |
979      FunctionFieldToBitNumber(SUB) | FunctionFieldToBitNumber(DSUB) |
980      FunctionFieldToBitNumber(SUBU) | FunctionFieldToBitNumber(DSUBU) |
981      FunctionFieldToBitNumber(AND) | FunctionFieldToBitNumber(OR) |
982      FunctionFieldToBitNumber(XOR) | FunctionFieldToBitNumber(NOR) |
983      FunctionFieldToBitNumber(SLT) | FunctionFieldToBitNumber(SLTU) |
984      FunctionFieldToBitNumber(TGE) | FunctionFieldToBitNumber(TGEU) |
985      FunctionFieldToBitNumber(TLT) | FunctionFieldToBitNumber(TLTU) |
986      FunctionFieldToBitNumber(TEQ) | FunctionFieldToBitNumber(TNE) |
987      FunctionFieldToBitNumber(MOVZ) | FunctionFieldToBitNumber(MOVN) |
988      FunctionFieldToBitNumber(MOVCI) | FunctionFieldToBitNumber(SELEQZ_S) |
989      FunctionFieldToBitNumber(SELNEZ_S) | FunctionFieldToBitNumber(SYNC);
990
991  // Get the encoding type of the instruction.
992  inline Type InstructionType(TypeChecks checks = NORMAL) const;
993
994
995  // Accessors for the different named fields used in the MIPS encoding.
996  inline Opcode OpcodeValue() const {
997    return static_cast<Opcode>(
998        Bits(kOpcodeShift + kOpcodeBits - 1, kOpcodeShift));
999  }
1000
1001  inline int RsValue() const {
1002    DCHECK(InstructionType() == kRegisterType ||
1003           InstructionType() == kImmediateType);
1004    return Bits(kRsShift + kRsBits - 1, kRsShift);
1005  }
1006
1007  inline int RtValue() const {
1008    DCHECK(InstructionType() == kRegisterType ||
1009           InstructionType() == kImmediateType);
1010    return Bits(kRtShift + kRtBits - 1, kRtShift);
1011  }
1012
1013  inline int RdValue() const {
1014    DCHECK(InstructionType() == kRegisterType);
1015    return Bits(kRdShift + kRdBits - 1, kRdShift);
1016  }
1017
1018  inline int SaValue() const {
1019    DCHECK(InstructionType() == kRegisterType);
1020    return Bits(kSaShift + kSaBits - 1, kSaShift);
1021  }
1022
1023  inline int LsaSaValue() const {
1024    DCHECK(InstructionType() == kRegisterType);
1025    return Bits(kSaShift + kLsaSaBits - 1, kSaShift);
1026  }
1027
1028  inline int FunctionValue() const {
1029    DCHECK(InstructionType() == kRegisterType ||
1030           InstructionType() == kImmediateType);
1031    return Bits(kFunctionShift + kFunctionBits - 1, kFunctionShift);
1032  }
1033
1034  inline int FdValue() const {
1035    return Bits(kFdShift + kFdBits - 1, kFdShift);
1036  }
1037
1038  inline int FsValue() const {
1039    return Bits(kFsShift + kFsBits - 1, kFsShift);
1040  }
1041
1042  inline int FtValue() const {
1043    return Bits(kFtShift + kFtBits - 1, kFtShift);
1044  }
1045
1046  inline int FrValue() const {
1047    return Bits(kFrShift + kFrBits -1, kFrShift);
1048  }
1049
1050  inline int Bp2Value() const {
1051    DCHECK(InstructionType() == kRegisterType);
1052    return Bits(kBp2Shift + kBp2Bits - 1, kBp2Shift);
1053  }
1054
1055  inline int Bp3Value() const {
1056    DCHECK(InstructionType() == kRegisterType);
1057    return Bits(kBp3Shift + kBp3Bits - 1, kBp3Shift);
1058  }
1059
1060  // Float Compare condition code instruction bits.
1061  inline int FCccValue() const {
1062    return Bits(kFCccShift + kFCccBits - 1, kFCccShift);
1063  }
1064
1065  // Float Branch condition code instruction bits.
1066  inline int FBccValue() const {
1067    return Bits(kFBccShift + kFBccBits - 1, kFBccShift);
1068  }
1069
1070  // Float Branch true/false instruction bit.
1071  inline int FBtrueValue() const {
1072    return Bits(kFBtrueShift + kFBtrueBits - 1, kFBtrueShift);
1073  }
1074
1075  // Return the fields at their original place in the instruction encoding.
1076  inline Opcode OpcodeFieldRaw() const {
1077    return static_cast<Opcode>(InstructionBits() & kOpcodeMask);
1078  }
1079
1080  inline int RsFieldRaw() const {
1081    DCHECK(InstructionType() == kRegisterType ||
1082           InstructionType() == kImmediateType);
1083    return InstructionBits() & kRsFieldMask;
1084  }
1085
1086  // Same as above function, but safe to call within InstructionType().
1087  inline int RsFieldRawNoAssert() const {
1088    return InstructionBits() & kRsFieldMask;
1089  }
1090
1091  inline int RtFieldRaw() const {
1092    DCHECK(InstructionType() == kRegisterType ||
1093           InstructionType() == kImmediateType);
1094    return InstructionBits() & kRtFieldMask;
1095  }
1096
1097  inline int RdFieldRaw() const {
1098    DCHECK(InstructionType() == kRegisterType);
1099    return InstructionBits() & kRdFieldMask;
1100  }
1101
1102  inline int SaFieldRaw() const {
1103    return InstructionBits() & kSaFieldMask;
1104  }
1105
1106  inline int FunctionFieldRaw() const {
1107    return InstructionBits() & kFunctionFieldMask;
1108  }
1109
1110  // Get the secondary field according to the opcode.
1111  inline int SecondaryValue() const {
1112    Opcode op = OpcodeFieldRaw();
1113    switch (op) {
1114      case SPECIAL:
1115      case SPECIAL2:
1116        return FunctionValue();
1117      case COP1:
1118        return RsValue();
1119      case REGIMM:
1120        return RtValue();
1121      default:
1122        return NULLSF;
1123    }
1124  }
1125
1126  inline int32_t ImmValue(int bits) const {
1127    DCHECK(InstructionType() == kImmediateType);
1128    return Bits(bits - 1, 0);
1129  }
1130
1131  inline int32_t Imm16Value() const {
1132    DCHECK(InstructionType() == kImmediateType);
1133    return Bits(kImm16Shift + kImm16Bits - 1, kImm16Shift);
1134  }
1135
1136  inline int32_t Imm18Value() const {
1137    DCHECK(InstructionType() == kImmediateType);
1138    return Bits(kImm18Shift + kImm18Bits - 1, kImm18Shift);
1139  }
1140
1141  inline int32_t Imm19Value() const {
1142    DCHECK(InstructionType() == kImmediateType);
1143    return Bits(kImm19Shift + kImm19Bits - 1, kImm19Shift);
1144  }
1145
1146  inline int32_t Imm21Value() const {
1147    DCHECK(InstructionType() == kImmediateType);
1148    return Bits(kImm21Shift + kImm21Bits - 1, kImm21Shift);
1149  }
1150
1151  inline int32_t Imm26Value() const {
1152    DCHECK((InstructionType() == kJumpType) ||
1153           (InstructionType() == kImmediateType));
1154    return Bits(kImm26Shift + kImm26Bits - 1, kImm26Shift);
1155  }
1156
1157  static bool IsForbiddenAfterBranchInstr(Instr instr);
1158
1159  // Say if the instruction should not be used in a branch delay slot or
1160  // immediately after a compact branch.
1161  inline bool IsForbiddenAfterBranch() const {
1162    return IsForbiddenAfterBranchInstr(InstructionBits());
1163  }
1164
1165  // Say if the instruction 'links'. e.g. jal, bal.
1166  bool IsLinkingInstruction() const;
1167  // Say if the instruction is a break or a trap.
1168  bool IsTrap() const;
1169
1170  // Instructions are read of out a code stream. The only way to get a
1171  // reference to an instruction is to convert a pointer. There is no way
1172  // to allocate or create instances of class Instruction.
1173  // Use the At(pc) function to create references to Instruction.
1174  static Instruction* At(byte* pc) {
1175    return reinterpret_cast<Instruction*>(pc);
1176  }
1177
1178 private:
1179  // We need to prevent the creation of instances of class Instruction.
1180  DISALLOW_IMPLICIT_CONSTRUCTORS(Instruction);
1181};
1182
1183
1184// -----------------------------------------------------------------------------
1185// MIPS assembly various constants.
1186
1187// C/C++ argument slots size.
1188const int kCArgSlotCount = 0;
1189
1190// TODO(plind): below should be based on kPointerSize
1191// TODO(plind): find all usages and remove the needless instructions for n64.
1192const int kCArgsSlotsSize = kCArgSlotCount * Instruction::kInstrSize * 2;
1193
1194const int kInvalidStackOffset = -1;
1195const int kBranchReturnOffset = 2 * Instruction::kInstrSize;
1196
1197
1198Instruction::Type Instruction::InstructionType(TypeChecks checks) const {
1199  if (checks == EXTRA) {
1200    if (OpcodeToBitNumber(OpcodeFieldRaw()) & kOpcodeImmediateTypeMask) {
1201      return kImmediateType;
1202    }
1203  }
1204  switch (OpcodeFieldRaw()) {
1205    case SPECIAL:
1206      if (checks == EXTRA) {
1207        if (FunctionFieldToBitNumber(FunctionFieldRaw()) &
1208            kFunctionFieldRegisterTypeMask) {
1209          return kRegisterType;
1210        } else {
1211          return kUnsupported;
1212        }
1213      } else {
1214        return kRegisterType;
1215      }
1216      break;
1217    case SPECIAL2:
1218      switch (FunctionFieldRaw()) {
1219        case MUL:
1220        case CLZ:
1221        case DCLZ:
1222          return kRegisterType;
1223        default:
1224          return kUnsupported;
1225      }
1226      break;
1227    case SPECIAL3:
1228      switch (FunctionFieldRaw()) {
1229        case INS:
1230        case DINS:
1231        case EXT:
1232        case DEXT:
1233        case DEXTM:
1234        case DEXTU:
1235          return kRegisterType;
1236        case BSHFL: {
1237          int sa = SaFieldRaw() >> kSaShift;
1238          switch (sa) {
1239            case BITSWAP:
1240            case WSBH:
1241            case SEB:
1242            case SEH:
1243              return kRegisterType;
1244          }
1245          sa >>= kBp2Bits;
1246          switch (sa) {
1247            case ALIGN:
1248              return kRegisterType;
1249            default:
1250              return kUnsupported;
1251          }
1252        }
1253        case DBSHFL: {
1254          int sa = SaFieldRaw() >> kSaShift;
1255          switch (sa) {
1256            case DBITSWAP:
1257            case DSBH:
1258            case DSHD:
1259              return kRegisterType;
1260          }
1261          sa = SaFieldRaw() >> kSaShift;
1262          sa >>= kBp3Bits;
1263          switch (sa) {
1264            case DALIGN:
1265              return kRegisterType;
1266            default:
1267              return kUnsupported;
1268          }
1269        }
1270        default:
1271          return kUnsupported;
1272      }
1273      break;
1274    case COP1:  // Coprocessor instructions.
1275      switch (RsFieldRawNoAssert()) {
1276        case BC1:  // Branch on coprocessor condition.
1277        case BC1EQZ:
1278        case BC1NEZ:
1279          return kImmediateType;
1280        default:
1281          return kRegisterType;
1282      }
1283      break;
1284    case COP1X:
1285      return kRegisterType;
1286
1287    // 26 bits immediate type instructions. e.g.: j imm26.
1288    case J:
1289    case JAL:
1290      return kJumpType;
1291
1292    default:
1293      if (checks == NORMAL) {
1294        return kImmediateType;
1295      } else {
1296        return kUnsupported;
1297      }
1298  }
1299  return kUnsupported;
1300}
1301
1302#undef OpcodeToBitNumber
1303#undef FunctionFieldToBitNumber
1304}  // namespace internal
1305}  // namespace v8
1306
1307#endif    // #ifndef V8_MIPS_CONSTANTS_H_
1308