Home | History | Annotate | Download | only in arm64
      1 // Copyright 2013 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_ARM64_ASSEMBLER_ARM64_H_
      6 #define V8_ARM64_ASSEMBLER_ARM64_H_
      7 
      8 #include <deque>
      9 #include <list>
     10 #include <map>
     11 #include <vector>
     12 
     13 #include "src/arm64/instructions-arm64.h"
     14 #include "src/assembler.h"
     15 #include "src/globals.h"
     16 #include "src/utils.h"
     17 
     18 
     19 namespace v8 {
     20 namespace internal {
     21 
     22 
     23 // -----------------------------------------------------------------------------
     24 // Registers.
     25 // clang-format off
     26 #define GENERAL_REGISTER_CODE_LIST(R)                     \
     27   R(0)  R(1)  R(2)  R(3)  R(4)  R(5)  R(6)  R(7)          \
     28   R(8)  R(9)  R(10) R(11) R(12) R(13) R(14) R(15)         \
     29   R(16) R(17) R(18) R(19) R(20) R(21) R(22) R(23)         \
     30   R(24) R(25) R(26) R(27) R(28) R(29) R(30) R(31)
     31 
     32 #define GENERAL_REGISTERS(R)                              \
     33   R(x0)  R(x1)  R(x2)  R(x3)  R(x4)  R(x5)  R(x6)  R(x7)  \
     34   R(x8)  R(x9)  R(x10) R(x11) R(x12) R(x13) R(x14) R(x15) \
     35   R(x16) R(x17) R(x18) R(x19) R(x20) R(x21) R(x22) R(x23) \
     36   R(x24) R(x25) R(x26) R(x27) R(x28) R(x29) R(x30) R(x31)
     37 
     38 #define ALLOCATABLE_GENERAL_REGISTERS(R)                  \
     39   R(x0)  R(x1)  R(x2)  R(x3)  R(x4)  R(x5)  R(x6)  R(x7)  \
     40   R(x8)  R(x9)  R(x10) R(x11) R(x12) R(x13) R(x14) R(x15) \
     41   R(x18) R(x19) R(x20) R(x21) R(x22) R(x23) R(x24) R(x27)
     42 
     43 #define DOUBLE_REGISTERS(R)                               \
     44   R(d0)  R(d1)  R(d2)  R(d3)  R(d4)  R(d5)  R(d6)  R(d7)  \
     45   R(d8)  R(d9)  R(d10) R(d11) R(d12) R(d13) R(d14) R(d15) \
     46   R(d16) R(d17) R(d18) R(d19) R(d20) R(d21) R(d22) R(d23) \
     47   R(d24) R(d25) R(d26) R(d27) R(d28) R(d29) R(d30) R(d31)
     48 
     49 #define ALLOCATABLE_DOUBLE_REGISTERS(R)                   \
     50   R(d0)  R(d1)  R(d2)  R(d3)  R(d4)  R(d5)  R(d6)  R(d7)  \
     51   R(d8)  R(d9)  R(d10) R(d11) R(d12) R(d13) R(d14) R(d16) \
     52   R(d17) R(d18) R(d19) R(d20) R(d21) R(d22) R(d23) R(d24) \
     53   R(d25) R(d26) R(d27) R(d28)
     54 // clang-format on
     55 
     56 static const int kRegListSizeInBits = sizeof(RegList) * kBitsPerByte;
     57 
     58 
     59 // Some CPURegister methods can return Register and FPRegister types, so we
     60 // need to declare them in advance.
     61 struct Register;
     62 struct FPRegister;
     63 
     64 
     65 struct CPURegister {
     66   enum Code {
     67 #define REGISTER_CODE(R) kCode_##R,
     68     GENERAL_REGISTERS(REGISTER_CODE)
     69 #undef REGISTER_CODE
     70         kAfterLast,
     71     kCode_no_reg = -1
     72   };
     73 
     74   enum RegisterType {
     75     // The kInvalid value is used to detect uninitialized static instances,
     76     // which are always zero-initialized before any constructors are called.
     77     kInvalid = 0,
     78     kRegister,
     79     kFPRegister,
     80     kNoRegister
     81   };
     82 
     83   static CPURegister Create(int code, int size, RegisterType type) {
     84     CPURegister r = {code, size, type};
     85     return r;
     86   }
     87 
     88   int code() const;
     89   RegisterType type() const;
     90   RegList Bit() const;
     91   int SizeInBits() const;
     92   int SizeInBytes() const;
     93   bool Is32Bits() const;
     94   bool Is64Bits() const;
     95   bool IsValid() const;
     96   bool IsValidOrNone() const;
     97   bool IsValidRegister() const;
     98   bool IsValidFPRegister() const;
     99   bool IsNone() const;
    100   bool Is(const CPURegister& other) const;
    101   bool Aliases(const CPURegister& other) const;
    102 
    103   bool IsZero() const;
    104   bool IsSP() const;
    105 
    106   bool IsRegister() const;
    107   bool IsFPRegister() const;
    108 
    109   Register X() const;
    110   Register W() const;
    111   FPRegister D() const;
    112   FPRegister S() const;
    113 
    114   bool IsSameSizeAndType(const CPURegister& other) const;
    115 
    116   // V8 compatibility.
    117   bool is(const CPURegister& other) const { return Is(other); }
    118   bool is_valid() const { return IsValid(); }
    119 
    120   int reg_code;
    121   int reg_size;
    122   RegisterType reg_type;
    123 };
    124 
    125 
    126 struct Register : public CPURegister {
    127   static Register Create(int code, int size) {
    128     return Register(CPURegister::Create(code, size, CPURegister::kRegister));
    129   }
    130 
    131   Register() {
    132     reg_code = 0;
    133     reg_size = 0;
    134     reg_type = CPURegister::kNoRegister;
    135   }
    136 
    137   explicit Register(const CPURegister& r) {
    138     reg_code = r.reg_code;
    139     reg_size = r.reg_size;
    140     reg_type = r.reg_type;
    141     DCHECK(IsValidOrNone());
    142   }
    143 
    144   Register(const Register& r) {  // NOLINT(runtime/explicit)
    145     reg_code = r.reg_code;
    146     reg_size = r.reg_size;
    147     reg_type = r.reg_type;
    148     DCHECK(IsValidOrNone());
    149   }
    150 
    151   const char* ToString();
    152   bool IsAllocatable() const;
    153   bool IsValid() const {
    154     DCHECK(IsRegister() || IsNone());
    155     return IsValidRegister();
    156   }
    157 
    158   static Register XRegFromCode(unsigned code);
    159   static Register WRegFromCode(unsigned code);
    160 
    161   // Start of V8 compatibility section ---------------------
    162   // These memebers are necessary for compilation.
    163   // A few of them may be unused for now.
    164 
    165   static const int kNumRegisters = kNumberOfRegisters;
    166   STATIC_ASSERT(kNumRegisters == Code::kAfterLast);
    167   static int NumRegisters() { return kNumRegisters; }
    168 
    169   // We allow crankshaft to use the following registers:
    170   //   - x0 to x15
    171   //   - x18 to x24
    172   //   - x27 (also context)
    173   //
    174   // TODO(all): Register x25 is currently free and could be available for
    175   // crankshaft, but we don't use it as we might use it as a per function
    176   // literal pool pointer in the future.
    177   //
    178   // TODO(all): Consider storing cp in x25 to have only two ranges.
    179   // We split allocatable registers in three ranges called
    180   //   - "low range"
    181   //   - "high range"
    182   //   - "context"
    183 
    184   static Register from_code(int code) {
    185     // Always return an X register.
    186     return Register::Create(code, kXRegSizeInBits);
    187   }
    188 
    189   // End of V8 compatibility section -----------------------
    190 };
    191 
    192 
    193 struct FPRegister : public CPURegister {
    194   enum Code {
    195 #define REGISTER_CODE(R) kCode_##R,
    196     DOUBLE_REGISTERS(REGISTER_CODE)
    197 #undef REGISTER_CODE
    198         kAfterLast,
    199     kCode_no_reg = -1
    200   };
    201 
    202   static FPRegister Create(int code, int size) {
    203     return FPRegister(
    204         CPURegister::Create(code, size, CPURegister::kFPRegister));
    205   }
    206 
    207   FPRegister() {
    208     reg_code = 0;
    209     reg_size = 0;
    210     reg_type = CPURegister::kNoRegister;
    211   }
    212 
    213   explicit FPRegister(const CPURegister& r) {
    214     reg_code = r.reg_code;
    215     reg_size = r.reg_size;
    216     reg_type = r.reg_type;
    217     DCHECK(IsValidOrNone());
    218   }
    219 
    220   FPRegister(const FPRegister& r) {  // NOLINT(runtime/explicit)
    221     reg_code = r.reg_code;
    222     reg_size = r.reg_size;
    223     reg_type = r.reg_type;
    224     DCHECK(IsValidOrNone());
    225   }
    226 
    227   const char* ToString();
    228   bool IsAllocatable() const;
    229   bool IsValid() const {
    230     DCHECK(IsFPRegister() || IsNone());
    231     return IsValidFPRegister();
    232   }
    233 
    234   static FPRegister SRegFromCode(unsigned code);
    235   static FPRegister DRegFromCode(unsigned code);
    236 
    237   // Start of V8 compatibility section ---------------------
    238   static const int kMaxNumRegisters = kNumberOfFPRegisters;
    239   STATIC_ASSERT(kMaxNumRegisters == Code::kAfterLast);
    240 
    241   // Crankshaft can use all the FP registers except:
    242   //   - d15 which is used to keep the 0 double value
    243   //   - d30 which is used in crankshaft as a double scratch register
    244   //   - d31 which is used in the MacroAssembler as a double scratch register
    245   static FPRegister from_code(int code) {
    246     // Always return a D register.
    247     return FPRegister::Create(code, kDRegSizeInBits);
    248   }
    249   // End of V8 compatibility section -----------------------
    250 };
    251 
    252 
    253 STATIC_ASSERT(sizeof(CPURegister) == sizeof(Register));
    254 STATIC_ASSERT(sizeof(CPURegister) == sizeof(FPRegister));
    255 
    256 
    257 #if defined(ARM64_DEFINE_REG_STATICS)
    258 #define INITIALIZE_REGISTER(register_class, name, code, size, type)      \
    259   const CPURegister init_##register_class##_##name = {code, size, type}; \
    260   const register_class& name = *reinterpret_cast<const register_class*>( \
    261                                     &init_##register_class##_##name)
    262 #define ALIAS_REGISTER(register_class, alias, name)                       \
    263   const register_class& alias = *reinterpret_cast<const register_class*>( \
    264                                      &init_##register_class##_##name)
    265 #else
    266 #define INITIALIZE_REGISTER(register_class, name, code, size, type) \
    267   extern const register_class& name
    268 #define ALIAS_REGISTER(register_class, alias, name) \
    269   extern const register_class& alias
    270 #endif  // defined(ARM64_DEFINE_REG_STATICS)
    271 
    272 // No*Reg is used to indicate an unused argument, or an error case. Note that
    273 // these all compare equal (using the Is() method). The Register and FPRegister
    274 // variants are provided for convenience.
    275 INITIALIZE_REGISTER(Register, NoReg, 0, 0, CPURegister::kNoRegister);
    276 INITIALIZE_REGISTER(FPRegister, NoFPReg, 0, 0, CPURegister::kNoRegister);
    277 INITIALIZE_REGISTER(CPURegister, NoCPUReg, 0, 0, CPURegister::kNoRegister);
    278 
    279 // v8 compatibility.
    280 INITIALIZE_REGISTER(Register, no_reg, 0, 0, CPURegister::kNoRegister);
    281 
    282 #define DEFINE_REGISTERS(N)                                                  \
    283   INITIALIZE_REGISTER(Register, w##N, N,                                     \
    284                       kWRegSizeInBits, CPURegister::kRegister);              \
    285   INITIALIZE_REGISTER(Register, x##N, N,                                     \
    286                       kXRegSizeInBits, CPURegister::kRegister);
    287 GENERAL_REGISTER_CODE_LIST(DEFINE_REGISTERS)
    288 #undef DEFINE_REGISTERS
    289 
    290 INITIALIZE_REGISTER(Register, wcsp, kSPRegInternalCode, kWRegSizeInBits,
    291                     CPURegister::kRegister);
    292 INITIALIZE_REGISTER(Register, csp, kSPRegInternalCode, kXRegSizeInBits,
    293                     CPURegister::kRegister);
    294 
    295 #define DEFINE_FPREGISTERS(N)                                                  \
    296   INITIALIZE_REGISTER(FPRegister, s##N, N,                                     \
    297                       kSRegSizeInBits, CPURegister::kFPRegister);              \
    298   INITIALIZE_REGISTER(FPRegister, d##N, N,                                     \
    299                       kDRegSizeInBits, CPURegister::kFPRegister);
    300 GENERAL_REGISTER_CODE_LIST(DEFINE_FPREGISTERS)
    301 #undef DEFINE_FPREGISTERS
    302 
    303 #undef INITIALIZE_REGISTER
    304 
    305 // Registers aliases.
    306 ALIAS_REGISTER(Register, ip0, x16);
    307 ALIAS_REGISTER(Register, ip1, x17);
    308 ALIAS_REGISTER(Register, wip0, w16);
    309 ALIAS_REGISTER(Register, wip1, w17);
    310 // Root register.
    311 ALIAS_REGISTER(Register, root, x26);
    312 ALIAS_REGISTER(Register, rr, x26);
    313 // Context pointer register.
    314 ALIAS_REGISTER(Register, cp, x27);
    315 // We use a register as a JS stack pointer to overcome the restriction on the
    316 // architectural SP alignment.
    317 // We chose x28 because it is contiguous with the other specific purpose
    318 // registers.
    319 STATIC_ASSERT(kJSSPCode == 28);
    320 ALIAS_REGISTER(Register, jssp, x28);
    321 ALIAS_REGISTER(Register, wjssp, w28);
    322 ALIAS_REGISTER(Register, fp, x29);
    323 ALIAS_REGISTER(Register, lr, x30);
    324 ALIAS_REGISTER(Register, xzr, x31);
    325 ALIAS_REGISTER(Register, wzr, w31);
    326 
    327 // Keeps the 0 double value.
    328 ALIAS_REGISTER(FPRegister, fp_zero, d15);
    329 // Crankshaft double scratch register.
    330 ALIAS_REGISTER(FPRegister, crankshaft_fp_scratch, d29);
    331 // MacroAssembler double scratch registers.
    332 ALIAS_REGISTER(FPRegister, fp_scratch, d30);
    333 ALIAS_REGISTER(FPRegister, fp_scratch1, d30);
    334 ALIAS_REGISTER(FPRegister, fp_scratch2, d31);
    335 
    336 #undef ALIAS_REGISTER
    337 
    338 
    339 Register GetAllocatableRegisterThatIsNotOneOf(Register reg1,
    340                                               Register reg2 = NoReg,
    341                                               Register reg3 = NoReg,
    342                                               Register reg4 = NoReg);
    343 
    344 
    345 // AreAliased returns true if any of the named registers overlap. Arguments set
    346 // to NoReg are ignored. The system stack pointer may be specified.
    347 bool AreAliased(const CPURegister& reg1,
    348                 const CPURegister& reg2,
    349                 const CPURegister& reg3 = NoReg,
    350                 const CPURegister& reg4 = NoReg,
    351                 const CPURegister& reg5 = NoReg,
    352                 const CPURegister& reg6 = NoReg,
    353                 const CPURegister& reg7 = NoReg,
    354                 const CPURegister& reg8 = NoReg);
    355 
    356 // AreSameSizeAndType returns true if all of the specified registers have the
    357 // same size, and are of the same type. The system stack pointer may be
    358 // specified. Arguments set to NoReg are ignored, as are any subsequent
    359 // arguments. At least one argument (reg1) must be valid (not NoCPUReg).
    360 bool AreSameSizeAndType(const CPURegister& reg1,
    361                         const CPURegister& reg2,
    362                         const CPURegister& reg3 = NoCPUReg,
    363                         const CPURegister& reg4 = NoCPUReg,
    364                         const CPURegister& reg5 = NoCPUReg,
    365                         const CPURegister& reg6 = NoCPUReg,
    366                         const CPURegister& reg7 = NoCPUReg,
    367                         const CPURegister& reg8 = NoCPUReg);
    368 
    369 
    370 typedef FPRegister DoubleRegister;
    371 
    372 
    373 // -----------------------------------------------------------------------------
    374 // Lists of registers.
    375 class CPURegList {
    376  public:
    377   explicit CPURegList(CPURegister reg1,
    378                       CPURegister reg2 = NoCPUReg,
    379                       CPURegister reg3 = NoCPUReg,
    380                       CPURegister reg4 = NoCPUReg)
    381       : list_(reg1.Bit() | reg2.Bit() | reg3.Bit() | reg4.Bit()),
    382         size_(reg1.SizeInBits()), type_(reg1.type()) {
    383     DCHECK(AreSameSizeAndType(reg1, reg2, reg3, reg4));
    384     DCHECK(IsValid());
    385   }
    386 
    387   CPURegList(CPURegister::RegisterType type, int size, RegList list)
    388       : list_(list), size_(size), type_(type) {
    389     DCHECK(IsValid());
    390   }
    391 
    392   CPURegList(CPURegister::RegisterType type, int size, int first_reg,
    393              int last_reg)
    394       : size_(size), type_(type) {
    395     DCHECK(((type == CPURegister::kRegister) &&
    396             (last_reg < kNumberOfRegisters)) ||
    397            ((type == CPURegister::kFPRegister) &&
    398             (last_reg < kNumberOfFPRegisters)));
    399     DCHECK(last_reg >= first_reg);
    400     list_ = (1UL << (last_reg + 1)) - 1;
    401     list_ &= ~((1UL << first_reg) - 1);
    402     DCHECK(IsValid());
    403   }
    404 
    405   CPURegister::RegisterType type() const {
    406     DCHECK(IsValid());
    407     return type_;
    408   }
    409 
    410   RegList list() const {
    411     DCHECK(IsValid());
    412     return list_;
    413   }
    414 
    415   inline void set_list(RegList new_list) {
    416     DCHECK(IsValid());
    417     list_ = new_list;
    418   }
    419 
    420   // Combine another CPURegList into this one. Registers that already exist in
    421   // this list are left unchanged. The type and size of the registers in the
    422   // 'other' list must match those in this list.
    423   void Combine(const CPURegList& other);
    424 
    425   // Remove every register in the other CPURegList from this one. Registers that
    426   // do not exist in this list are ignored. The type of the registers in the
    427   // 'other' list must match those in this list.
    428   void Remove(const CPURegList& other);
    429 
    430   // Variants of Combine and Remove which take CPURegisters.
    431   void Combine(const CPURegister& other);
    432   void Remove(const CPURegister& other1,
    433               const CPURegister& other2 = NoCPUReg,
    434               const CPURegister& other3 = NoCPUReg,
    435               const CPURegister& other4 = NoCPUReg);
    436 
    437   // Variants of Combine and Remove which take a single register by its code;
    438   // the type and size of the register is inferred from this list.
    439   void Combine(int code);
    440   void Remove(int code);
    441 
    442   // Remove all callee-saved registers from the list. This can be useful when
    443   // preparing registers for an AAPCS64 function call, for example.
    444   void RemoveCalleeSaved();
    445 
    446   CPURegister PopLowestIndex();
    447   CPURegister PopHighestIndex();
    448 
    449   // AAPCS64 callee-saved registers.
    450   static CPURegList GetCalleeSaved(int size = kXRegSizeInBits);
    451   static CPURegList GetCalleeSavedFP(int size = kDRegSizeInBits);
    452 
    453   // AAPCS64 caller-saved registers. Note that this includes lr.
    454   static CPURegList GetCallerSaved(int size = kXRegSizeInBits);
    455   static CPURegList GetCallerSavedFP(int size = kDRegSizeInBits);
    456 
    457   // Registers saved as safepoints.
    458   static CPURegList GetSafepointSavedRegisters();
    459 
    460   bool IsEmpty() const {
    461     DCHECK(IsValid());
    462     return list_ == 0;
    463   }
    464 
    465   bool IncludesAliasOf(const CPURegister& other1,
    466                        const CPURegister& other2 = NoCPUReg,
    467                        const CPURegister& other3 = NoCPUReg,
    468                        const CPURegister& other4 = NoCPUReg) const {
    469     DCHECK(IsValid());
    470     RegList list = 0;
    471     if (!other1.IsNone() && (other1.type() == type_)) list |= other1.Bit();
    472     if (!other2.IsNone() && (other2.type() == type_)) list |= other2.Bit();
    473     if (!other3.IsNone() && (other3.type() == type_)) list |= other3.Bit();
    474     if (!other4.IsNone() && (other4.type() == type_)) list |= other4.Bit();
    475     return (list_ & list) != 0;
    476   }
    477 
    478   int Count() const {
    479     DCHECK(IsValid());
    480     return CountSetBits(list_, kRegListSizeInBits);
    481   }
    482 
    483   int RegisterSizeInBits() const {
    484     DCHECK(IsValid());
    485     return size_;
    486   }
    487 
    488   int RegisterSizeInBytes() const {
    489     int size_in_bits = RegisterSizeInBits();
    490     DCHECK((size_in_bits % kBitsPerByte) == 0);
    491     return size_in_bits / kBitsPerByte;
    492   }
    493 
    494   int TotalSizeInBytes() const {
    495     DCHECK(IsValid());
    496     return RegisterSizeInBytes() * Count();
    497   }
    498 
    499  private:
    500   RegList list_;
    501   int size_;
    502   CPURegister::RegisterType type_;
    503 
    504   bool IsValid() const {
    505     const RegList kValidRegisters = 0x8000000ffffffff;
    506     const RegList kValidFPRegisters = 0x0000000ffffffff;
    507     switch (type_) {
    508       case CPURegister::kRegister:
    509         return (list_ & kValidRegisters) == list_;
    510       case CPURegister::kFPRegister:
    511         return (list_ & kValidFPRegisters) == list_;
    512       case CPURegister::kNoRegister:
    513         return list_ == 0;
    514       default:
    515         UNREACHABLE();
    516         return false;
    517     }
    518   }
    519 };
    520 
    521 
    522 // AAPCS64 callee-saved registers.
    523 #define kCalleeSaved CPURegList::GetCalleeSaved()
    524 #define kCalleeSavedFP CPURegList::GetCalleeSavedFP()
    525 
    526 
    527 // AAPCS64 caller-saved registers. Note that this includes lr.
    528 #define kCallerSaved CPURegList::GetCallerSaved()
    529 #define kCallerSavedFP CPURegList::GetCallerSavedFP()
    530 
    531 // -----------------------------------------------------------------------------
    532 // Immediates.
    533 class Immediate {
    534  public:
    535   template<typename T>
    536   inline explicit Immediate(Handle<T> handle);
    537 
    538   // This is allowed to be an implicit constructor because Immediate is
    539   // a wrapper class that doesn't normally perform any type conversion.
    540   template<typename T>
    541   inline Immediate(T value);  // NOLINT(runtime/explicit)
    542 
    543   template<typename T>
    544   inline Immediate(T value, RelocInfo::Mode rmode);
    545 
    546   int64_t value() const { return value_; }
    547   RelocInfo::Mode rmode() const { return rmode_; }
    548 
    549  private:
    550   void InitializeHandle(Handle<Object> value);
    551 
    552   int64_t value_;
    553   RelocInfo::Mode rmode_;
    554 };
    555 
    556 
    557 // -----------------------------------------------------------------------------
    558 // Operands.
    559 const int kSmiShift = kSmiTagSize + kSmiShiftSize;
    560 const uint64_t kSmiShiftMask = (1UL << kSmiShift) - 1;
    561 
    562 // Represents an operand in a machine instruction.
    563 class Operand {
    564   // TODO(all): If necessary, study more in details which methods
    565   // TODO(all): should be inlined or not.
    566  public:
    567   // rm, {<shift> {#<shift_amount>}}
    568   // where <shift> is one of {LSL, LSR, ASR, ROR}.
    569   //       <shift_amount> is uint6_t.
    570   // This is allowed to be an implicit constructor because Operand is
    571   // a wrapper class that doesn't normally perform any type conversion.
    572   inline Operand(Register reg,
    573                  Shift shift = LSL,
    574                  unsigned shift_amount = 0);  // NOLINT(runtime/explicit)
    575 
    576   // rm, <extend> {#<shift_amount>}
    577   // where <extend> is one of {UXTB, UXTH, UXTW, UXTX, SXTB, SXTH, SXTW, SXTX}.
    578   //       <shift_amount> is uint2_t.
    579   inline Operand(Register reg,
    580                  Extend extend,
    581                  unsigned shift_amount = 0);
    582 
    583   template<typename T>
    584   inline explicit Operand(Handle<T> handle);
    585 
    586   // Implicit constructor for all int types, ExternalReference, and Smi.
    587   template<typename T>
    588   inline Operand(T t);  // NOLINT(runtime/explicit)
    589 
    590   // Implicit constructor for int types.
    591   template<typename T>
    592   inline Operand(T t, RelocInfo::Mode rmode);
    593 
    594   inline bool IsImmediate() const;
    595   inline bool IsShiftedRegister() const;
    596   inline bool IsExtendedRegister() const;
    597   inline bool IsZero() const;
    598 
    599   // This returns an LSL shift (<= 4) operand as an equivalent extend operand,
    600   // which helps in the encoding of instructions that use the stack pointer.
    601   inline Operand ToExtendedRegister() const;
    602 
    603   inline Immediate immediate() const;
    604   inline int64_t ImmediateValue() const;
    605   inline Register reg() const;
    606   inline Shift shift() const;
    607   inline Extend extend() const;
    608   inline unsigned shift_amount() const;
    609 
    610   // Relocation information.
    611   bool NeedsRelocation(const Assembler* assembler) const;
    612 
    613   // Helpers
    614   inline static Operand UntagSmi(Register smi);
    615   inline static Operand UntagSmiAndScale(Register smi, int scale);
    616 
    617  private:
    618   Immediate immediate_;
    619   Register reg_;
    620   Shift shift_;
    621   Extend extend_;
    622   unsigned shift_amount_;
    623 };
    624 
    625 
    626 // MemOperand represents a memory operand in a load or store instruction.
    627 class MemOperand {
    628  public:
    629   inline MemOperand();
    630   inline explicit MemOperand(Register base,
    631                              int64_t offset = 0,
    632                              AddrMode addrmode = Offset);
    633   inline explicit MemOperand(Register base,
    634                              Register regoffset,
    635                              Shift shift = LSL,
    636                              unsigned shift_amount = 0);
    637   inline explicit MemOperand(Register base,
    638                              Register regoffset,
    639                              Extend extend,
    640                              unsigned shift_amount = 0);
    641   inline explicit MemOperand(Register base,
    642                              const Operand& offset,
    643                              AddrMode addrmode = Offset);
    644 
    645   const Register& base() const { return base_; }
    646   const Register& regoffset() const { return regoffset_; }
    647   int64_t offset() const { return offset_; }
    648   AddrMode addrmode() const { return addrmode_; }
    649   Shift shift() const { return shift_; }
    650   Extend extend() const { return extend_; }
    651   unsigned shift_amount() const { return shift_amount_; }
    652   inline bool IsImmediateOffset() const;
    653   inline bool IsRegisterOffset() const;
    654   inline bool IsPreIndex() const;
    655   inline bool IsPostIndex() const;
    656 
    657   // For offset modes, return the offset as an Operand. This helper cannot
    658   // handle indexed modes.
    659   inline Operand OffsetAsOperand() const;
    660 
    661   enum PairResult {
    662     kNotPair,   // Can't use a pair instruction.
    663     kPairAB,    // Can use a pair instruction (operandA has lower address).
    664     kPairBA     // Can use a pair instruction (operandB has lower address).
    665   };
    666   // Check if two MemOperand are consistent for stp/ldp use.
    667   static PairResult AreConsistentForPair(const MemOperand& operandA,
    668                                          const MemOperand& operandB,
    669                                          int access_size_log2 = kXRegSizeLog2);
    670 
    671  private:
    672   Register base_;
    673   Register regoffset_;
    674   int64_t offset_;
    675   AddrMode addrmode_;
    676   Shift shift_;
    677   Extend extend_;
    678   unsigned shift_amount_;
    679 };
    680 
    681 
    682 class ConstPool {
    683  public:
    684   explicit ConstPool(Assembler* assm)
    685       : assm_(assm),
    686         first_use_(-1),
    687         shared_entries_count(0) {}
    688   void RecordEntry(intptr_t data, RelocInfo::Mode mode);
    689   int EntryCount() const {
    690     return shared_entries_count + static_cast<int>(unique_entries_.size());
    691   }
    692   bool IsEmpty() const {
    693     return shared_entries_.empty() && unique_entries_.empty();
    694   }
    695   // Distance in bytes between the current pc and the first instruction
    696   // using the pool. If there are no pending entries return kMaxInt.
    697   int DistanceToFirstUse();
    698   // Offset after which instructions using the pool will be out of range.
    699   int MaxPcOffset();
    700   // Maximum size the constant pool can be with current entries. It always
    701   // includes alignment padding and branch over.
    702   int WorstCaseSize();
    703   // Size in bytes of the literal pool *if* it is emitted at the current
    704   // pc. The size will include the branch over the pool if it was requested.
    705   int SizeIfEmittedAtCurrentPc(bool require_jump);
    706   // Emit the literal pool at the current pc with a branch over the pool if
    707   // requested.
    708   void Emit(bool require_jump);
    709   // Discard any pending pool entries.
    710   void Clear();
    711 
    712  private:
    713   bool CanBeShared(RelocInfo::Mode mode);
    714   void EmitMarker();
    715   void EmitGuard();
    716   void EmitEntries();
    717 
    718   Assembler* assm_;
    719   // Keep track of the first instruction requiring a constant pool entry
    720   // since the previous constant pool was emitted.
    721   int first_use_;
    722   // values, pc offset(s) of entries which can be shared.
    723   std::multimap<uint64_t, int> shared_entries_;
    724   // Number of distinct literal in shared entries.
    725   int shared_entries_count;
    726   // values, pc offset of entries which cannot be shared.
    727   std::vector<std::pair<uint64_t, int> > unique_entries_;
    728 };
    729 
    730 
    731 // -----------------------------------------------------------------------------
    732 // Assembler.
    733 
    734 class Assembler : public AssemblerBase {
    735  public:
    736   // Create an assembler. Instructions and relocation information are emitted
    737   // into a buffer, with the instructions starting from the beginning and the
    738   // relocation information starting from the end of the buffer. See CodeDesc
    739   // for a detailed comment on the layout (globals.h).
    740   //
    741   // If the provided buffer is NULL, the assembler allocates and grows its own
    742   // buffer, and buffer_size determines the initial buffer size. The buffer is
    743   // owned by the assembler and deallocated upon destruction of the assembler.
    744   //
    745   // If the provided buffer is not NULL, the assembler uses the provided buffer
    746   // for code generation and assumes its size to be buffer_size. If the buffer
    747   // is too small, a fatal error occurs. No deallocation of the buffer is done
    748   // upon destruction of the assembler.
    749   Assembler(Isolate* arg_isolate, void* buffer, int buffer_size);
    750 
    751   virtual ~Assembler();
    752 
    753   virtual void AbortedCodeGeneration() {
    754     constpool_.Clear();
    755   }
    756 
    757   // System functions ---------------------------------------------------------
    758   // Start generating code from the beginning of the buffer, discarding any code
    759   // and data that has already been emitted into the buffer.
    760   //
    761   // In order to avoid any accidental transfer of state, Reset DCHECKs that the
    762   // constant pool is not blocked.
    763   void Reset();
    764 
    765   // GetCode emits any pending (non-emitted) code and fills the descriptor
    766   // desc. GetCode() is idempotent; it returns the same result if no other
    767   // Assembler functions are invoked in between GetCode() calls.
    768   //
    769   // The descriptor (desc) can be NULL. In that case, the code is finalized as
    770   // usual, but the descriptor is not populated.
    771   void GetCode(CodeDesc* desc);
    772 
    773   // Insert the smallest number of nop instructions
    774   // possible to align the pc offset to a multiple
    775   // of m. m must be a power of 2 (>= 4).
    776   void Align(int m);
    777   // Insert the smallest number of zero bytes possible to align the pc offset
    778   // to a mulitple of m. m must be a power of 2 (>= 2).
    779   void DataAlign(int m);
    780 
    781   inline void Unreachable();
    782 
    783   // Label --------------------------------------------------------------------
    784   // Bind a label to the current pc. Note that labels can only be bound once,
    785   // and if labels are linked to other instructions, they _must_ be bound
    786   // before they go out of scope.
    787   void bind(Label* label);
    788 
    789 
    790   // RelocInfo and pools ------------------------------------------------------
    791 
    792   // Record relocation information for current pc_.
    793   void RecordRelocInfo(RelocInfo::Mode rmode, intptr_t data = 0);
    794 
    795   // Return the address in the constant pool of the code target address used by
    796   // the branch/call instruction at pc.
    797   inline static Address target_pointer_address_at(Address pc);
    798 
    799   // Read/Modify the code target address in the branch/call instruction at pc.
    800   inline static Address target_address_at(Address pc, Address constant_pool);
    801   inline static void set_target_address_at(
    802       Isolate* isolate, Address pc, Address constant_pool, Address target,
    803       ICacheFlushMode icache_flush_mode = FLUSH_ICACHE_IF_NEEDED);
    804   static inline Address target_address_at(Address pc, Code* code);
    805   static inline void set_target_address_at(
    806       Isolate* isolate, Address pc, Code* code, Address target,
    807       ICacheFlushMode icache_flush_mode = FLUSH_ICACHE_IF_NEEDED);
    808 
    809   // Return the code target address at a call site from the return address of
    810   // that call in the instruction stream.
    811   inline static Address target_address_from_return_address(Address pc);
    812 
    813   // Given the address of the beginning of a call, return the address in the
    814   // instruction stream that call will return from.
    815   inline static Address return_address_from_call_start(Address pc);
    816 
    817   // This sets the branch destination (which is in the constant pool on ARM).
    818   // This is for calls and branches within generated code.
    819   inline static void deserialization_set_special_target_at(
    820       Isolate* isolate, Address constant_pool_entry, Code* code,
    821       Address target);
    822 
    823   // This sets the internal reference at the pc.
    824   inline static void deserialization_set_target_internal_reference_at(
    825       Isolate* isolate, Address pc, Address target,
    826       RelocInfo::Mode mode = RelocInfo::INTERNAL_REFERENCE);
    827 
    828   // All addresses in the constant pool are the same size as pointers.
    829   static const int kSpecialTargetSize = kPointerSize;
    830 
    831   // The sizes of the call sequences emitted by MacroAssembler::Call.
    832   // Wherever possible, use MacroAssembler::CallSize instead of these constants,
    833   // as it will choose the correct value for a given relocation mode.
    834   //
    835   // Without relocation:
    836   //  movz  temp, #(target & 0x000000000000ffff)
    837   //  movk  temp, #(target & 0x00000000ffff0000)
    838   //  movk  temp, #(target & 0x0000ffff00000000)
    839   //  blr   temp
    840   //
    841   // With relocation:
    842   //  ldr   temp, =target
    843   //  blr   temp
    844   static const int kCallSizeWithoutRelocation = 4 * kInstructionSize;
    845   static const int kCallSizeWithRelocation = 2 * kInstructionSize;
    846 
    847   // Size of the generated code in bytes
    848   uint64_t SizeOfGeneratedCode() const {
    849     DCHECK((pc_ >= buffer_) && (pc_ < (buffer_ + buffer_size_)));
    850     return pc_ - buffer_;
    851   }
    852 
    853   // Return the code size generated from label to the current position.
    854   uint64_t SizeOfCodeGeneratedSince(const Label* label) {
    855     DCHECK(label->is_bound());
    856     DCHECK(pc_offset() >= label->pos());
    857     DCHECK(pc_offset() < buffer_size_);
    858     return pc_offset() - label->pos();
    859   }
    860 
    861   // Check the size of the code generated since the given label. This function
    862   // is used primarily to work around comparisons between signed and unsigned
    863   // quantities, since V8 uses both.
    864   // TODO(jbramley): Work out what sign to use for these things and if possible,
    865   // change things to be consistent.
    866   void AssertSizeOfCodeGeneratedSince(const Label* label, ptrdiff_t size) {
    867     DCHECK(size >= 0);
    868     DCHECK(static_cast<uint64_t>(size) == SizeOfCodeGeneratedSince(label));
    869   }
    870 
    871   // Return the number of instructions generated from label to the
    872   // current position.
    873   uint64_t InstructionsGeneratedSince(const Label* label) {
    874     return SizeOfCodeGeneratedSince(label) / kInstructionSize;
    875   }
    876 
    877   static const int kPatchDebugBreakSlotAddressOffset =  0;
    878 
    879   // Number of instructions necessary to be able to later patch it to a call.
    880   static const int kDebugBreakSlotInstructions = 5;
    881   static const int kDebugBreakSlotLength =
    882     kDebugBreakSlotInstructions * kInstructionSize;
    883 
    884   // Prevent contant pool emission until EndBlockConstPool is called.
    885   // Call to this function can be nested but must be followed by an equal
    886   // number of call to EndBlockConstpool.
    887   void StartBlockConstPool();
    888 
    889   // Resume constant pool emission. Need to be called as many time as
    890   // StartBlockConstPool to have an effect.
    891   void EndBlockConstPool();
    892 
    893   bool is_const_pool_blocked() const;
    894   static bool IsConstantPoolAt(Instruction* instr);
    895   static int ConstantPoolSizeAt(Instruction* instr);
    896   // See Assembler::CheckConstPool for more info.
    897   void EmitPoolGuard();
    898 
    899   // Prevent veneer pool emission until EndBlockVeneerPool is called.
    900   // Call to this function can be nested but must be followed by an equal
    901   // number of call to EndBlockConstpool.
    902   void StartBlockVeneerPool();
    903 
    904   // Resume constant pool emission. Need to be called as many time as
    905   // StartBlockVeneerPool to have an effect.
    906   void EndBlockVeneerPool();
    907 
    908   bool is_veneer_pool_blocked() const {
    909     return veneer_pool_blocked_nesting_ > 0;
    910   }
    911 
    912   // Block/resume emission of constant pools and veneer pools.
    913   void StartBlockPools() {
    914     StartBlockConstPool();
    915     StartBlockVeneerPool();
    916   }
    917   void EndBlockPools() {
    918     EndBlockConstPool();
    919     EndBlockVeneerPool();
    920   }
    921 
    922   // Debugging ----------------------------------------------------------------
    923   PositionsRecorder* positions_recorder() { return &positions_recorder_; }
    924   void RecordComment(const char* msg);
    925 
    926   // Record a deoptimization reason that can be used by a log or cpu profiler.
    927   // Use --trace-deopt to enable.
    928   void RecordDeoptReason(const int reason, const SourcePosition position);
    929 
    930   int buffer_space() const;
    931 
    932   // Mark generator continuation.
    933   void RecordGeneratorContinuation();
    934 
    935   // Mark address of a debug break slot.
    936   void RecordDebugBreakSlot(RelocInfo::Mode mode);
    937 
    938   // Record the emission of a constant pool.
    939   //
    940   // The emission of constant and veneer pools depends on the size of the code
    941   // generated and the number of RelocInfo recorded.
    942   // The Debug mechanism needs to map code offsets between two versions of a
    943   // function, compiled with and without debugger support (see for example
    944   // Debug::PrepareForBreakPoints()).
    945   // Compiling functions with debugger support generates additional code
    946   // (DebugCodegen::GenerateSlot()). This may affect the emission of the pools
    947   // and cause the version of the code with debugger support to have pools
    948   // generated in different places.
    949   // Recording the position and size of emitted pools allows to correctly
    950   // compute the offset mappings between the different versions of a function in
    951   // all situations.
    952   //
    953   // The parameter indicates the size of the pool (in bytes), including
    954   // the marker and branch over the data.
    955   void RecordConstPool(int size);
    956 
    957 
    958   // Instruction set functions ------------------------------------------------
    959 
    960   // Branch / Jump instructions.
    961   // For branches offsets are scaled, i.e. they in instrcutions not in bytes.
    962   // Branch to register.
    963   void br(const Register& xn);
    964 
    965   // Branch-link to register.
    966   void blr(const Register& xn);
    967 
    968   // Branch to register with return hint.
    969   void ret(const Register& xn = lr);
    970 
    971   // Unconditional branch to label.
    972   void b(Label* label);
    973 
    974   // Conditional branch to label.
    975   void b(Label* label, Condition cond);
    976 
    977   // Unconditional branch to PC offset.
    978   void b(int imm26);
    979 
    980   // Conditional branch to PC offset.
    981   void b(int imm19, Condition cond);
    982 
    983   // Branch-link to label / pc offset.
    984   void bl(Label* label);
    985   void bl(int imm26);
    986 
    987   // Compare and branch to label / pc offset if zero.
    988   void cbz(const Register& rt, Label* label);
    989   void cbz(const Register& rt, int imm19);
    990 
    991   // Compare and branch to label / pc offset if not zero.
    992   void cbnz(const Register& rt, Label* label);
    993   void cbnz(const Register& rt, int imm19);
    994 
    995   // Test bit and branch to label / pc offset if zero.
    996   void tbz(const Register& rt, unsigned bit_pos, Label* label);
    997   void tbz(const Register& rt, unsigned bit_pos, int imm14);
    998 
    999   // Test bit and branch to label / pc offset if not zero.
   1000   void tbnz(const Register& rt, unsigned bit_pos, Label* label);
   1001   void tbnz(const Register& rt, unsigned bit_pos, int imm14);
   1002 
   1003   // Address calculation instructions.
   1004   // Calculate a PC-relative address. Unlike for branches the offset in adr is
   1005   // unscaled (i.e. the result can be unaligned).
   1006   void adr(const Register& rd, Label* label);
   1007   void adr(const Register& rd, int imm21);
   1008 
   1009   // Data Processing instructions.
   1010   // Add.
   1011   void add(const Register& rd,
   1012            const Register& rn,
   1013            const Operand& operand);
   1014 
   1015   // Add and update status flags.
   1016   void adds(const Register& rd,
   1017             const Register& rn,
   1018             const Operand& operand);
   1019 
   1020   // Compare negative.
   1021   void cmn(const Register& rn, const Operand& operand);
   1022 
   1023   // Subtract.
   1024   void sub(const Register& rd,
   1025            const Register& rn,
   1026            const Operand& operand);
   1027 
   1028   // Subtract and update status flags.
   1029   void subs(const Register& rd,
   1030             const Register& rn,
   1031             const Operand& operand);
   1032 
   1033   // Compare.
   1034   void cmp(const Register& rn, const Operand& operand);
   1035 
   1036   // Negate.
   1037   void neg(const Register& rd,
   1038            const Operand& operand);
   1039 
   1040   // Negate and update status flags.
   1041   void negs(const Register& rd,
   1042             const Operand& operand);
   1043 
   1044   // Add with carry bit.
   1045   void adc(const Register& rd,
   1046            const Register& rn,
   1047            const Operand& operand);
   1048 
   1049   // Add with carry bit and update status flags.
   1050   void adcs(const Register& rd,
   1051             const Register& rn,
   1052             const Operand& operand);
   1053 
   1054   // Subtract with carry bit.
   1055   void sbc(const Register& rd,
   1056            const Register& rn,
   1057            const Operand& operand);
   1058 
   1059   // Subtract with carry bit and update status flags.
   1060   void sbcs(const Register& rd,
   1061             const Register& rn,
   1062             const Operand& operand);
   1063 
   1064   // Negate with carry bit.
   1065   void ngc(const Register& rd,
   1066            const Operand& operand);
   1067 
   1068   // Negate with carry bit and update status flags.
   1069   void ngcs(const Register& rd,
   1070             const Operand& operand);
   1071 
   1072   // Logical instructions.
   1073   // Bitwise and (A & B).
   1074   void and_(const Register& rd,
   1075             const Register& rn,
   1076             const Operand& operand);
   1077 
   1078   // Bitwise and (A & B) and update status flags.
   1079   void ands(const Register& rd,
   1080             const Register& rn,
   1081             const Operand& operand);
   1082 
   1083   // Bit test, and set flags.
   1084   void tst(const Register& rn, const Operand& operand);
   1085 
   1086   // Bit clear (A & ~B).
   1087   void bic(const Register& rd,
   1088            const Register& rn,
   1089            const Operand& operand);
   1090 
   1091   // Bit clear (A & ~B) and update status flags.
   1092   void bics(const Register& rd,
   1093             const Register& rn,
   1094             const Operand& operand);
   1095 
   1096   // Bitwise or (A | B).
   1097   void orr(const Register& rd, const Register& rn, const Operand& operand);
   1098 
   1099   // Bitwise nor (A | ~B).
   1100   void orn(const Register& rd, const Register& rn, const Operand& operand);
   1101 
   1102   // Bitwise eor/xor (A ^ B).
   1103   void eor(const Register& rd, const Register& rn, const Operand& operand);
   1104 
   1105   // Bitwise enor/xnor (A ^ ~B).
   1106   void eon(const Register& rd, const Register& rn, const Operand& operand);
   1107 
   1108   // Logical shift left variable.
   1109   void lslv(const Register& rd, const Register& rn, const Register& rm);
   1110 
   1111   // Logical shift right variable.
   1112   void lsrv(const Register& rd, const Register& rn, const Register& rm);
   1113 
   1114   // Arithmetic shift right variable.
   1115   void asrv(const Register& rd, const Register& rn, const Register& rm);
   1116 
   1117   // Rotate right variable.
   1118   void rorv(const Register& rd, const Register& rn, const Register& rm);
   1119 
   1120   // Bitfield instructions.
   1121   // Bitfield move.
   1122   void bfm(const Register& rd, const Register& rn, int immr, int imms);
   1123 
   1124   // Signed bitfield move.
   1125   void sbfm(const Register& rd, const Register& rn, int immr, int imms);
   1126 
   1127   // Unsigned bitfield move.
   1128   void ubfm(const Register& rd, const Register& rn, int immr, int imms);
   1129 
   1130   // Bfm aliases.
   1131   // Bitfield insert.
   1132   void bfi(const Register& rd, const Register& rn, int lsb, int width) {
   1133     DCHECK(width >= 1);
   1134     DCHECK(lsb + width <= rn.SizeInBits());
   1135     bfm(rd, rn, (rd.SizeInBits() - lsb) & (rd.SizeInBits() - 1), width - 1);
   1136   }
   1137 
   1138   // Bitfield extract and insert low.
   1139   void bfxil(const Register& rd, const Register& rn, int lsb, int width) {
   1140     DCHECK(width >= 1);
   1141     DCHECK(lsb + width <= rn.SizeInBits());
   1142     bfm(rd, rn, lsb, lsb + width - 1);
   1143   }
   1144 
   1145   // Sbfm aliases.
   1146   // Arithmetic shift right.
   1147   void asr(const Register& rd, const Register& rn, int shift) {
   1148     DCHECK(shift < rd.SizeInBits());
   1149     sbfm(rd, rn, shift, rd.SizeInBits() - 1);
   1150   }
   1151 
   1152   // Signed bitfield insert in zero.
   1153   void sbfiz(const Register& rd, const Register& rn, int lsb, int width) {
   1154     DCHECK(width >= 1);
   1155     DCHECK(lsb + width <= rn.SizeInBits());
   1156     sbfm(rd, rn, (rd.SizeInBits() - lsb) & (rd.SizeInBits() - 1), width - 1);
   1157   }
   1158 
   1159   // Signed bitfield extract.
   1160   void sbfx(const Register& rd, const Register& rn, int lsb, int width) {
   1161     DCHECK(width >= 1);
   1162     DCHECK(lsb + width <= rn.SizeInBits());
   1163     sbfm(rd, rn, lsb, lsb + width - 1);
   1164   }
   1165 
   1166   // Signed extend byte.
   1167   void sxtb(const Register& rd, const Register& rn) {
   1168     sbfm(rd, rn, 0, 7);
   1169   }
   1170 
   1171   // Signed extend halfword.
   1172   void sxth(const Register& rd, const Register& rn) {
   1173     sbfm(rd, rn, 0, 15);
   1174   }
   1175 
   1176   // Signed extend word.
   1177   void sxtw(const Register& rd, const Register& rn) {
   1178     sbfm(rd, rn, 0, 31);
   1179   }
   1180 
   1181   // Ubfm aliases.
   1182   // Logical shift left.
   1183   void lsl(const Register& rd, const Register& rn, int shift) {
   1184     int reg_size = rd.SizeInBits();
   1185     DCHECK(shift < reg_size);
   1186     ubfm(rd, rn, (reg_size - shift) % reg_size, reg_size - shift - 1);
   1187   }
   1188 
   1189   // Logical shift right.
   1190   void lsr(const Register& rd, const Register& rn, int shift) {
   1191     DCHECK(shift < rd.SizeInBits());
   1192     ubfm(rd, rn, shift, rd.SizeInBits() - 1);
   1193   }
   1194 
   1195   // Unsigned bitfield insert in zero.
   1196   void ubfiz(const Register& rd, const Register& rn, int lsb, int width) {
   1197     DCHECK(width >= 1);
   1198     DCHECK(lsb + width <= rn.SizeInBits());
   1199     ubfm(rd, rn, (rd.SizeInBits() - lsb) & (rd.SizeInBits() - 1), width - 1);
   1200   }
   1201 
   1202   // Unsigned bitfield extract.
   1203   void ubfx(const Register& rd, const Register& rn, int lsb, int width) {
   1204     DCHECK(width >= 1);
   1205     DCHECK(lsb + width <= rn.SizeInBits());
   1206     ubfm(rd, rn, lsb, lsb + width - 1);
   1207   }
   1208 
   1209   // Unsigned extend byte.
   1210   void uxtb(const Register& rd, const Register& rn) {
   1211     ubfm(rd, rn, 0, 7);
   1212   }
   1213 
   1214   // Unsigned extend halfword.
   1215   void uxth(const Register& rd, const Register& rn) {
   1216     ubfm(rd, rn, 0, 15);
   1217   }
   1218 
   1219   // Unsigned extend word.
   1220   void uxtw(const Register& rd, const Register& rn) {
   1221     ubfm(rd, rn, 0, 31);
   1222   }
   1223 
   1224   // Extract.
   1225   void extr(const Register& rd, const Register& rn, const Register& rm,
   1226             int lsb);
   1227 
   1228   // Conditional select: rd = cond ? rn : rm.
   1229   void csel(const Register& rd,
   1230             const Register& rn,
   1231             const Register& rm,
   1232             Condition cond);
   1233 
   1234   // Conditional select increment: rd = cond ? rn : rm + 1.
   1235   void csinc(const Register& rd,
   1236              const Register& rn,
   1237              const Register& rm,
   1238              Condition cond);
   1239 
   1240   // Conditional select inversion: rd = cond ? rn : ~rm.
   1241   void csinv(const Register& rd,
   1242              const Register& rn,
   1243              const Register& rm,
   1244              Condition cond);
   1245 
   1246   // Conditional select negation: rd = cond ? rn : -rm.
   1247   void csneg(const Register& rd,
   1248              const Register& rn,
   1249              const Register& rm,
   1250              Condition cond);
   1251 
   1252   // Conditional set: rd = cond ? 1 : 0.
   1253   void cset(const Register& rd, Condition cond);
   1254 
   1255   // Conditional set minus: rd = cond ? -1 : 0.
   1256   void csetm(const Register& rd, Condition cond);
   1257 
   1258   // Conditional increment: rd = cond ? rn + 1 : rn.
   1259   void cinc(const Register& rd, const Register& rn, Condition cond);
   1260 
   1261   // Conditional invert: rd = cond ? ~rn : rn.
   1262   void cinv(const Register& rd, const Register& rn, Condition cond);
   1263 
   1264   // Conditional negate: rd = cond ? -rn : rn.
   1265   void cneg(const Register& rd, const Register& rn, Condition cond);
   1266 
   1267   // Extr aliases.
   1268   void ror(const Register& rd, const Register& rs, unsigned shift) {
   1269     extr(rd, rs, rs, shift);
   1270   }
   1271 
   1272   // Conditional comparison.
   1273   // Conditional compare negative.
   1274   void ccmn(const Register& rn,
   1275             const Operand& operand,
   1276             StatusFlags nzcv,
   1277             Condition cond);
   1278 
   1279   // Conditional compare.
   1280   void ccmp(const Register& rn,
   1281             const Operand& operand,
   1282             StatusFlags nzcv,
   1283             Condition cond);
   1284 
   1285   // Multiplication.
   1286   // 32 x 32 -> 32-bit and 64 x 64 -> 64-bit multiply.
   1287   void mul(const Register& rd, const Register& rn, const Register& rm);
   1288 
   1289   // 32 + 32 x 32 -> 32-bit and 64 + 64 x 64 -> 64-bit multiply accumulate.
   1290   void madd(const Register& rd,
   1291             const Register& rn,
   1292             const Register& rm,
   1293             const Register& ra);
   1294 
   1295   // -(32 x 32) -> 32-bit and -(64 x 64) -> 64-bit multiply.
   1296   void mneg(const Register& rd, const Register& rn, const Register& rm);
   1297 
   1298   // 32 - 32 x 32 -> 32-bit and 64 - 64 x 64 -> 64-bit multiply subtract.
   1299   void msub(const Register& rd,
   1300             const Register& rn,
   1301             const Register& rm,
   1302             const Register& ra);
   1303 
   1304   // 32 x 32 -> 64-bit multiply.
   1305   void smull(const Register& rd, const Register& rn, const Register& rm);
   1306 
   1307   // Xd = bits<127:64> of Xn * Xm.
   1308   void smulh(const Register& rd, const Register& rn, const Register& rm);
   1309 
   1310   // Signed 32 x 32 -> 64-bit multiply and accumulate.
   1311   void smaddl(const Register& rd,
   1312               const Register& rn,
   1313               const Register& rm,
   1314               const Register& ra);
   1315 
   1316   // Unsigned 32 x 32 -> 64-bit multiply and accumulate.
   1317   void umaddl(const Register& rd,
   1318               const Register& rn,
   1319               const Register& rm,
   1320               const Register& ra);
   1321 
   1322   // Signed 32 x 32 -> 64-bit multiply and subtract.
   1323   void smsubl(const Register& rd,
   1324               const Register& rn,
   1325               const Register& rm,
   1326               const Register& ra);
   1327 
   1328   // Unsigned 32 x 32 -> 64-bit multiply and subtract.
   1329   void umsubl(const Register& rd,
   1330               const Register& rn,
   1331               const Register& rm,
   1332               const Register& ra);
   1333 
   1334   // Signed integer divide.
   1335   void sdiv(const Register& rd, const Register& rn, const Register& rm);
   1336 
   1337   // Unsigned integer divide.
   1338   void udiv(const Register& rd, const Register& rn, const Register& rm);
   1339 
   1340   // Bit count, bit reverse and endian reverse.
   1341   void rbit(const Register& rd, const Register& rn);
   1342   void rev16(const Register& rd, const Register& rn);
   1343   void rev32(const Register& rd, const Register& rn);
   1344   void rev(const Register& rd, const Register& rn);
   1345   void clz(const Register& rd, const Register& rn);
   1346   void cls(const Register& rd, const Register& rn);
   1347 
   1348   // Memory instructions.
   1349 
   1350   // Load integer or FP register.
   1351   void ldr(const CPURegister& rt, const MemOperand& src);
   1352 
   1353   // Store integer or FP register.
   1354   void str(const CPURegister& rt, const MemOperand& dst);
   1355 
   1356   // Load word with sign extension.
   1357   void ldrsw(const Register& rt, const MemOperand& src);
   1358 
   1359   // Load byte.
   1360   void ldrb(const Register& rt, const MemOperand& src);
   1361 
   1362   // Store byte.
   1363   void strb(const Register& rt, const MemOperand& dst);
   1364 
   1365   // Load byte with sign extension.
   1366   void ldrsb(const Register& rt, const MemOperand& src);
   1367 
   1368   // Load half-word.
   1369   void ldrh(const Register& rt, const MemOperand& src);
   1370 
   1371   // Store half-word.
   1372   void strh(const Register& rt, const MemOperand& dst);
   1373 
   1374   // Load half-word with sign extension.
   1375   void ldrsh(const Register& rt, const MemOperand& src);
   1376 
   1377   // Load integer or FP register pair.
   1378   void ldp(const CPURegister& rt, const CPURegister& rt2,
   1379            const MemOperand& src);
   1380 
   1381   // Store integer or FP register pair.
   1382   void stp(const CPURegister& rt, const CPURegister& rt2,
   1383            const MemOperand& dst);
   1384 
   1385   // Load word pair with sign extension.
   1386   void ldpsw(const Register& rt, const Register& rt2, const MemOperand& src);
   1387 
   1388   // Load literal to register from a pc relative address.
   1389   void ldr_pcrel(const CPURegister& rt, int imm19);
   1390 
   1391   // Load literal to register.
   1392   void ldr(const CPURegister& rt, const Immediate& imm);
   1393 
   1394   // Move instructions. The default shift of -1 indicates that the move
   1395   // instruction will calculate an appropriate 16-bit immediate and left shift
   1396   // that is equal to the 64-bit immediate argument. If an explicit left shift
   1397   // is specified (0, 16, 32 or 48), the immediate must be a 16-bit value.
   1398   //
   1399   // For movk, an explicit shift can be used to indicate which half word should
   1400   // be overwritten, eg. movk(x0, 0, 0) will overwrite the least-significant
   1401   // half word with zero, whereas movk(x0, 0, 48) will overwrite the
   1402   // most-significant.
   1403 
   1404   // Move and keep.
   1405   void movk(const Register& rd, uint64_t imm, int shift = -1) {
   1406     MoveWide(rd, imm, shift, MOVK);
   1407   }
   1408 
   1409   // Move with non-zero.
   1410   void movn(const Register& rd, uint64_t imm, int shift = -1) {
   1411     MoveWide(rd, imm, shift, MOVN);
   1412   }
   1413 
   1414   // Move with zero.
   1415   void movz(const Register& rd, uint64_t imm, int shift = -1) {
   1416     MoveWide(rd, imm, shift, MOVZ);
   1417   }
   1418 
   1419   // Misc instructions.
   1420   // Monitor debug-mode breakpoint.
   1421   void brk(int code);
   1422 
   1423   // Halting debug-mode breakpoint.
   1424   void hlt(int code);
   1425 
   1426   // Move register to register.
   1427   void mov(const Register& rd, const Register& rn);
   1428 
   1429   // Move NOT(operand) to register.
   1430   void mvn(const Register& rd, const Operand& operand);
   1431 
   1432   // System instructions.
   1433   // Move to register from system register.
   1434   void mrs(const Register& rt, SystemRegister sysreg);
   1435 
   1436   // Move from register to system register.
   1437   void msr(SystemRegister sysreg, const Register& rt);
   1438 
   1439   // System hint.
   1440   void hint(SystemHint code);
   1441 
   1442   // Data memory barrier
   1443   void dmb(BarrierDomain domain, BarrierType type);
   1444 
   1445   // Data synchronization barrier
   1446   void dsb(BarrierDomain domain, BarrierType type);
   1447 
   1448   // Instruction synchronization barrier
   1449   void isb();
   1450 
   1451   // Alias for system instructions.
   1452   void nop() { hint(NOP); }
   1453 
   1454   // Different nop operations are used by the code generator to detect certain
   1455   // states of the generated code.
   1456   enum NopMarkerTypes {
   1457     DEBUG_BREAK_NOP,
   1458     INTERRUPT_CODE_NOP,
   1459     ADR_FAR_NOP,
   1460     FIRST_NOP_MARKER = DEBUG_BREAK_NOP,
   1461     LAST_NOP_MARKER = ADR_FAR_NOP
   1462   };
   1463 
   1464   void nop(NopMarkerTypes n) {
   1465     DCHECK((FIRST_NOP_MARKER <= n) && (n <= LAST_NOP_MARKER));
   1466     mov(Register::XRegFromCode(n), Register::XRegFromCode(n));
   1467   }
   1468 
   1469   // FP instructions.
   1470   // Move immediate to FP register.
   1471   void fmov(FPRegister fd, double imm);
   1472   void fmov(FPRegister fd, float imm);
   1473 
   1474   // Move FP register to register.
   1475   void fmov(Register rd, FPRegister fn);
   1476 
   1477   // Move register to FP register.
   1478   void fmov(FPRegister fd, Register rn);
   1479 
   1480   // Move FP register to FP register.
   1481   void fmov(FPRegister fd, FPRegister fn);
   1482 
   1483   // FP add.
   1484   void fadd(const FPRegister& fd, const FPRegister& fn, const FPRegister& fm);
   1485 
   1486   // FP subtract.
   1487   void fsub(const FPRegister& fd, const FPRegister& fn, const FPRegister& fm);
   1488 
   1489   // FP multiply.
   1490   void fmul(const FPRegister& fd, const FPRegister& fn, const FPRegister& fm);
   1491 
   1492   // FP fused multiply and add.
   1493   void fmadd(const FPRegister& fd,
   1494              const FPRegister& fn,
   1495              const FPRegister& fm,
   1496              const FPRegister& fa);
   1497 
   1498   // FP fused multiply and subtract.
   1499   void fmsub(const FPRegister& fd,
   1500              const FPRegister& fn,
   1501              const FPRegister& fm,
   1502              const FPRegister& fa);
   1503 
   1504   // FP fused multiply, add and negate.
   1505   void fnmadd(const FPRegister& fd,
   1506               const FPRegister& fn,
   1507               const FPRegister& fm,
   1508               const FPRegister& fa);
   1509 
   1510   // FP fused multiply, subtract and negate.
   1511   void fnmsub(const FPRegister& fd,
   1512               const FPRegister& fn,
   1513               const FPRegister& fm,
   1514               const FPRegister& fa);
   1515 
   1516   // FP divide.
   1517   void fdiv(const FPRegister& fd, const FPRegister& fn, const FPRegister& fm);
   1518 
   1519   // FP maximum.
   1520   void fmax(const FPRegister& fd, const FPRegister& fn, const FPRegister& fm);
   1521 
   1522   // FP minimum.
   1523   void fmin(const FPRegister& fd, const FPRegister& fn, const FPRegister& fm);
   1524 
   1525   // FP maximum.
   1526   void fmaxnm(const FPRegister& fd, const FPRegister& fn, const FPRegister& fm);
   1527 
   1528   // FP minimum.
   1529   void fminnm(const FPRegister& fd, const FPRegister& fn, const FPRegister& fm);
   1530 
   1531   // FP absolute.
   1532   void fabs(const FPRegister& fd, const FPRegister& fn);
   1533 
   1534   // FP negate.
   1535   void fneg(const FPRegister& fd, const FPRegister& fn);
   1536 
   1537   // FP square root.
   1538   void fsqrt(const FPRegister& fd, const FPRegister& fn);
   1539 
   1540   // FP round to integer (nearest with ties to away).
   1541   void frinta(const FPRegister& fd, const FPRegister& fn);
   1542 
   1543   // FP round to integer (toward minus infinity).
   1544   void frintm(const FPRegister& fd, const FPRegister& fn);
   1545 
   1546   // FP round to integer (nearest with ties to even).
   1547   void frintn(const FPRegister& fd, const FPRegister& fn);
   1548 
   1549   // FP round to integer (towards plus infinity).
   1550   void frintp(const FPRegister& fd, const FPRegister& fn);
   1551 
   1552   // FP round to integer (towards zero.)
   1553   void frintz(const FPRegister& fd, const FPRegister& fn);
   1554 
   1555   // FP compare registers.
   1556   void fcmp(const FPRegister& fn, const FPRegister& fm);
   1557 
   1558   // FP compare immediate.
   1559   void fcmp(const FPRegister& fn, double value);
   1560 
   1561   // FP conditional compare.
   1562   void fccmp(const FPRegister& fn,
   1563              const FPRegister& fm,
   1564              StatusFlags nzcv,
   1565              Condition cond);
   1566 
   1567   // FP conditional select.
   1568   void fcsel(const FPRegister& fd,
   1569              const FPRegister& fn,
   1570              const FPRegister& fm,
   1571              Condition cond);
   1572 
   1573   // Common FP Convert function
   1574   void FPConvertToInt(const Register& rd,
   1575                       const FPRegister& fn,
   1576                       FPIntegerConvertOp op);
   1577 
   1578   // FP convert between single and double precision.
   1579   void fcvt(const FPRegister& fd, const FPRegister& fn);
   1580 
   1581   // Convert FP to unsigned integer (nearest with ties to away).
   1582   void fcvtau(const Register& rd, const FPRegister& fn);
   1583 
   1584   // Convert FP to signed integer (nearest with ties to away).
   1585   void fcvtas(const Register& rd, const FPRegister& fn);
   1586 
   1587   // Convert FP to unsigned integer (round towards -infinity).
   1588   void fcvtmu(const Register& rd, const FPRegister& fn);
   1589 
   1590   // Convert FP to signed integer (round towards -infinity).
   1591   void fcvtms(const Register& rd, const FPRegister& fn);
   1592 
   1593   // Convert FP to unsigned integer (nearest with ties to even).
   1594   void fcvtnu(const Register& rd, const FPRegister& fn);
   1595 
   1596   // Convert FP to signed integer (nearest with ties to even).
   1597   void fcvtns(const Register& rd, const FPRegister& fn);
   1598 
   1599   // Convert FP to unsigned integer (round towards zero).
   1600   void fcvtzu(const Register& rd, const FPRegister& fn);
   1601 
   1602   // Convert FP to signed integer (rounf towards zero).
   1603   void fcvtzs(const Register& rd, const FPRegister& fn);
   1604 
   1605   // Convert signed integer or fixed point to FP.
   1606   void scvtf(const FPRegister& fd, const Register& rn, unsigned fbits = 0);
   1607 
   1608   // Convert unsigned integer or fixed point to FP.
   1609   void ucvtf(const FPRegister& fd, const Register& rn, unsigned fbits = 0);
   1610 
   1611   // Instruction functions used only for test, debug, and patching.
   1612   // Emit raw instructions in the instruction stream.
   1613   void dci(Instr raw_inst) { Emit(raw_inst); }
   1614 
   1615   // Emit 8 bits of data in the instruction stream.
   1616   void dc8(uint8_t data) { EmitData(&data, sizeof(data)); }
   1617 
   1618   // Emit 32 bits of data in the instruction stream.
   1619   void dc32(uint32_t data) { EmitData(&data, sizeof(data)); }
   1620 
   1621   // Emit 64 bits of data in the instruction stream.
   1622   void dc64(uint64_t data) { EmitData(&data, sizeof(data)); }
   1623 
   1624   // Emit an address in the instruction stream.
   1625   void dcptr(Label* label);
   1626 
   1627   // Copy a string into the instruction stream, including the terminating NULL
   1628   // character. The instruction pointer (pc_) is then aligned correctly for
   1629   // subsequent instructions.
   1630   void EmitStringData(const char* string);
   1631 
   1632   // Pseudo-instructions ------------------------------------------------------
   1633 
   1634   // Parameters are described in arm64/instructions-arm64.h.
   1635   void debug(const char* message, uint32_t code, Instr params = BREAK);
   1636 
   1637   // Required by V8.
   1638   void dd(uint32_t data) { dc32(data); }
   1639   void db(uint8_t data) { dc8(data); }
   1640   void dq(uint64_t data) { dc64(data); }
   1641   void dp(uintptr_t data) { dc64(data); }
   1642 
   1643   // Code generation helpers --------------------------------------------------
   1644 
   1645   bool IsConstPoolEmpty() const { return constpool_.IsEmpty(); }
   1646 
   1647   Instruction* pc() const { return Instruction::Cast(pc_); }
   1648 
   1649   Instruction* InstructionAt(ptrdiff_t offset) const {
   1650     return reinterpret_cast<Instruction*>(buffer_ + offset);
   1651   }
   1652 
   1653   ptrdiff_t InstructionOffset(Instruction* instr) const {
   1654     return reinterpret_cast<byte*>(instr) - buffer_;
   1655   }
   1656 
   1657   // Register encoding.
   1658   static Instr Rd(CPURegister rd) {
   1659     DCHECK(rd.code() != kSPRegInternalCode);
   1660     return rd.code() << Rd_offset;
   1661   }
   1662 
   1663   static Instr Rn(CPURegister rn) {
   1664     DCHECK(rn.code() != kSPRegInternalCode);
   1665     return rn.code() << Rn_offset;
   1666   }
   1667 
   1668   static Instr Rm(CPURegister rm) {
   1669     DCHECK(rm.code() != kSPRegInternalCode);
   1670     return rm.code() << Rm_offset;
   1671   }
   1672 
   1673   static Instr Ra(CPURegister ra) {
   1674     DCHECK(ra.code() != kSPRegInternalCode);
   1675     return ra.code() << Ra_offset;
   1676   }
   1677 
   1678   static Instr Rt(CPURegister rt) {
   1679     DCHECK(rt.code() != kSPRegInternalCode);
   1680     return rt.code() << Rt_offset;
   1681   }
   1682 
   1683   static Instr Rt2(CPURegister rt2) {
   1684     DCHECK(rt2.code() != kSPRegInternalCode);
   1685     return rt2.code() << Rt2_offset;
   1686   }
   1687 
   1688   // These encoding functions allow the stack pointer to be encoded, and
   1689   // disallow the zero register.
   1690   static Instr RdSP(Register rd) {
   1691     DCHECK(!rd.IsZero());
   1692     return (rd.code() & kRegCodeMask) << Rd_offset;
   1693   }
   1694 
   1695   static Instr RnSP(Register rn) {
   1696     DCHECK(!rn.IsZero());
   1697     return (rn.code() & kRegCodeMask) << Rn_offset;
   1698   }
   1699 
   1700   // Flags encoding.
   1701   inline static Instr Flags(FlagsUpdate S);
   1702   inline static Instr Cond(Condition cond);
   1703 
   1704   // PC-relative address encoding.
   1705   inline static Instr ImmPCRelAddress(int imm21);
   1706 
   1707   // Branch encoding.
   1708   inline static Instr ImmUncondBranch(int imm26);
   1709   inline static Instr ImmCondBranch(int imm19);
   1710   inline static Instr ImmCmpBranch(int imm19);
   1711   inline static Instr ImmTestBranch(int imm14);
   1712   inline static Instr ImmTestBranchBit(unsigned bit_pos);
   1713 
   1714   // Data Processing encoding.
   1715   inline static Instr SF(Register rd);
   1716   inline static Instr ImmAddSub(int imm);
   1717   inline static Instr ImmS(unsigned imms, unsigned reg_size);
   1718   inline static Instr ImmR(unsigned immr, unsigned reg_size);
   1719   inline static Instr ImmSetBits(unsigned imms, unsigned reg_size);
   1720   inline static Instr ImmRotate(unsigned immr, unsigned reg_size);
   1721   inline static Instr ImmLLiteral(int imm19);
   1722   inline static Instr BitN(unsigned bitn, unsigned reg_size);
   1723   inline static Instr ShiftDP(Shift shift);
   1724   inline static Instr ImmDPShift(unsigned amount);
   1725   inline static Instr ExtendMode(Extend extend);
   1726   inline static Instr ImmExtendShift(unsigned left_shift);
   1727   inline static Instr ImmCondCmp(unsigned imm);
   1728   inline static Instr Nzcv(StatusFlags nzcv);
   1729 
   1730   static bool IsImmAddSub(int64_t immediate);
   1731   static bool IsImmLogical(uint64_t value,
   1732                            unsigned width,
   1733                            unsigned* n,
   1734                            unsigned* imm_s,
   1735                            unsigned* imm_r);
   1736 
   1737   // MemOperand offset encoding.
   1738   inline static Instr ImmLSUnsigned(int imm12);
   1739   inline static Instr ImmLS(int imm9);
   1740   inline static Instr ImmLSPair(int imm7, LSDataSize size);
   1741   inline static Instr ImmShiftLS(unsigned shift_amount);
   1742   inline static Instr ImmException(int imm16);
   1743   inline static Instr ImmSystemRegister(int imm15);
   1744   inline static Instr ImmHint(int imm7);
   1745   inline static Instr ImmBarrierDomain(int imm2);
   1746   inline static Instr ImmBarrierType(int imm2);
   1747   inline static LSDataSize CalcLSDataSize(LoadStoreOp op);
   1748 
   1749   static bool IsImmLSUnscaled(int64_t offset);
   1750   static bool IsImmLSScaled(int64_t offset, LSDataSize size);
   1751   static bool IsImmLLiteral(int64_t offset);
   1752 
   1753   // Move immediates encoding.
   1754   inline static Instr ImmMoveWide(int imm);
   1755   inline static Instr ShiftMoveWide(int shift);
   1756 
   1757   // FP Immediates.
   1758   static Instr ImmFP32(float imm);
   1759   static Instr ImmFP64(double imm);
   1760   inline static Instr FPScale(unsigned scale);
   1761 
   1762   // FP register type.
   1763   inline static Instr FPType(FPRegister fd);
   1764 
   1765   // Class for scoping postponing the constant pool generation.
   1766   class BlockConstPoolScope {
   1767    public:
   1768     explicit BlockConstPoolScope(Assembler* assem) : assem_(assem) {
   1769       assem_->StartBlockConstPool();
   1770     }
   1771     ~BlockConstPoolScope() {
   1772       assem_->EndBlockConstPool();
   1773     }
   1774 
   1775    private:
   1776     Assembler* assem_;
   1777 
   1778     DISALLOW_IMPLICIT_CONSTRUCTORS(BlockConstPoolScope);
   1779   };
   1780 
   1781   // Check if is time to emit a constant pool.
   1782   void CheckConstPool(bool force_emit, bool require_jump);
   1783 
   1784   void PatchConstantPoolAccessInstruction(int pc_offset, int offset,
   1785                                           ConstantPoolEntry::Access access,
   1786                                           ConstantPoolEntry::Type type) {
   1787     // No embedded constant pool support.
   1788     UNREACHABLE();
   1789   }
   1790 
   1791   // Returns true if we should emit a veneer as soon as possible for a branch
   1792   // which can at most reach to specified pc.
   1793   bool ShouldEmitVeneer(int max_reachable_pc,
   1794                         int margin = kVeneerDistanceMargin);
   1795   bool ShouldEmitVeneers(int margin = kVeneerDistanceMargin) {
   1796     return ShouldEmitVeneer(unresolved_branches_first_limit(), margin);
   1797   }
   1798 
   1799   // The maximum code size generated for a veneer. Currently one branch
   1800   // instruction. This is for code size checking purposes, and can be extended
   1801   // in the future for example if we decide to add nops between the veneers.
   1802   static const int kMaxVeneerCodeSize = 1 * kInstructionSize;
   1803 
   1804   void RecordVeneerPool(int location_offset, int size);
   1805   // Emits veneers for branches that are approaching their maximum range.
   1806   // If need_protection is true, the veneers are protected by a branch jumping
   1807   // over the code.
   1808   void EmitVeneers(bool force_emit, bool need_protection,
   1809                    int margin = kVeneerDistanceMargin);
   1810   void EmitVeneersGuard() { EmitPoolGuard(); }
   1811   // Checks whether veneers need to be emitted at this point.
   1812   // If force_emit is set, a veneer is generated for *all* unresolved branches.
   1813   void CheckVeneerPool(bool force_emit, bool require_jump,
   1814                        int margin = kVeneerDistanceMargin);
   1815 
   1816   class BlockPoolsScope {
   1817    public:
   1818     explicit BlockPoolsScope(Assembler* assem) : assem_(assem) {
   1819       assem_->StartBlockPools();
   1820     }
   1821     ~BlockPoolsScope() {
   1822       assem_->EndBlockPools();
   1823     }
   1824 
   1825    private:
   1826     Assembler* assem_;
   1827 
   1828     DISALLOW_IMPLICIT_CONSTRUCTORS(BlockPoolsScope);
   1829   };
   1830 
   1831  protected:
   1832   inline const Register& AppropriateZeroRegFor(const CPURegister& reg) const;
   1833 
   1834   void LoadStore(const CPURegister& rt,
   1835                  const MemOperand& addr,
   1836                  LoadStoreOp op);
   1837 
   1838   void LoadStorePair(const CPURegister& rt, const CPURegister& rt2,
   1839                      const MemOperand& addr, LoadStorePairOp op);
   1840   static bool IsImmLSPair(int64_t offset, LSDataSize size);
   1841 
   1842   void Logical(const Register& rd,
   1843                const Register& rn,
   1844                const Operand& operand,
   1845                LogicalOp op);
   1846   void LogicalImmediate(const Register& rd,
   1847                         const Register& rn,
   1848                         unsigned n,
   1849                         unsigned imm_s,
   1850                         unsigned imm_r,
   1851                         LogicalOp op);
   1852 
   1853   void ConditionalCompare(const Register& rn,
   1854                           const Operand& operand,
   1855                           StatusFlags nzcv,
   1856                           Condition cond,
   1857                           ConditionalCompareOp op);
   1858   static bool IsImmConditionalCompare(int64_t immediate);
   1859 
   1860   void AddSubWithCarry(const Register& rd,
   1861                        const Register& rn,
   1862                        const Operand& operand,
   1863                        FlagsUpdate S,
   1864                        AddSubWithCarryOp op);
   1865 
   1866   // Functions for emulating operands not directly supported by the instruction
   1867   // set.
   1868   void EmitShift(const Register& rd,
   1869                  const Register& rn,
   1870                  Shift shift,
   1871                  unsigned amount);
   1872   void EmitExtendShift(const Register& rd,
   1873                        const Register& rn,
   1874                        Extend extend,
   1875                        unsigned left_shift);
   1876 
   1877   void AddSub(const Register& rd,
   1878               const Register& rn,
   1879               const Operand& operand,
   1880               FlagsUpdate S,
   1881               AddSubOp op);
   1882 
   1883   static bool IsImmFP32(float imm);
   1884   static bool IsImmFP64(double imm);
   1885 
   1886   // Find an appropriate LoadStoreOp or LoadStorePairOp for the specified
   1887   // registers. Only simple loads are supported; sign- and zero-extension (such
   1888   // as in LDPSW_x or LDRB_w) are not supported.
   1889   static inline LoadStoreOp LoadOpFor(const CPURegister& rt);
   1890   static inline LoadStorePairOp LoadPairOpFor(const CPURegister& rt,
   1891                                               const CPURegister& rt2);
   1892   static inline LoadStoreOp StoreOpFor(const CPURegister& rt);
   1893   static inline LoadStorePairOp StorePairOpFor(const CPURegister& rt,
   1894                                                const CPURegister& rt2);
   1895   static inline LoadLiteralOp LoadLiteralOpFor(const CPURegister& rt);
   1896 
   1897   // Remove the specified branch from the unbound label link chain.
   1898   // If available, a veneer for this label can be used for other branches in the
   1899   // chain if the link chain cannot be fixed up without this branch.
   1900   void RemoveBranchFromLabelLinkChain(Instruction* branch,
   1901                                       Label* label,
   1902                                       Instruction* label_veneer = NULL);
   1903 
   1904  private:
   1905   // Instruction helpers.
   1906   void MoveWide(const Register& rd,
   1907                 uint64_t imm,
   1908                 int shift,
   1909                 MoveWideImmediateOp mov_op);
   1910   void DataProcShiftedRegister(const Register& rd,
   1911                                const Register& rn,
   1912                                const Operand& operand,
   1913                                FlagsUpdate S,
   1914                                Instr op);
   1915   void DataProcExtendedRegister(const Register& rd,
   1916                                 const Register& rn,
   1917                                 const Operand& operand,
   1918                                 FlagsUpdate S,
   1919                                 Instr op);
   1920   void ConditionalSelect(const Register& rd,
   1921                          const Register& rn,
   1922                          const Register& rm,
   1923                          Condition cond,
   1924                          ConditionalSelectOp op);
   1925   void DataProcessing1Source(const Register& rd,
   1926                              const Register& rn,
   1927                              DataProcessing1SourceOp op);
   1928   void DataProcessing3Source(const Register& rd,
   1929                              const Register& rn,
   1930                              const Register& rm,
   1931                              const Register& ra,
   1932                              DataProcessing3SourceOp op);
   1933   void FPDataProcessing1Source(const FPRegister& fd,
   1934                                const FPRegister& fn,
   1935                                FPDataProcessing1SourceOp op);
   1936   void FPDataProcessing2Source(const FPRegister& fd,
   1937                                const FPRegister& fn,
   1938                                const FPRegister& fm,
   1939                                FPDataProcessing2SourceOp op);
   1940   void FPDataProcessing3Source(const FPRegister& fd,
   1941                                const FPRegister& fn,
   1942                                const FPRegister& fm,
   1943                                const FPRegister& fa,
   1944                                FPDataProcessing3SourceOp op);
   1945 
   1946   // Label helpers.
   1947 
   1948   // Return an offset for a label-referencing instruction, typically a branch.
   1949   int LinkAndGetByteOffsetTo(Label* label);
   1950 
   1951   // This is the same as LinkAndGetByteOffsetTo, but return an offset
   1952   // suitable for fields that take instruction offsets.
   1953   inline int LinkAndGetInstructionOffsetTo(Label* label);
   1954 
   1955   static const int kStartOfLabelLinkChain = 0;
   1956 
   1957   // Verify that a label's link chain is intact.
   1958   void CheckLabelLinkChain(Label const * label);
   1959 
   1960   void RecordLiteral(int64_t imm, unsigned size);
   1961 
   1962   // Postpone the generation of the constant pool for the specified number of
   1963   // instructions.
   1964   void BlockConstPoolFor(int instructions);
   1965 
   1966   // Set how far from current pc the next constant pool check will be.
   1967   void SetNextConstPoolCheckIn(int instructions) {
   1968     next_constant_pool_check_ = pc_offset() + instructions * kInstructionSize;
   1969   }
   1970 
   1971   // Emit the instruction at pc_.
   1972   void Emit(Instr instruction) {
   1973     STATIC_ASSERT(sizeof(*pc_) == 1);
   1974     STATIC_ASSERT(sizeof(instruction) == kInstructionSize);
   1975     DCHECK((pc_ + sizeof(instruction)) <= (buffer_ + buffer_size_));
   1976 
   1977     memcpy(pc_, &instruction, sizeof(instruction));
   1978     pc_ += sizeof(instruction);
   1979     CheckBuffer();
   1980   }
   1981 
   1982   // Emit data inline in the instruction stream.
   1983   void EmitData(void const * data, unsigned size) {
   1984     DCHECK(sizeof(*pc_) == 1);
   1985     DCHECK((pc_ + size) <= (buffer_ + buffer_size_));
   1986 
   1987     // TODO(all): Somehow register we have some data here. Then we can
   1988     // disassemble it correctly.
   1989     memcpy(pc_, data, size);
   1990     pc_ += size;
   1991     CheckBuffer();
   1992   }
   1993 
   1994   void GrowBuffer();
   1995   void CheckBufferSpace();
   1996   void CheckBuffer();
   1997 
   1998   // Pc offset of the next constant pool check.
   1999   int next_constant_pool_check_;
   2000 
   2001   // Constant pool generation
   2002   // Pools are emitted in the instruction stream. They are emitted when:
   2003   //  * the distance to the first use is above a pre-defined distance or
   2004   //  * the numbers of entries in the pool is above a pre-defined size or
   2005   //  * code generation is finished
   2006   // If a pool needs to be emitted before code generation is finished a branch
   2007   // over the emitted pool will be inserted.
   2008 
   2009   // Constants in the pool may be addresses of functions that gets relocated;
   2010   // if so, a relocation info entry is associated to the constant pool entry.
   2011 
   2012   // Repeated checking whether the constant pool should be emitted is rather
   2013   // expensive. By default we only check again once a number of instructions
   2014   // has been generated. That also means that the sizing of the buffers is not
   2015   // an exact science, and that we rely on some slop to not overrun buffers.
   2016   static const int kCheckConstPoolInterval = 128;
   2017 
   2018   // Distance to first use after a which a pool will be emitted. Pool entries
   2019   // are accessed with pc relative load therefore this cannot be more than
   2020   // 1 * MB. Since constant pool emission checks are interval based this value
   2021   // is an approximation.
   2022   static const int kApproxMaxDistToConstPool = 64 * KB;
   2023 
   2024   // Number of pool entries after which a pool will be emitted. Since constant
   2025   // pool emission checks are interval based this value is an approximation.
   2026   static const int kApproxMaxPoolEntryCount = 512;
   2027 
   2028   // Emission of the constant pool may be blocked in some code sequences.
   2029   int const_pool_blocked_nesting_;  // Block emission if this is not zero.
   2030   int no_const_pool_before_;  // Block emission before this pc offset.
   2031 
   2032   // Emission of the veneer pools may be blocked in some code sequences.
   2033   int veneer_pool_blocked_nesting_;  // Block emission if this is not zero.
   2034 
   2035   // Relocation info generation
   2036   // Each relocation is encoded as a variable size value
   2037   static const int kMaxRelocSize = RelocInfoWriter::kMaxSize;
   2038   RelocInfoWriter reloc_info_writer;
   2039   // Internal reference positions, required for (potential) patching in
   2040   // GrowBuffer(); contains only those internal references whose labels
   2041   // are already bound.
   2042   std::deque<int> internal_reference_positions_;
   2043 
   2044   // Relocation info records are also used during code generation as temporary
   2045   // containers for constants and code target addresses until they are emitted
   2046   // to the constant pool. These pending relocation info records are temporarily
   2047   // stored in a separate buffer until a constant pool is emitted.
   2048   // If every instruction in a long sequence is accessing the pool, we need one
   2049   // pending relocation entry per instruction.
   2050 
   2051   // The pending constant pool.
   2052   ConstPool constpool_;
   2053 
   2054   // Relocation for a type-recording IC has the AST id added to it.  This
   2055   // member variable is a way to pass the information from the call site to
   2056   // the relocation info.
   2057   TypeFeedbackId recorded_ast_id_;
   2058 
   2059   inline TypeFeedbackId RecordedAstId();
   2060   inline void ClearRecordedAstId();
   2061 
   2062  protected:
   2063   // Record the AST id of the CallIC being compiled, so that it can be placed
   2064   // in the relocation information.
   2065   void SetRecordedAstId(TypeFeedbackId ast_id) {
   2066     DCHECK(recorded_ast_id_.IsNone());
   2067     recorded_ast_id_ = ast_id;
   2068   }
   2069 
   2070   // Code generation
   2071   // The relocation writer's position is at least kGap bytes below the end of
   2072   // the generated instructions. This is so that multi-instruction sequences do
   2073   // not have to check for overflow. The same is true for writes of large
   2074   // relocation info entries, and debug strings encoded in the instruction
   2075   // stream.
   2076   static const int kGap = 128;
   2077 
   2078  public:
   2079   class FarBranchInfo {
   2080    public:
   2081     FarBranchInfo(int offset, Label* label)
   2082         : pc_offset_(offset), label_(label) {}
   2083     // Offset of the branch in the code generation buffer.
   2084     int pc_offset_;
   2085     // The label branched to.
   2086     Label* label_;
   2087   };
   2088 
   2089  protected:
   2090   // Information about unresolved (forward) branches.
   2091   // The Assembler is only allowed to delete out-of-date information from here
   2092   // after a label is bound. The MacroAssembler uses this information to
   2093   // generate veneers.
   2094   //
   2095   // The second member gives information about the unresolved branch. The first
   2096   // member of the pair is the maximum offset that the branch can reach in the
   2097   // buffer. The map is sorted according to this reachable offset, allowing to
   2098   // easily check when veneers need to be emitted.
   2099   // Note that the maximum reachable offset (first member of the pairs) should
   2100   // always be positive but has the same type as the return value for
   2101   // pc_offset() for convenience.
   2102   std::multimap<int, FarBranchInfo> unresolved_branches_;
   2103 
   2104   // We generate a veneer for a branch if we reach within this distance of the
   2105   // limit of the range.
   2106   static const int kVeneerDistanceMargin = 1 * KB;
   2107   // The factor of 2 is a finger in the air guess. With a default margin of
   2108   // 1KB, that leaves us an addional 256 instructions to avoid generating a
   2109   // protective branch.
   2110   static const int kVeneerNoProtectionFactor = 2;
   2111   static const int kVeneerDistanceCheckMargin =
   2112     kVeneerNoProtectionFactor * kVeneerDistanceMargin;
   2113   int unresolved_branches_first_limit() const {
   2114     DCHECK(!unresolved_branches_.empty());
   2115     return unresolved_branches_.begin()->first;
   2116   }
   2117   // This is similar to next_constant_pool_check_ and helps reduce the overhead
   2118   // of checking for veneer pools.
   2119   // It is maintained to the closest unresolved branch limit minus the maximum
   2120   // veneer margin (or kMaxInt if there are no unresolved branches).
   2121   int next_veneer_pool_check_;
   2122 
   2123  private:
   2124   // If a veneer is emitted for a branch instruction, that instruction must be
   2125   // removed from the associated label's link chain so that the assembler does
   2126   // not later attempt (likely unsuccessfully) to patch it to branch directly to
   2127   // the label.
   2128   void DeleteUnresolvedBranchInfoForLabel(Label* label);
   2129   // This function deletes the information related to the label by traversing
   2130   // the label chain, and for each PC-relative instruction in the chain checking
   2131   // if pending unresolved information exists. Its complexity is proportional to
   2132   // the length of the label chain.
   2133   void DeleteUnresolvedBranchInfoForLabelTraverse(Label* label);
   2134 
   2135  private:
   2136   PositionsRecorder positions_recorder_;
   2137   friend class PositionsRecorder;
   2138   friend class EnsureSpace;
   2139   friend class ConstPool;
   2140 };
   2141 
   2142 class PatchingAssembler : public Assembler {
   2143  public:
   2144   // Create an Assembler with a buffer starting at 'start'.
   2145   // The buffer size is
   2146   //   size of instructions to patch + kGap
   2147   // Where kGap is the distance from which the Assembler tries to grow the
   2148   // buffer.
   2149   // If more or fewer instructions than expected are generated or if some
   2150   // relocation information takes space in the buffer, the PatchingAssembler
   2151   // will crash trying to grow the buffer.
   2152   PatchingAssembler(Isolate* isolate, Instruction* start, unsigned count)
   2153       : Assembler(isolate, reinterpret_cast<byte*>(start),
   2154                   count * kInstructionSize + kGap) {
   2155     StartBlockPools();
   2156   }
   2157 
   2158   PatchingAssembler(Isolate* isolate, byte* start, unsigned count)
   2159       : Assembler(isolate, start, count * kInstructionSize + kGap) {
   2160     // Block constant pool emission.
   2161     StartBlockPools();
   2162   }
   2163 
   2164   ~PatchingAssembler() {
   2165     // Const pool should still be blocked.
   2166     DCHECK(is_const_pool_blocked());
   2167     EndBlockPools();
   2168     // Verify we have generated the number of instruction we expected.
   2169     DCHECK((pc_offset() + kGap) == buffer_size_);
   2170     // Verify no relocation information has been emitted.
   2171     DCHECK(IsConstPoolEmpty());
   2172     // Flush the Instruction cache.
   2173     size_t length = buffer_size_ - kGap;
   2174     Assembler::FlushICache(isolate(), buffer_, length);
   2175   }
   2176 
   2177   // See definition of PatchAdrFar() for details.
   2178   static const int kAdrFarPatchableNNops = 2;
   2179   static const int kAdrFarPatchableNInstrs = kAdrFarPatchableNNops + 2;
   2180   void PatchAdrFar(int64_t target_offset);
   2181 };
   2182 
   2183 
   2184 class EnsureSpace BASE_EMBEDDED {
   2185  public:
   2186   explicit EnsureSpace(Assembler* assembler) {
   2187     assembler->CheckBufferSpace();
   2188   }
   2189 };
   2190 
   2191 }  // namespace internal
   2192 }  // namespace v8
   2193 
   2194 #endif  // V8_ARM64_ASSEMBLER_ARM64_H_
   2195