13233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org// Copyright 2012 the V8 project authors. All rights reserved.
25c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Redistribution and use in source and binary forms, with or without
35c838251403b0be9a882540f1922577abba4c872ager@chromium.org// modification, are permitted provided that the following conditions are
45c838251403b0be9a882540f1922577abba4c872ager@chromium.org// met:
55c838251403b0be9a882540f1922577abba4c872ager@chromium.org//
65c838251403b0be9a882540f1922577abba4c872ager@chromium.org//     * Redistributions of source code must retain the above copyright
75c838251403b0be9a882540f1922577abba4c872ager@chromium.org//       notice, this list of conditions and the following disclaimer.
85c838251403b0be9a882540f1922577abba4c872ager@chromium.org//     * Redistributions in binary form must reproduce the above
95c838251403b0be9a882540f1922577abba4c872ager@chromium.org//       copyright notice, this list of conditions and the following
105c838251403b0be9a882540f1922577abba4c872ager@chromium.org//       disclaimer in the documentation and/or other materials provided
115c838251403b0be9a882540f1922577abba4c872ager@chromium.org//       with the distribution.
125c838251403b0be9a882540f1922577abba4c872ager@chromium.org//     * Neither the name of Google Inc. nor the names of its
135c838251403b0be9a882540f1922577abba4c872ager@chromium.org//       contributors may be used to endorse or promote products derived
145c838251403b0be9a882540f1922577abba4c872ager@chromium.org//       from this software without specific prior written permission.
155c838251403b0be9a882540f1922577abba4c872ager@chromium.org//
165c838251403b0be9a882540f1922577abba4c872ager@chromium.org// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
175c838251403b0be9a882540f1922577abba4c872ager@chromium.org// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
185c838251403b0be9a882540f1922577abba4c872ager@chromium.org// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
195c838251403b0be9a882540f1922577abba4c872ager@chromium.org// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
205c838251403b0be9a882540f1922577abba4c872ager@chromium.org// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
215c838251403b0be9a882540f1922577abba4c872ager@chromium.org// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
225c838251403b0be9a882540f1922577abba4c872ager@chromium.org// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
235c838251403b0be9a882540f1922577abba4c872ager@chromium.org// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
245c838251403b0be9a882540f1922577abba4c872ager@chromium.org// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
255c838251403b0be9a882540f1922577abba4c872ager@chromium.org// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
265c838251403b0be9a882540f1922577abba4c872ager@chromium.org// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
275c838251403b0be9a882540f1922577abba4c872ager@chromium.org
285c838251403b0be9a882540f1922577abba4c872ager@chromium.org#ifndef  V8_MIPS_CONSTANTS_H_
295c838251403b0be9a882540f1922577abba4c872ager@chromium.org#define  V8_MIPS_CONSTANTS_H_
305c838251403b0be9a882540f1922577abba4c872ager@chromium.org
315c838251403b0be9a882540f1922577abba4c872ager@chromium.org// UNIMPLEMENTED_ macro for MIPS.
327516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org#ifdef DEBUG
335c838251403b0be9a882540f1922577abba4c872ager@chromium.org#define UNIMPLEMENTED_MIPS()                                                  \
345c838251403b0be9a882540f1922577abba4c872ager@chromium.org  v8::internal::PrintF("%s, \tline %d: \tfunction %s not implemented. \n",    \
355c838251403b0be9a882540f1922577abba4c872ager@chromium.org                       __FILE__, __LINE__, __func__)
367516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org#else
377516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org#define UNIMPLEMENTED_MIPS()
387516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org#endif
397516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
405c838251403b0be9a882540f1922577abba4c872ager@chromium.org#define UNSUPPORTED_MIPS() v8::internal::PrintF("Unsupported instruction.\n")
415c838251403b0be9a882540f1922577abba4c872ager@chromium.org
423233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.orgenum ArchVariants {
433233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org  kMips32r2,
443233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org  kMips32r1,
453233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org  kLoongson
463233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org};
475c838251403b0be9a882540f1922577abba4c872ager@chromium.org
487516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org#ifdef _MIPS_ARCH_MIPS32R2
493233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org  static const ArchVariants kArchVariant = kMips32r2;
503233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org#elif _MIPS_ARCH_LOONGSON
513233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org// The loongson flag refers to the LOONGSON architectures based on MIPS-III,
523233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org// which predates (and is a subset of) the mips32r2 and r1 architectures.
533233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org  static const ArchVariants kArchVariant = kLoongson;
547516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org#else
553233d2f30cad1f77ff9f43fcbee12f182b18f6b6mstarzinger@chromium.org  static const ArchVariants kArchVariant = kMips32r1;
567516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org#endif
577516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
587516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
5940cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org#if(defined(__mips_hard_float) && __mips_hard_float != 0)
6040cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org// Use floating-point coprocessor instructions. This flag is raised when
6140cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org// -mhard-float is passed to the compiler.
621b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst bool IsMipsSoftFloatABI = false;
6340cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org#elif(defined(__mips_soft_float) && __mips_soft_float != 0)
64e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org// This flag is raised when -msoft-float is passed to the compiler.
65e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org// Although FPU is a base requirement for v8, soft-float ABI is used
66e27d617298263725e8a48c2aa14029759b952623mstarzinger@chromium.org// on soft-float systems with FPU kernel emulation.
671b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst bool IsMipsSoftFloatABI = true;
6840cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org#else
691b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst bool IsMipsSoftFloatABI = true;
7040cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org#endif
7140cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org
7240cb878ef373bea9bdf7998829891e4096751dd0danno@chromium.org
735c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Defines constants and accessor classes to assemble, disassemble and
745c838251403b0be9a882540f1922577abba4c872ager@chromium.org// simulate MIPS32 instructions.
755c838251403b0be9a882540f1922577abba4c872ager@chromium.org//
765c838251403b0be9a882540f1922577abba4c872ager@chromium.org// See: MIPS32 Architecture For Programmers
775c838251403b0be9a882540f1922577abba4c872ager@chromium.org//      Volume II: The MIPS32 Instruction Set
785c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Try www.cs.cornell.edu/courses/cs3410/2008fa/MIPS_Vol2.pdf.
795c838251403b0be9a882540f1922577abba4c872ager@chromium.org
807516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgnamespace v8 {
817516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgnamespace internal {
825c838251403b0be9a882540f1922577abba4c872ager@chromium.org
835c838251403b0be9a882540f1922577abba4c872ager@chromium.org// -----------------------------------------------------------------------------
8483a4728861129dc263ded92157f3e6389f851f19karlklose@chromium.org// Registers and FPURegisters.
855c838251403b0be9a882540f1922577abba4c872ager@chromium.org
865c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Number of general purpose registers.
871b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kNumRegisters = 32;
881b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kInvalidRegister = -1;
895c838251403b0be9a882540f1922577abba4c872ager@chromium.org
905c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Number of registers with HI, LO, and pc.
911b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kNumSimuRegisters = 35;
925c838251403b0be9a882540f1922577abba4c872ager@chromium.org
935c838251403b0be9a882540f1922577abba4c872ager@chromium.org// In the simulator, the PC register is simulated as the 34th register.
941b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kPCRegister = 34;
955c838251403b0be9a882540f1922577abba4c872ager@chromium.org
965c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Number coprocessor registers.
971b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kNumFPURegisters = 32;
981b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kInvalidFPURegister = -1;
995c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1007516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// FPU (coprocessor 1) control registers. Currently only FCSR is implemented.
1011b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFCSRRegister = 31;
1021b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kInvalidFPUControlRegister = -1;
10359297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.orgconst uint32_t kFPUInvalidResult = static_cast<uint32_t>(1 << 31) - 1;
1047516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
1057516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// FCSR constants.
1061b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSRInexactFlagBit = 2;
1071b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSRUnderflowFlagBit = 3;
1081b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSROverflowFlagBit = 4;
1091b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSRDivideByZeroFlagBit = 5;
1101b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSRInvalidOpFlagBit = 6;
1111b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.org
1121b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSRInexactFlagMask = 1 << kFCSRInexactFlagBit;
1131b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSRUnderflowFlagMask = 1 << kFCSRUnderflowFlagBit;
1141b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSROverflowFlagMask = 1 << kFCSROverflowFlagBit;
1151b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSRDivideByZeroFlagMask = 1 << kFCSRDivideByZeroFlagBit;
1161b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSRInvalidOpFlagMask = 1 << kFCSRInvalidOpFlagBit;
1171b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.org
1181b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSRFlagMask =
119d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com    kFCSRInexactFlagMask |
120d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com    kFCSRUnderflowFlagMask |
121d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com    kFCSROverflowFlagMask |
122d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com    kFCSRDivideByZeroFlagMask |
123d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com    kFCSRInvalidOpFlagMask;
124d6076d96a1411932548838e5960b594564264010erik.corry@gmail.com
1251b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFCSRExceptionFlagMask = kFCSRFlagMask ^ kFCSRInexactFlagMask;
1267516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
1275c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Helper functions for converting between register numbers and names.
1285c838251403b0be9a882540f1922577abba4c872ager@chromium.orgclass Registers {
1295c838251403b0be9a882540f1922577abba4c872ager@chromium.org public:
1305c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Return the name of the register.
1315c838251403b0be9a882540f1922577abba4c872ager@chromium.org  static const char* Name(int reg);
1325c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1335c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Lookup the register number for the name provided.
1345c838251403b0be9a882540f1922577abba4c872ager@chromium.org  static int Number(const char* name);
1355c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1365c838251403b0be9a882540f1922577abba4c872ager@chromium.org  struct RegisterAlias {
1375c838251403b0be9a882540f1922577abba4c872ager@chromium.org    int reg;
138f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com    const char* name;
1395c838251403b0be9a882540f1922577abba4c872ager@chromium.org  };
1405c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1415c838251403b0be9a882540f1922577abba4c872ager@chromium.org  static const int32_t kMaxValue = 0x7fffffff;
1425c838251403b0be9a882540f1922577abba4c872ager@chromium.org  static const int32_t kMinValue = 0x80000000;
1435c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1445c838251403b0be9a882540f1922577abba4c872ager@chromium.org private:
1455c838251403b0be9a882540f1922577abba4c872ager@chromium.org  static const char* names_[kNumSimuRegisters];
1465c838251403b0be9a882540f1922577abba4c872ager@chromium.org  static const RegisterAlias aliases_[];
1475c838251403b0be9a882540f1922577abba4c872ager@chromium.org};
1485c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1495c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Helper functions for converting between register numbers and names.
1507516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgclass FPURegisters {
1515c838251403b0be9a882540f1922577abba4c872ager@chromium.org public:
1525c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Return the name of the register.
1535c838251403b0be9a882540f1922577abba4c872ager@chromium.org  static const char* Name(int reg);
1545c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1555c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Lookup the register number for the name provided.
1565c838251403b0be9a882540f1922577abba4c872ager@chromium.org  static int Number(const char* name);
1575c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1585c838251403b0be9a882540f1922577abba4c872ager@chromium.org  struct RegisterAlias {
1595c838251403b0be9a882540f1922577abba4c872ager@chromium.org    int creg;
160f2038fb01417bcf7698b87a5dfaa4a861539618aerik.corry@gmail.com    const char* name;
1615c838251403b0be9a882540f1922577abba4c872ager@chromium.org  };
1625c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1635c838251403b0be9a882540f1922577abba4c872ager@chromium.org private:
1647516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  static const char* names_[kNumFPURegisters];
1655c838251403b0be9a882540f1922577abba4c872ager@chromium.org  static const RegisterAlias aliases_[];
1665c838251403b0be9a882540f1922577abba4c872ager@chromium.org};
1675c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1685c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1695c838251403b0be9a882540f1922577abba4c872ager@chromium.org// -----------------------------------------------------------------------------
1705c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Instructions encoding constants.
1715c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1725c838251403b0be9a882540f1922577abba4c872ager@chromium.org// On MIPS all instructions are 32 bits.
1735c838251403b0be9a882540f1922577abba4c872ager@chromium.orgtypedef int32_t Instr;
1745c838251403b0be9a882540f1922577abba4c872ager@chromium.org
1755c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Special Software Interrupt codes when used in the presence of the MIPS
1765c838251403b0be9a882540f1922577abba4c872ager@chromium.org// simulator.
1775c838251403b0be9a882540f1922577abba4c872ager@chromium.orgenum SoftwareInterruptCodes {
1785c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Transition to C code.
1795c838251403b0be9a882540f1922577abba4c872ager@chromium.org  call_rt_redirected = 0xfffff
1805c838251403b0be9a882540f1922577abba4c872ager@chromium.org};
1815c838251403b0be9a882540f1922577abba4c872ager@chromium.org
182c54d36599f1e72bddd09d5b7a980304c7b638048ricow@chromium.org// On MIPS Simulator breakpoints can have different codes:
183c54d36599f1e72bddd09d5b7a980304c7b638048ricow@chromium.org// - Breaks between 0 and kMaxWatchpointCode are treated as simple watchpoints,
184c54d36599f1e72bddd09d5b7a980304c7b638048ricow@chromium.org//   the simulator will run through them and print the registers.
185c54d36599f1e72bddd09d5b7a980304c7b638048ricow@chromium.org// - Breaks between kMaxWatchpointCode and kMaxStopCode are treated as stop()
186c54d36599f1e72bddd09d5b7a980304c7b638048ricow@chromium.org//   instructions (see Assembler::stop()).
187c54d36599f1e72bddd09d5b7a980304c7b638048ricow@chromium.org// - Breaks larger than kMaxStopCode are simple breaks, dropping you into the
188c54d36599f1e72bddd09d5b7a980304c7b638048ricow@chromium.org//   debugger.
1891b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kMaxWatchpointCode = 31;
1901b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kMaxStopCode = 127;
191c54d36599f1e72bddd09d5b7a980304c7b638048ricow@chromium.orgSTATIC_ASSERT(kMaxWatchpointCode < kMaxStopCode);
192c54d36599f1e72bddd09d5b7a980304c7b638048ricow@chromium.org
193c54d36599f1e72bddd09d5b7a980304c7b638048ricow@chromium.org
1945c838251403b0be9a882540f1922577abba4c872ager@chromium.org// ----- Fields offset and length.
1951b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kOpcodeShift   = 26;
1961b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kOpcodeBits    = 6;
1971b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kRsShift       = 21;
1981b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kRsBits        = 5;
1991b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kRtShift       = 16;
2001b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kRtBits        = 5;
2011b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kRdShift       = 11;
2021b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kRdBits        = 5;
2031b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kSaShift       = 6;
2041b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kSaBits        = 5;
2051b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFunctionShift = 0;
2061b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFunctionBits  = 6;
2071b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kLuiShift      = 16;
2081b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.org
2091b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kImm16Shift = 0;
2101b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kImm16Bits  = 16;
2111b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kImm26Shift = 0;
2121b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kImm26Bits  = 26;
2131b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kImm28Shift = 0;
2141b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kImm28Bits  = 28;
2155c838251403b0be9a882540f1922577abba4c872ager@chromium.org
21634e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org// In branches and jumps immediate fields point to words, not bytes,
21734e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org// and are therefore shifted by 2.
2181b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kImmFieldShift = 2;
2191b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.org
22059297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.orgconst int kFrBits        = 5;
22159297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.orgconst int kFrShift       = 21;
2221b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFsShift       = 11;
2231b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFsBits        = 5;
2241b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFtShift       = 16;
2251b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFtBits        = 5;
2261b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFdShift       = 6;
2271b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFdBits        = 5;
2281b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFCccShift     = 8;
2291b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFCccBits      = 3;
2301b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFBccShift     = 18;
2311b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFBccBits      = 3;
2321b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFBtrueShift   = 16;
2331b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kFBtrueBits    = 1;
2345c838251403b0be9a882540f1922577abba4c872ager@chromium.org
23583a4728861129dc263ded92157f3e6389f851f19karlklose@chromium.org// ----- Miscellaneous useful masks.
2365c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Instruction bit masks.
2371b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kOpcodeMask   = ((1 << kOpcodeBits) - 1) << kOpcodeShift;
2381b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kImm16Mask    = ((1 << kImm16Bits) - 1) << kImm16Shift;
2391b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kImm26Mask    = ((1 << kImm26Bits) - 1) << kImm26Shift;
2401b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kImm28Mask    = ((1 << kImm28Bits) - 1) << kImm28Shift;
2411b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kRsFieldMask  = ((1 << kRsBits) - 1) << kRsShift;
2421b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kRtFieldMask  = ((1 << kRtBits) - 1) << kRtShift;
2431b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kRdFieldMask  = ((1 << kRdBits) - 1) << kRdShift;
2441b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kSaFieldMask  = ((1 << kSaBits) - 1) << kSaShift;
2451b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kFunctionFieldMask = ((1 << kFunctionBits) - 1) << kFunctionShift;
2465c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Misc masks.
2471b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kHiMask       =   0xffff << 16;
2481b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kLoMask       =   0xffff;
2491b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kSignMask     =   0x80000000;
2501b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int  kJumpAddrMask = (1 << (kImm26Bits + kImmFieldShift)) - 1;
2515c838251403b0be9a882540f1922577abba4c872ager@chromium.org
2525c838251403b0be9a882540f1922577abba4c872ager@chromium.org// ----- MIPS Opcodes and Function Fields.
2535c838251403b0be9a882540f1922577abba4c872ager@chromium.org// We use this presentation to stay close to the table representation in
2545c838251403b0be9a882540f1922577abba4c872ager@chromium.org// MIPS32 Architecture For Programmers, Volume II: The MIPS32 Instruction Set.
2555c838251403b0be9a882540f1922577abba4c872ager@chromium.orgenum Opcode {
2565c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SPECIAL   =   0 << kOpcodeShift,
2575c838251403b0be9a882540f1922577abba4c872ager@chromium.org  REGIMM    =   1 << kOpcodeShift,
2585c838251403b0be9a882540f1922577abba4c872ager@chromium.org
2595c838251403b0be9a882540f1922577abba4c872ager@chromium.org  J         =   ((0 << 3) + 2) << kOpcodeShift,
2605c838251403b0be9a882540f1922577abba4c872ager@chromium.org  JAL       =   ((0 << 3) + 3) << kOpcodeShift,
2615c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BEQ       =   ((0 << 3) + 4) << kOpcodeShift,
2625c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BNE       =   ((0 << 3) + 5) << kOpcodeShift,
2635c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BLEZ      =   ((0 << 3) + 6) << kOpcodeShift,
2645c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BGTZ      =   ((0 << 3) + 7) << kOpcodeShift,
2655c838251403b0be9a882540f1922577abba4c872ager@chromium.org
2665c838251403b0be9a882540f1922577abba4c872ager@chromium.org  ADDI      =   ((1 << 3) + 0) << kOpcodeShift,
2675c838251403b0be9a882540f1922577abba4c872ager@chromium.org  ADDIU     =   ((1 << 3) + 1) << kOpcodeShift,
2685c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SLTI      =   ((1 << 3) + 2) << kOpcodeShift,
2695c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SLTIU     =   ((1 << 3) + 3) << kOpcodeShift,
2705c838251403b0be9a882540f1922577abba4c872ager@chromium.org  ANDI      =   ((1 << 3) + 4) << kOpcodeShift,
2715c838251403b0be9a882540f1922577abba4c872ager@chromium.org  ORI       =   ((1 << 3) + 5) << kOpcodeShift,
2725c838251403b0be9a882540f1922577abba4c872ager@chromium.org  XORI      =   ((1 << 3) + 6) << kOpcodeShift,
2735c838251403b0be9a882540f1922577abba4c872ager@chromium.org  LUI       =   ((1 << 3) + 7) << kOpcodeShift,
2745c838251403b0be9a882540f1922577abba4c872ager@chromium.org
27583a4728861129dc263ded92157f3e6389f851f19karlklose@chromium.org  COP1      =   ((2 << 3) + 1) << kOpcodeShift,  // Coprocessor 1 class.
2765c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BEQL      =   ((2 << 3) + 4) << kOpcodeShift,
2775c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BNEL      =   ((2 << 3) + 5) << kOpcodeShift,
2785c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BLEZL     =   ((2 << 3) + 6) << kOpcodeShift,
2795c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BGTZL     =   ((2 << 3) + 7) << kOpcodeShift,
2805c838251403b0be9a882540f1922577abba4c872ager@chromium.org
2815c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SPECIAL2  =   ((3 << 3) + 4) << kOpcodeShift,
2827516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  SPECIAL3  =   ((3 << 3) + 7) << kOpcodeShift,
2835c838251403b0be9a882540f1922577abba4c872ager@chromium.org
2845c838251403b0be9a882540f1922577abba4c872ager@chromium.org  LB        =   ((4 << 3) + 0) << kOpcodeShift,
2857516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  LH        =   ((4 << 3) + 1) << kOpcodeShift,
2867516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  LWL       =   ((4 << 3) + 2) << kOpcodeShift,
2875c838251403b0be9a882540f1922577abba4c872ager@chromium.org  LW        =   ((4 << 3) + 3) << kOpcodeShift,
2885c838251403b0be9a882540f1922577abba4c872ager@chromium.org  LBU       =   ((4 << 3) + 4) << kOpcodeShift,
2897516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  LHU       =   ((4 << 3) + 5) << kOpcodeShift,
2907516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  LWR       =   ((4 << 3) + 6) << kOpcodeShift,
2915c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SB        =   ((5 << 3) + 0) << kOpcodeShift,
2927516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  SH        =   ((5 << 3) + 1) << kOpcodeShift,
2937516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  SWL       =   ((5 << 3) + 2) << kOpcodeShift,
2945c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SW        =   ((5 << 3) + 3) << kOpcodeShift,
2957516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  SWR       =   ((5 << 3) + 6) << kOpcodeShift,
2965c838251403b0be9a882540f1922577abba4c872ager@chromium.org
2975c838251403b0be9a882540f1922577abba4c872ager@chromium.org  LWC1      =   ((6 << 3) + 1) << kOpcodeShift,
2985c838251403b0be9a882540f1922577abba4c872ager@chromium.org  LDC1      =   ((6 << 3) + 5) << kOpcodeShift,
2995c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3005c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SWC1      =   ((7 << 3) + 1) << kOpcodeShift,
30159297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org  SDC1      =   ((7 << 3) + 5) << kOpcodeShift,
30259297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org
30359297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org  COP1X     =   ((1 << 4) + 3) << kOpcodeShift
3045c838251403b0be9a882540f1922577abba4c872ager@chromium.org};
3055c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3065c838251403b0be9a882540f1922577abba4c872ager@chromium.orgenum SecondaryField {
3075c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // SPECIAL Encoding of Function Field.
3085c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SLL       =   ((0 << 3) + 0),
30934e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  MOVCI     =   ((0 << 3) + 1),
3105c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SRL       =   ((0 << 3) + 2),
3115c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SRA       =   ((0 << 3) + 3),
3125c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SLLV      =   ((0 << 3) + 4),
3135c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SRLV      =   ((0 << 3) + 6),
3145c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SRAV      =   ((0 << 3) + 7),
3155c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3165c838251403b0be9a882540f1922577abba4c872ager@chromium.org  JR        =   ((1 << 3) + 0),
3175c838251403b0be9a882540f1922577abba4c872ager@chromium.org  JALR      =   ((1 << 3) + 1),
3187516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  MOVZ      =   ((1 << 3) + 2),
3197516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  MOVN      =   ((1 << 3) + 3),
3205c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BREAK     =   ((1 << 3) + 5),
3215c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3225c838251403b0be9a882540f1922577abba4c872ager@chromium.org  MFHI      =   ((2 << 3) + 0),
3235c838251403b0be9a882540f1922577abba4c872ager@chromium.org  MFLO      =   ((2 << 3) + 2),
3245c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3255c838251403b0be9a882540f1922577abba4c872ager@chromium.org  MULT      =   ((3 << 3) + 0),
3265c838251403b0be9a882540f1922577abba4c872ager@chromium.org  MULTU     =   ((3 << 3) + 1),
3275c838251403b0be9a882540f1922577abba4c872ager@chromium.org  DIV       =   ((3 << 3) + 2),
3285c838251403b0be9a882540f1922577abba4c872ager@chromium.org  DIVU      =   ((3 << 3) + 3),
3295c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3305c838251403b0be9a882540f1922577abba4c872ager@chromium.org  ADD       =   ((4 << 3) + 0),
3315c838251403b0be9a882540f1922577abba4c872ager@chromium.org  ADDU      =   ((4 << 3) + 1),
3325c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SUB       =   ((4 << 3) + 2),
3335c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SUBU      =   ((4 << 3) + 3),
3345c838251403b0be9a882540f1922577abba4c872ager@chromium.org  AND       =   ((4 << 3) + 4),
3355c838251403b0be9a882540f1922577abba4c872ager@chromium.org  OR        =   ((4 << 3) + 5),
3365c838251403b0be9a882540f1922577abba4c872ager@chromium.org  XOR       =   ((4 << 3) + 6),
3375c838251403b0be9a882540f1922577abba4c872ager@chromium.org  NOR       =   ((4 << 3) + 7),
3385c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3395c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SLT       =   ((5 << 3) + 2),
3405c838251403b0be9a882540f1922577abba4c872ager@chromium.org  SLTU      =   ((5 << 3) + 3),
3415c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3425c838251403b0be9a882540f1922577abba4c872ager@chromium.org  TGE       =   ((6 << 3) + 0),
3435c838251403b0be9a882540f1922577abba4c872ager@chromium.org  TGEU      =   ((6 << 3) + 1),
3445c838251403b0be9a882540f1922577abba4c872ager@chromium.org  TLT       =   ((6 << 3) + 2),
3455c838251403b0be9a882540f1922577abba4c872ager@chromium.org  TLTU      =   ((6 << 3) + 3),
3465c838251403b0be9a882540f1922577abba4c872ager@chromium.org  TEQ       =   ((6 << 3) + 4),
3475c838251403b0be9a882540f1922577abba4c872ager@chromium.org  TNE       =   ((6 << 3) + 6),
3485c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3495c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // SPECIAL2 Encoding of Function Field.
3505c838251403b0be9a882540f1922577abba4c872ager@chromium.org  MUL       =   ((0 << 3) + 2),
3517516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  CLZ       =   ((4 << 3) + 0),
3527516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  CLO       =   ((4 << 3) + 1),
3537516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
3547516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  // SPECIAL3 Encoding of Function Field.
3557516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  EXT       =   ((0 << 3) + 0),
3567516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  INS       =   ((0 << 3) + 4),
3575c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3585c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // REGIMM  encoding of rt Field.
3595c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BLTZ      =   ((0 << 3) + 0) << 16,
3605c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BGEZ      =   ((0 << 3) + 1) << 16,
3615c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BLTZAL    =   ((2 << 3) + 0) << 16,
3625c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BGEZAL    =   ((2 << 3) + 1) << 16,
3635c838251403b0be9a882540f1922577abba4c872ager@chromium.org
3645c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // COP1 Encoding of rs Field.
3655c838251403b0be9a882540f1922577abba4c872ager@chromium.org  MFC1      =   ((0 << 3) + 0) << 21,
3667516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  CFC1      =   ((0 << 3) + 2) << 21,
3675c838251403b0be9a882540f1922577abba4c872ager@chromium.org  MFHC1     =   ((0 << 3) + 3) << 21,
3685c838251403b0be9a882540f1922577abba4c872ager@chromium.org  MTC1      =   ((0 << 3) + 4) << 21,
3697516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  CTC1      =   ((0 << 3) + 6) << 21,
3705c838251403b0be9a882540f1922577abba4c872ager@chromium.org  MTHC1     =   ((0 << 3) + 7) << 21,
3715c838251403b0be9a882540f1922577abba4c872ager@chromium.org  BC1       =   ((1 << 3) + 0) << 21,
3725c838251403b0be9a882540f1922577abba4c872ager@chromium.org  S         =   ((2 << 3) + 0) << 21,
3735c838251403b0be9a882540f1922577abba4c872ager@chromium.org  D         =   ((2 << 3) + 1) << 21,
3745c838251403b0be9a882540f1922577abba4c872ager@chromium.org  W         =   ((2 << 3) + 4) << 21,
3755c838251403b0be9a882540f1922577abba4c872ager@chromium.org  L         =   ((2 << 3) + 5) << 21,
3765c838251403b0be9a882540f1922577abba4c872ager@chromium.org  PS        =   ((2 << 3) + 6) << 21,
3775c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // COP1 Encoding of Function Field When rs=S.
3787516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  ROUND_L_S =   ((1 << 3) + 0),
3797516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  TRUNC_L_S =   ((1 << 3) + 1),
3807516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  CEIL_L_S  =   ((1 << 3) + 2),
3817516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  FLOOR_L_S =   ((1 << 3) + 3),
3827516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  ROUND_W_S =   ((1 << 3) + 4),
3837516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  TRUNC_W_S =   ((1 << 3) + 5),
3847516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  CEIL_W_S  =   ((1 << 3) + 6),
3857516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  FLOOR_W_S =   ((1 << 3) + 7),
3865c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_D_S   =   ((4 << 3) + 1),
3875c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_W_S   =   ((4 << 3) + 4),
3885c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_L_S   =   ((4 << 3) + 5),
3895c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_PS_S  =   ((4 << 3) + 6),
3905c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // COP1 Encoding of Function Field When rs=D.
3917516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  ADD_D     =   ((0 << 3) + 0),
3927516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  SUB_D     =   ((0 << 3) + 1),
3937516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  MUL_D     =   ((0 << 3) + 2),
3947516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  DIV_D     =   ((0 << 3) + 3),
3957516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  SQRT_D    =   ((0 << 3) + 4),
3967516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  ABS_D     =   ((0 << 3) + 5),
3977516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  MOV_D     =   ((0 << 3) + 6),
3987516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  NEG_D     =   ((0 << 3) + 7),
3997516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  ROUND_L_D =   ((1 << 3) + 0),
4007516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  TRUNC_L_D =   ((1 << 3) + 1),
4017516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  CEIL_L_D  =   ((1 << 3) + 2),
4027516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  FLOOR_L_D =   ((1 << 3) + 3),
4037516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  ROUND_W_D =   ((1 << 3) + 4),
4047516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  TRUNC_W_D =   ((1 << 3) + 5),
4057516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  CEIL_W_D  =   ((1 << 3) + 6),
4067516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  FLOOR_W_D =   ((1 << 3) + 7),
4075c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_S_D   =   ((4 << 3) + 0),
4085c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_W_D   =   ((4 << 3) + 4),
4095c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_L_D   =   ((4 << 3) + 5),
4107516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  C_F_D     =   ((6 << 3) + 0),
4117516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  C_UN_D    =   ((6 << 3) + 1),
4127516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  C_EQ_D    =   ((6 << 3) + 2),
4137516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  C_UEQ_D   =   ((6 << 3) + 3),
4147516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  C_OLT_D   =   ((6 << 3) + 4),
4157516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  C_ULT_D   =   ((6 << 3) + 5),
4167516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  C_OLE_D   =   ((6 << 3) + 6),
4177516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  C_ULE_D   =   ((6 << 3) + 7),
4185c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // COP1 Encoding of Function Field When rs=W or L.
4195c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_S_W   =   ((4 << 3) + 0),
4205c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_D_W   =   ((4 << 3) + 1),
4215c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_S_L   =   ((4 << 3) + 0),
4225c838251403b0be9a882540f1922577abba4c872ager@chromium.org  CVT_D_L   =   ((4 << 3) + 1),
4235c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // COP1 Encoding of Function Field When rs=PS.
42459297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org  // COP1X Encoding of Function Field.
42559297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org  MADD_D    =   ((4 << 3) + 1),
4265c838251403b0be9a882540f1922577abba4c872ager@chromium.org
4275c838251403b0be9a882540f1922577abba4c872ager@chromium.org  NULLSF    =   0
4285c838251403b0be9a882540f1922577abba4c872ager@chromium.org};
4295c838251403b0be9a882540f1922577abba4c872ager@chromium.org
4305c838251403b0be9a882540f1922577abba4c872ager@chromium.org
4315c838251403b0be9a882540f1922577abba4c872ager@chromium.org// ----- Emulated conditions.
4325c838251403b0be9a882540f1922577abba4c872ager@chromium.org// On MIPS we use this enum to abstract from conditionnal branch instructions.
433750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org// The 'U' prefix is used to specify unsigned comparisons.
434750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org// Oppposite conditions must be paired as odd/even numbers
435750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org// because 'NegateCondition' function flips LSB to negate condition.
4365c838251403b0be9a882540f1922577abba4c872ager@chromium.orgenum Condition {
4375c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Any value < 0 is considered no_condition.
4387516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  kNoCondition  = -1,
4395c838251403b0be9a882540f1922577abba4c872ager@chromium.org
4405c838251403b0be9a882540f1922577abba4c872ager@chromium.org  overflow      =  0,
4415c838251403b0be9a882540f1922577abba4c872ager@chromium.org  no_overflow   =  1,
4425c838251403b0be9a882540f1922577abba4c872ager@chromium.org  Uless         =  2,
4435c838251403b0be9a882540f1922577abba4c872ager@chromium.org  Ugreater_equal=  3,
4445c838251403b0be9a882540f1922577abba4c872ager@chromium.org  equal         =  4,
4455c838251403b0be9a882540f1922577abba4c872ager@chromium.org  not_equal     =  5,
4465c838251403b0be9a882540f1922577abba4c872ager@chromium.org  Uless_equal   =  6,
4475c838251403b0be9a882540f1922577abba4c872ager@chromium.org  Ugreater      =  7,
4485c838251403b0be9a882540f1922577abba4c872ager@chromium.org  negative      =  8,
4495c838251403b0be9a882540f1922577abba4c872ager@chromium.org  positive      =  9,
4505c838251403b0be9a882540f1922577abba4c872ager@chromium.org  parity_even   = 10,
4515c838251403b0be9a882540f1922577abba4c872ager@chromium.org  parity_odd    = 11,
4525c838251403b0be9a882540f1922577abba4c872ager@chromium.org  less          = 12,
4535c838251403b0be9a882540f1922577abba4c872ager@chromium.org  greater_equal = 13,
4545c838251403b0be9a882540f1922577abba4c872ager@chromium.org  less_equal    = 14,
4555c838251403b0be9a882540f1922577abba4c872ager@chromium.org  greater       = 15,
456750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org  ueq           = 16,  // Unordered or Equal.
457750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org  nue           = 17,  // Not (Unordered or Equal).
4585c838251403b0be9a882540f1922577abba4c872ager@chromium.org
459750145ab1b720c97adf2b548cc8fbd28c8b8e06dulan@chromium.org  cc_always     = 18,
4605c838251403b0be9a882540f1922577abba4c872ager@chromium.org
46183a4728861129dc263ded92157f3e6389f851f19karlklose@chromium.org  // Aliases.
4625c838251403b0be9a882540f1922577abba4c872ager@chromium.org  carry         = Uless,
4635c838251403b0be9a882540f1922577abba4c872ager@chromium.org  not_carry     = Ugreater_equal,
4645c838251403b0be9a882540f1922577abba4c872ager@chromium.org  zero          = equal,
4655c838251403b0be9a882540f1922577abba4c872ager@chromium.org  eq            = equal,
4665c838251403b0be9a882540f1922577abba4c872ager@chromium.org  not_zero      = not_equal,
4675c838251403b0be9a882540f1922577abba4c872ager@chromium.org  ne            = not_equal,
4687516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  nz            = not_equal,
4695c838251403b0be9a882540f1922577abba4c872ager@chromium.org  sign          = negative,
4705c838251403b0be9a882540f1922577abba4c872ager@chromium.org  not_sign      = positive,
4717516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  mi            = negative,
4727516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  pl            = positive,
4737516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  hi            = Ugreater,
4747516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  ls            = Uless_equal,
4757516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  ge            = greater_equal,
4767516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  lt            = less,
4777516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  gt            = greater,
4787516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  le            = less_equal,
4797516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  hs            = Ugreater_equal,
4807516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  lo            = Uless,
4817516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  al            = cc_always,
4827516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
4837516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  cc_default    = kNoCondition
4845c838251403b0be9a882540f1922577abba4c872ager@chromium.org};
4855c838251403b0be9a882540f1922577abba4c872ager@chromium.org
4867516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
4877516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// Returns the equivalent of !cc.
4887516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// Negation of the default kNoCondition (-1) results in a non-default
4897516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// no_condition value (-2). As long as tests for no_condition check
4907516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// for condition < 0, this will work as expected.
4917516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orginline Condition NegateCondition(Condition cc) {
4927516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  ASSERT(cc != cc_always);
4937516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  return static_cast<Condition>(cc ^ 1);
4947516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org}
4957516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
4967516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
4977516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orginline Condition ReverseCondition(Condition cc) {
4987516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  switch (cc) {
4997516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    case Uless:
5007516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org      return Ugreater;
5017516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    case Ugreater:
5027516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org      return Uless;
5037516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    case Ugreater_equal:
5047516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org      return Uless_equal;
5057516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    case Uless_equal:
5067516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org      return Ugreater_equal;
5077516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    case less:
5087516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org      return greater;
5097516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    case greater:
5107516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org      return less;
5117516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    case greater_equal:
5127516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org      return less_equal;
5137516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    case less_equal:
5147516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org      return greater_equal;
5157516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    default:
5167516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org      return cc;
5177516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  };
5187516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org}
5197516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
5207516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
5215c838251403b0be9a882540f1922577abba4c872ager@chromium.org// ----- Coprocessor conditions.
5225c838251403b0be9a882540f1922577abba4c872ager@chromium.orgenum FPUCondition {
52334e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  kNoFPUCondition = -1,
52434e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org
52534e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  F     = 0,  // False.
52634e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  UN    = 1,  // Unordered.
52734e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  EQ    = 2,  // Equal.
52834e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  UEQ   = 3,  // Unordered or Equal.
52934e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  OLT   = 4,  // Ordered or Less Than.
53034e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  ULT   = 5,  // Unordered or Less Than.
53134e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  OLE   = 6,  // Ordered or Less Than or Equal.
53234e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  ULE   = 7   // Unordered or Less Than or Equal.
53334e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org};
53434e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org
53534e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org
53634e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org// FPU rounding modes.
53734e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.orgenum FPURoundingMode {
53834e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  RN = 0 << 0,  // Round to Nearest.
53934e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  RZ = 1 << 0,  // Round towards zero.
54034e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  RP = 2 << 0,  // Round towards Plus Infinity.
54134e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  RM = 3 << 0,  // Round towards Minus Infinity.
54234e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org
54334e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  // Aliases.
54434e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  kRoundToNearest = RN,
54534e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  kRoundToZero = RZ,
54634e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  kRoundToPlusInf = RP,
54734e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  kRoundToMinusInf = RM
54834e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org};
54934e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org
5501b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst uint32_t kFPURoundingModeMask = 3 << 0;
55134e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org
55234e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.orgenum CheckForInexactConversion {
55334e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  kCheckForInexactConversion,
55434e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org  kDontCheckForInexactConversion
5555c838251403b0be9a882540f1922577abba4c872ager@chromium.org};
5565c838251403b0be9a882540f1922577abba4c872ager@chromium.org
5575c838251403b0be9a882540f1922577abba4c872ager@chromium.org
5587516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// -----------------------------------------------------------------------------
5597516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// Hints.
5607516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
5617516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// Branch hints are not used on the MIPS.  They are defined so that they can
5627516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// appear in shared function signatures, but will be ignored in MIPS
5637516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// implementations.
5647516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgenum Hint {
5657516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  no_hint = 0
5667516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org};
5677516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
5687516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
5697516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orginline Hint NegateHint(Hint hint) {
5707516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  return no_hint;
5717516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org}
5727516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
5737516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
5747516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// -----------------------------------------------------------------------------
5757516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// Specific instructions, constants, and masks.
5767516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// These constants are declared in assembler-mips.cc, as they use named
5777516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// registers and other constants.
5787516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
5797516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// addiu(sp, sp, 4) aka Pop() operation or part of Pop(r)
5807516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// operations as post-increment of sp.
5817516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kPopInstruction;
5827516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// addiu(sp, sp, -4) part of Push(r) operation as pre-decrement of sp.
5837516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kPushInstruction;
5847516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// sw(r, MemOperand(sp, 0))
5857516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kPushRegPattern;
58683a4728861129dc263ded92157f3e6389f851f19karlklose@chromium.org// lw(r, MemOperand(sp, 0))
5877516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kPopRegPattern;
5887516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kLwRegFpOffsetPattern;
5897516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kSwRegFpOffsetPattern;
5907516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kLwRegFpNegOffsetPattern;
5917516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kSwRegFpNegOffsetPattern;
5927516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// A mask for the Rt register for push, pop, lw, sw instructions.
5937516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kRtMask;
5947516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kLwSwInstrTypeMask;
5957516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kLwSwInstrArgumentMask;
5967516f05132429850aa326421ed3e25f23b4c071blrn@chromium.orgextern const Instr kLwSwOffsetMask;
5977516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
5985c838251403b0be9a882540f1922577abba4c872ager@chromium.org// Break 0xfffff, reserved for redirected real time call.
5995c838251403b0be9a882540f1922577abba4c872ager@chromium.orgconst Instr rtCallRedirInstr = SPECIAL | BREAK | call_rt_redirected << 6;
6005c838251403b0be9a882540f1922577abba4c872ager@chromium.org// A nop instruction. (Encoding of sll 0 0 0).
6015c838251403b0be9a882540f1922577abba4c872ager@chromium.orgconst Instr nopInstr = 0;
6025c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6035c838251403b0be9a882540f1922577abba4c872ager@chromium.orgclass Instruction {
6045c838251403b0be9a882540f1922577abba4c872ager@chromium.org public:
6055c838251403b0be9a882540f1922577abba4c872ager@chromium.org  enum {
6067516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    kInstrSize = 4,
6077516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    kInstrSizeLog2 = 2,
6085c838251403b0be9a882540f1922577abba4c872ager@chromium.org    // On MIPS PC cannot actually be directly accessed. We behave as if PC was
6097516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    // always the value of the current instruction being executed.
6105c838251403b0be9a882540f1922577abba4c872ager@chromium.org    kPCReadOffset = 0
6115c838251403b0be9a882540f1922577abba4c872ager@chromium.org  };
6125c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6135c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Get the raw instruction bits.
6145c838251403b0be9a882540f1922577abba4c872ager@chromium.org  inline Instr InstructionBits() const {
6155c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return *reinterpret_cast<const Instr*>(this);
6165c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6175c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6185c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Set the raw instruction bits to value.
6195c838251403b0be9a882540f1922577abba4c872ager@chromium.org  inline void SetInstructionBits(Instr value) {
6205c838251403b0be9a882540f1922577abba4c872ager@chromium.org    *reinterpret_cast<Instr*>(this) = value;
6215c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6225c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6235c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Read one particular bit out of the instruction bits.
6245c838251403b0be9a882540f1922577abba4c872ager@chromium.org  inline int Bit(int nr) const {
6255c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return (InstructionBits() >> nr) & 1;
6265c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6275c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6285c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Read a bit field out of the instruction bits.
6295c838251403b0be9a882540f1922577abba4c872ager@chromium.org  inline int Bits(int hi, int lo) const {
6305c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return (InstructionBits() >> lo) & ((2 << (hi - lo)) - 1);
6315c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6325c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6335c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Instruction type.
6345c838251403b0be9a882540f1922577abba4c872ager@chromium.org  enum Type {
6355c838251403b0be9a882540f1922577abba4c872ager@chromium.org    kRegisterType,
6365c838251403b0be9a882540f1922577abba4c872ager@chromium.org    kImmediateType,
6375c838251403b0be9a882540f1922577abba4c872ager@chromium.org    kJumpType,
6385c838251403b0be9a882540f1922577abba4c872ager@chromium.org    kUnsupported = -1
6395c838251403b0be9a882540f1922577abba4c872ager@chromium.org  };
6405c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6415c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Get the encoding type of the instruction.
6425c838251403b0be9a882540f1922577abba4c872ager@chromium.org  Type InstructionType() const;
6435c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6445c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6455c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Accessors for the different named fields used in the MIPS encoding.
6467516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline Opcode OpcodeValue() const {
6475c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return static_cast<Opcode>(
6485c838251403b0be9a882540f1922577abba4c872ager@chromium.org        Bits(kOpcodeShift + kOpcodeBits - 1, kOpcodeShift));
6495c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6505c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6517516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int RsValue() const {
6525c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kRegisterType ||
6535c838251403b0be9a882540f1922577abba4c872ager@chromium.org           InstructionType() == kImmediateType);
6545c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return Bits(kRsShift + kRsBits - 1, kRsShift);
6555c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6565c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6577516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int RtValue() const {
6585c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kRegisterType ||
6595c838251403b0be9a882540f1922577abba4c872ager@chromium.org           InstructionType() == kImmediateType);
6605c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return Bits(kRtShift + kRtBits - 1, kRtShift);
6615c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6625c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6637516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int RdValue() const {
6645c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kRegisterType);
6655c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return Bits(kRdShift + kRdBits - 1, kRdShift);
6665c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6675c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6687516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int SaValue() const {
6695c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kRegisterType);
6705c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return Bits(kSaShift + kSaBits - 1, kSaShift);
6715c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6725c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6737516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int FunctionValue() const {
6745c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kRegisterType ||
6755c838251403b0be9a882540f1922577abba4c872ager@chromium.org           InstructionType() == kImmediateType);
6765c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return Bits(kFunctionShift + kFunctionBits - 1, kFunctionShift);
6775c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6785c838251403b0be9a882540f1922577abba4c872ager@chromium.org
6797516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int FdValue() const {
6807516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    return Bits(kFdShift + kFdBits - 1, kFdShift);
6817516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  }
6827516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
6837516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int FsValue() const {
6847516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    return Bits(kFsShift + kFsBits - 1, kFsShift);
6857516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  }
6867516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
6877516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int FtValue() const {
6887516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    return Bits(kFtShift + kFtBits - 1, kFtShift);
6895c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
6905c838251403b0be9a882540f1922577abba4c872ager@chromium.org
69159297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org  inline int FrValue() const {
69259297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org    return Bits(kFrShift + kFrBits -1, kFrShift);
69359297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org  }
69459297c735ad2a41156ae9c723a39ff259ad061e0jkummerow@chromium.org
6957516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  // Float Compare condition code instruction bits.
6967516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int FCccValue() const {
6977516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    return Bits(kFCccShift + kFCccBits - 1, kFCccShift);
6987516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  }
6997516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
7007516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  // Float Branch condition code instruction bits.
7017516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int FBccValue() const {
7027516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    return Bits(kFBccShift + kFBccBits - 1, kFBccShift);
7037516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  }
7047516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
7057516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  // Float Branch true/false instruction bit.
7067516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int FBtrueValue() const {
7077516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    return Bits(kFBtrueShift + kFBtrueBits - 1, kFBtrueShift);
7085c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7095c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7105c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Return the fields at their original place in the instruction encoding.
7115c838251403b0be9a882540f1922577abba4c872ager@chromium.org  inline Opcode OpcodeFieldRaw() const {
7125c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return static_cast<Opcode>(InstructionBits() & kOpcodeMask);
7135c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7145c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7155c838251403b0be9a882540f1922577abba4c872ager@chromium.org  inline int RsFieldRaw() const {
7165c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kRegisterType ||
7175c838251403b0be9a882540f1922577abba4c872ager@chromium.org           InstructionType() == kImmediateType);
7185c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return InstructionBits() & kRsFieldMask;
7195c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7205c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7217516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  // Same as above function, but safe to call within InstructionType().
7227516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int RsFieldRawNoAssert() const {
7237516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org    return InstructionBits() & kRsFieldMask;
7247516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  }
7257516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org
7265c838251403b0be9a882540f1922577abba4c872ager@chromium.org  inline int RtFieldRaw() const {
7275c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kRegisterType ||
7285c838251403b0be9a882540f1922577abba4c872ager@chromium.org           InstructionType() == kImmediateType);
7295c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return InstructionBits() & kRtFieldMask;
7305c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7315c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7325c838251403b0be9a882540f1922577abba4c872ager@chromium.org  inline int RdFieldRaw() const {
7335c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kRegisterType);
7345c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return InstructionBits() & kRdFieldMask;
7355c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7365c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7375c838251403b0be9a882540f1922577abba4c872ager@chromium.org  inline int SaFieldRaw() const {
7385c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kRegisterType);
7395c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return InstructionBits() & kSaFieldMask;
7405c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7415c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7425c838251403b0be9a882540f1922577abba4c872ager@chromium.org  inline int FunctionFieldRaw() const {
7435c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return InstructionBits() & kFunctionFieldMask;
7445c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7455c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7465c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Get the secondary field according to the opcode.
7477516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int SecondaryValue() const {
7485c838251403b0be9a882540f1922577abba4c872ager@chromium.org    Opcode op = OpcodeFieldRaw();
7495c838251403b0be9a882540f1922577abba4c872ager@chromium.org    switch (op) {
7505c838251403b0be9a882540f1922577abba4c872ager@chromium.org      case SPECIAL:
7515c838251403b0be9a882540f1922577abba4c872ager@chromium.org      case SPECIAL2:
7527516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org        return FunctionValue();
7535c838251403b0be9a882540f1922577abba4c872ager@chromium.org      case COP1:
7547516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org        return RsValue();
7555c838251403b0be9a882540f1922577abba4c872ager@chromium.org      case REGIMM:
7567516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org        return RtValue();
7575c838251403b0be9a882540f1922577abba4c872ager@chromium.org      default:
7585c838251403b0be9a882540f1922577abba4c872ager@chromium.org        return NULLSF;
7595c838251403b0be9a882540f1922577abba4c872ager@chromium.org    }
7605c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7615c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7627516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int32_t Imm16Value() const {
7635c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kImmediateType);
7645c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return Bits(kImm16Shift + kImm16Bits - 1, kImm16Shift);
7655c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7665c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7677516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  inline int32_t Imm26Value() const {
7685c838251403b0be9a882540f1922577abba4c872ager@chromium.org    ASSERT(InstructionType() == kJumpType);
76934e60787ea1e76f3ee49e859f71f036170c21f0elrn@chromium.org    return Bits(kImm26Shift + kImm26Bits - 1, kImm26Shift);
7705c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7715c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7725c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Say if the instruction should not be used in a branch delay slot.
7737516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  bool IsForbiddenInBranchDelay() const;
7742efb900e7350b14be905abdeab077f3a64c583cfulan@chromium.org  // Say if the instruction 'links'. e.g. jal, bal.
7757516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  bool IsLinkingInstruction() const;
7765c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Say if the instruction is a break or a trap.
7777516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org  bool IsTrap() const;
7785c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7795c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Instructions are read of out a code stream. The only way to get a
7805c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // reference to an instruction is to convert a pointer. There is no way
7815c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // to allocate or create instances of class Instruction.
7825c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // Use the At(pc) function to create references to Instruction.
78383a4728861129dc263ded92157f3e6389f851f19karlklose@chromium.org  static Instruction* At(byte* pc) {
7845c838251403b0be9a882540f1922577abba4c872ager@chromium.org    return reinterpret_cast<Instruction*>(pc);
7855c838251403b0be9a882540f1922577abba4c872ager@chromium.org  }
7865c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7875c838251403b0be9a882540f1922577abba4c872ager@chromium.org private:
7885c838251403b0be9a882540f1922577abba4c872ager@chromium.org  // We need to prevent the creation of instances of class Instruction.
7895c838251403b0be9a882540f1922577abba4c872ager@chromium.org  DISALLOW_IMPLICIT_CONSTRUCTORS(Instruction);
7905c838251403b0be9a882540f1922577abba4c872ager@chromium.org};
7915c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7925c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7935c838251403b0be9a882540f1922577abba4c872ager@chromium.org// -----------------------------------------------------------------------------
7945c838251403b0be9a882540f1922577abba4c872ager@chromium.org// MIPS assembly various constants.
7955c838251403b0be9a882540f1922577abba4c872ager@chromium.org
7967516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// C/C++ argument slots size.
7971b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kCArgSlotCount = 4;
7981b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kCArgsSlotsSize = kCArgSlotCount * Instruction::kInstrSize;
7997516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// JS argument slots size.
8001b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kJSArgsSlotsSize = 0 * Instruction::kInstrSize;
8017516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org// Assembly builtins argument slots size.
8021b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kBArgsSlotsSize = 0 * Instruction::kInstrSize;
8035c838251403b0be9a882540f1922577abba4c872ager@chromium.org
8041b3afd1cab9087ca3c4e585d3da77d374d65c082mstarzinger@chromium.orgconst int kBranchReturnOffset = 2 * Instruction::kInstrSize;
8055c838251403b0be9a882540f1922577abba4c872ager@chromium.org
8067516f05132429850aa326421ed3e25f23b4c071blrn@chromium.org} }   // namespace v8::internal
8075c838251403b0be9a882540f1922577abba4c872ager@chromium.org
8085c838251403b0be9a882540f1922577abba4c872ager@chromium.org#endif    // #ifndef V8_MIPS_CONSTANTS_H_
809