Bug 1188650 - Part 1/2 - Rename LIR-Common.h to shared/LIR-shared.h. r=nbp
authorSean Stangl <sstangl@mozilla.com>
Tue, 28 Jul 2015 15:25:07 -0700
changeset 287877 ada67c4f187d1b2bb8b7850ea8342f32030fb6d9
parent 287876 f763ac7bd0bdb6f643c64c2ddb9275023719f59a
child 287878 7b2a1ef36fcb715267e20baee84f7b26fc51bad8
push id5067
push userraliiev@mozilla.com
push dateMon, 21 Sep 2015 14:04:52 +0000
treeherdermozilla-beta@14221ffe5b2f [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersnbp
bugs1188650
milestone42.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1188650 - Part 1/2 - Rename LIR-Common.h to shared/LIR-shared.h. r=nbp
js/src/jit/LIR-Common.h
js/src/jit/LIR.h
js/src/jit/shared/LIR-shared.h
deleted file mode 100644
--- a/js/src/jit/LIR-Common.h
+++ /dev/null
@@ -1,7124 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
- * vim: set ts=8 sts=4 et sw=4 tw=99:
- * This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
-
-#ifndef jit_LIR_Common_h
-#define jit_LIR_Common_h
-
-#include "jsutil.h"
-
-#include "jit/AtomicOp.h"
-#include "jit/shared/Assembler-shared.h"
-
-// This file declares LIR instructions that are common to every platform.
-
-namespace js {
-namespace jit {
-
-class Range;
-
-template <size_t Temps, size_t ExtraUses = 0>
-class LBinaryMath : public LInstructionHelper<1, 2 + ExtraUses, Temps>
-{
-  public:
-    const LAllocation* lhs() {
-        return this->getOperand(0);
-    }
-    const LAllocation* rhs() {
-        return this->getOperand(1);
-    }
-};
-
-// An LOsiPoint captures a snapshot after a call and ensures enough space to
-// patch in a call to the invalidation mechanism.
-//
-// Note: LSafepoints are 1:1 with LOsiPoints, so it holds a reference to the
-// corresponding LSafepoint to inform it of the LOsiPoint's masm offset when it
-// gets CG'd.
-class LOsiPoint : public LInstructionHelper<0, 0, 0>
-{
-    LSafepoint* safepoint_;
-
-  public:
-    LOsiPoint(LSafepoint* safepoint, LSnapshot* snapshot)
-      : safepoint_(safepoint)
-    {
-        MOZ_ASSERT(safepoint && snapshot);
-        assignSnapshot(snapshot);
-    }
-
-    LSafepoint* associatedSafepoint() {
-        return safepoint_;
-    }
-
-    LIR_HEADER(OsiPoint)
-};
-
-class LMove
-{
-    LAllocation from_;
-    LAllocation to_;
-    LDefinition::Type type_;
-
-  public:
-    LMove(LAllocation from, LAllocation to, LDefinition::Type type)
-      : from_(from),
-        to_(to),
-        type_(type)
-    { }
-
-    LAllocation from() const {
-        return from_;
-    }
-    LAllocation to() const {
-        return to_;
-    }
-    LDefinition::Type type() const {
-        return type_;
-    }
-};
-
-class LMoveGroup : public LInstructionHelper<0, 0, 0>
-{
-    js::Vector<LMove, 2, JitAllocPolicy> moves_;
-
-#ifdef JS_CODEGEN_X86
-    // Optional general register available for use when executing moves.
-    LAllocation scratchRegister_;
-#endif
-
-    explicit LMoveGroup(TempAllocator& alloc)
-      : moves_(alloc)
-    { }
-
-  public:
-    LIR_HEADER(MoveGroup)
-
-    static LMoveGroup* New(TempAllocator& alloc) {
-        return new(alloc) LMoveGroup(alloc);
-    }
-
-    void printOperands(GenericPrinter& out);
-
-    // Add a move which takes place simultaneously with all others in the group.
-    bool add(LAllocation from, LAllocation to, LDefinition::Type type);
-
-    // Add a move which takes place after existing moves in the group.
-    bool addAfter(LAllocation from, LAllocation to, LDefinition::Type type);
-
-    size_t numMoves() const {
-        return moves_.length();
-    }
-    const LMove& getMove(size_t i) const {
-        return moves_[i];
-    }
-
-#ifdef JS_CODEGEN_X86
-    void setScratchRegister(Register reg) {
-        scratchRegister_ = LGeneralReg(reg);
-    }
-    LAllocation maybeScratchRegister() {
-        return scratchRegister_;
-    }
-#endif
-
-    bool uses(Register reg) {
-        for (size_t i = 0; i < numMoves(); i++) {
-            LMove move = getMove(i);
-            if (move.from() == LGeneralReg(reg) || move.to() == LGeneralReg(reg))
-                return true;
-        }
-        return false;
-    }
-};
-
-
-// Constructs a SIMD object (value type) based on the MIRType of its input.
-class LSimdBox : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(SimdBox)
-
-    explicit LSimdBox(const LAllocation& simd, const LDefinition& temp)
-    {
-        setOperand(0, simd);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MSimdBox* mir() const {
-        return mir_->toSimdBox();
-    }
-};
-
-class LSimdUnbox : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(SimdUnbox)
-
-    LSimdUnbox(const LAllocation& obj, const LDefinition& temp)
-    {
-        setOperand(0, obj);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MSimdUnbox* mir() const {
-        return mir_->toSimdUnbox();
-    }
-};
-
-// Constructs a SIMD value with 4 equal components (e.g. int32x4, float32x4).
-class LSimdSplatX4 : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(SimdSplatX4)
-    explicit LSimdSplatX4(const LAllocation& v)
-    {
-        setOperand(0, v);
-    }
-
-    MSimdSplatX4* mir() const {
-        return mir_->toSimdSplatX4();
-    }
-};
-
-// Reinterpret the bits of a SIMD value with a different type.
-class LSimdReinterpretCast : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(SimdReinterpretCast)
-    explicit LSimdReinterpretCast(const LAllocation& v)
-    {
-        setOperand(0, v);
-    }
-
-    MSimdReinterpretCast* mir() const {
-        return mir_->toSimdReinterpretCast();
-    }
-};
-
-class LSimdExtractElementBase : public LInstructionHelper<1, 1, 0>
-{
-  protected:
-    explicit LSimdExtractElementBase(const LAllocation& base) {
-        setOperand(0, base);
-    }
-
-  public:
-    const LAllocation* getBase() {
-        return getOperand(0);
-    }
-    SimdLane lane() const {
-        return mir_->toSimdExtractElement()->lane();
-    }
-    const char* extraName() const {
-        switch (lane()) {
-          case LaneX: return "lane x";
-          case LaneY: return "lane y";
-          case LaneZ: return "lane z";
-          case LaneW: return "lane w";
-        }
-        return "unknown lane";
-    }
-};
-
-// Extracts an element from a given SIMD int32x4 lane.
-class LSimdExtractElementI : public LSimdExtractElementBase
-{
-  public:
-    LIR_HEADER(SimdExtractElementI);
-    explicit LSimdExtractElementI(const LAllocation& base)
-      : LSimdExtractElementBase(base)
-    {}
-};
-// Extracts an element from a given SIMD float32x4 lane.
-class LSimdExtractElementF : public LSimdExtractElementBase
-{
-  public:
-    LIR_HEADER(SimdExtractElementF);
-    explicit LSimdExtractElementF(const LAllocation& base)
-      : LSimdExtractElementBase(base)
-    {}
-};
-
-class LSimdInsertElementBase : public LInstructionHelper<1, 2, 0>
-{
-  protected:
-    LSimdInsertElementBase(const LAllocation& vec, const LAllocation& val)
-    {
-        setOperand(0, vec);
-        setOperand(1, val);
-    }
-
-  public:
-    const LAllocation* vector() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-    SimdLane lane() const {
-        return mir_->toSimdInsertElement()->lane();
-    }
-    const char* extraName() const {
-        return MSimdInsertElement::LaneName(lane());
-    }
-};
-
-// Replace an element from a given SIMD int32x4 lane with a given value.
-class LSimdInsertElementI : public LSimdInsertElementBase
-{
-  public:
-    LIR_HEADER(SimdInsertElementI);
-    LSimdInsertElementI(const LAllocation& vec, const LAllocation& val)
-      : LSimdInsertElementBase(vec, val)
-    {}
-};
-
-// Replace an element from a given SIMD float32x4 lane with a given value.
-class LSimdInsertElementF : public LSimdInsertElementBase
-{
-  public:
-    LIR_HEADER(SimdInsertElementF);
-    LSimdInsertElementF(const LAllocation& vec, const LAllocation& val)
-      : LSimdInsertElementBase(vec, val)
-    {}
-};
-
-class LSimdSignMaskX4 : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(SimdSignMaskX4);
-
-    explicit LSimdSignMaskX4(const LAllocation& input) {
-        setOperand(0, input);
-    }
-};
-
-// Base class for both int32x4 and float32x4 shuffle instructions.
-class LSimdSwizzleBase : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    explicit LSimdSwizzleBase(const LAllocation& base)
-    {
-        setOperand(0, base);
-    }
-
-    const LAllocation* getBase() {
-        return getOperand(0);
-    }
-
-    uint32_t laneX() const { return mir_->toSimdSwizzle()->laneX(); }
-    uint32_t laneY() const { return mir_->toSimdSwizzle()->laneY(); }
-    uint32_t laneZ() const { return mir_->toSimdSwizzle()->laneZ(); }
-    uint32_t laneW() const { return mir_->toSimdSwizzle()->laneW(); }
-
-    bool lanesMatch(uint32_t x, uint32_t y, uint32_t z, uint32_t w) const {
-        return mir_->toSimdSwizzle()->lanesMatch(x, y, z, w);
-    }
-};
-
-// Shuffles a int32x4 into another int32x4 vector.
-class LSimdSwizzleI : public LSimdSwizzleBase
-{
-  public:
-    LIR_HEADER(SimdSwizzleI);
-    explicit LSimdSwizzleI(const LAllocation& base) : LSimdSwizzleBase(base)
-    {}
-};
-// Shuffles a float32x4 into another float32x4 vector.
-class LSimdSwizzleF : public LSimdSwizzleBase
-{
-  public:
-    LIR_HEADER(SimdSwizzleF);
-    explicit LSimdSwizzleF(const LAllocation& base) : LSimdSwizzleBase(base)
-    {}
-};
-
-class LSimdGeneralShuffleBase : public LVariadicInstruction<1, 1>
-{
-  public:
-    explicit LSimdGeneralShuffleBase(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-    const LAllocation* vector(unsigned i) {
-        MOZ_ASSERT(i < mir()->numVectors());
-        return getOperand(i);
-    }
-    const LAllocation* lane(unsigned i) {
-        MOZ_ASSERT(i < mir()->numLanes());
-        return getOperand(mir()->numVectors() + i);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    MSimdGeneralShuffle* mir() const {
-        return mir_->toSimdGeneralShuffle();
-    }
-};
-
-class LSimdGeneralShuffleI : public LSimdGeneralShuffleBase
-{
-  public:
-    LIR_HEADER(SimdGeneralShuffleI);
-    explicit LSimdGeneralShuffleI(const LDefinition& temp)
-      : LSimdGeneralShuffleBase(temp)
-    {}
-};
-
-class LSimdGeneralShuffleF : public LSimdGeneralShuffleBase
-{
-  public:
-    LIR_HEADER(SimdGeneralShuffleF);
-    explicit LSimdGeneralShuffleF(const LDefinition& temp)
-      : LSimdGeneralShuffleBase(temp)
-    {}
-};
-
-// Base class for both int32x4 and float32x4 shuffle instructions.
-class LSimdShuffle : public LInstructionHelper<1, 2, 1>
-{
-  public:
-    LIR_HEADER(SimdShuffle);
-    LSimdShuffle()
-    {}
-
-    const LAllocation* lhs() {
-        return getOperand(0);
-    }
-    const LAllocation* rhs() {
-        return getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    uint32_t laneX() const { return mir_->toSimdShuffle()->laneX(); }
-    uint32_t laneY() const { return mir_->toSimdShuffle()->laneY(); }
-    uint32_t laneZ() const { return mir_->toSimdShuffle()->laneZ(); }
-    uint32_t laneW() const { return mir_->toSimdShuffle()->laneW(); }
-
-    bool lanesMatch(uint32_t x, uint32_t y, uint32_t z, uint32_t w) const {
-        return mir_->toSimdShuffle()->lanesMatch(x, y, z, w);
-    }
-};
-
-// Binary SIMD comparison operation between two SIMD operands
-class LSimdBinaryComp: public LInstructionHelper<1, 2, 0>
-{
-  protected:
-    LSimdBinaryComp() {}
-
-public:
-    const LAllocation* lhs() {
-        return getOperand(0);
-    }
-    const LAllocation* rhs() {
-        return getOperand(1);
-    }
-    MSimdBinaryComp::Operation operation() const {
-        return mir_->toSimdBinaryComp()->operation();
-    }
-    const char* extraName() const {
-        return MSimdBinaryComp::OperationName(operation());
-    }
-};
-
-// Binary SIMD comparison operation between two Int32x4 operands
-class LSimdBinaryCompIx4 : public LSimdBinaryComp
-{
-  public:
-    LIR_HEADER(SimdBinaryCompIx4);
-    LSimdBinaryCompIx4() : LSimdBinaryComp() {}
-};
-
-// Binary SIMD comparison operation between two Float32x4 operands
-class LSimdBinaryCompFx4 : public LSimdBinaryComp
-{
-  public:
-    LIR_HEADER(SimdBinaryCompFx4);
-    LSimdBinaryCompFx4() : LSimdBinaryComp() {}
-};
-
-// Binary SIMD arithmetic operation between two SIMD operands
-class LSimdBinaryArith : public LInstructionHelper<1, 2, 1>
-{
-  public:
-    LSimdBinaryArith() {}
-
-    const LAllocation* lhs() {
-        return this->getOperand(0);
-    }
-    const LAllocation* rhs() {
-        return this->getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MSimdBinaryArith::Operation operation() const {
-        return this->mir_->toSimdBinaryArith()->operation();
-    }
-    const char* extraName() const {
-        return MSimdBinaryArith::OperationName(operation());
-    }
-};
-
-// Binary SIMD arithmetic operation between two Int32x4 operands
-class LSimdBinaryArithIx4 : public LSimdBinaryArith
-{
-  public:
-    LIR_HEADER(SimdBinaryArithIx4);
-    LSimdBinaryArithIx4() : LSimdBinaryArith() {}
-};
-
-// Binary SIMD arithmetic operation between two Float32x4 operands
-class LSimdBinaryArithFx4 : public LSimdBinaryArith
-{
-  public:
-    LIR_HEADER(SimdBinaryArithFx4);
-    LSimdBinaryArithFx4() : LSimdBinaryArith() {}
-};
-
-// Unary SIMD arithmetic operation on a SIMD operand
-class LSimdUnaryArith : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    explicit LSimdUnaryArith(const LAllocation& in) {
-        setOperand(0, in);
-    }
-    MSimdUnaryArith::Operation operation() const {
-        return mir_->toSimdUnaryArith()->operation();
-    }
-};
-
-// Unary SIMD arithmetic operation on a Int32x4 operand
-class LSimdUnaryArithIx4 : public LSimdUnaryArith
-{
-  public:
-    LIR_HEADER(SimdUnaryArithIx4);
-    explicit LSimdUnaryArithIx4(const LAllocation& in) : LSimdUnaryArith(in) {}
-};
-
-// Unary SIMD arithmetic operation on a Float32x4 operand
-class LSimdUnaryArithFx4 : public LSimdUnaryArith
-{
-  public:
-    LIR_HEADER(SimdUnaryArithFx4);
-    explicit LSimdUnaryArithFx4(const LAllocation& in) : LSimdUnaryArith(in) {}
-};
-
-// Binary SIMD bitwise operation between two int32x4 or float32x4 operands
-class LSimdBinaryBitwiseX4 : public LInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(SimdBinaryBitwiseX4);
-    const LAllocation* lhs() {
-        return getOperand(0);
-    }
-    const LAllocation* rhs() {
-        return getOperand(1);
-    }
-    MSimdBinaryBitwise::Operation operation() const {
-        return mir_->toSimdBinaryBitwise()->operation();
-    }
-    const char* extraName() const {
-        return MSimdBinaryBitwise::OperationName(operation());
-    }
-    MIRType type() const {
-        return mir_->type();
-    }
-};
-
-class LSimdShift : public LInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(SimdShift)
-    LSimdShift(const LAllocation& vec, const LAllocation& val) {
-        setOperand(0, vec);
-        setOperand(1, val);
-    }
-    const LAllocation* vector() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-    MSimdShift::Operation operation() const {
-        return mir_->toSimdShift()->operation();
-    }
-    const char* extraName() const {
-        return MSimdShift::OperationName(operation());
-    }
-    MSimdShift* mir() const {
-        return mir_->toSimdShift();
-    }
-};
-
-// SIMD selection of lanes from two int32x4 or float32x4 arguments based on a
-// int32x4 argument.
-class LSimdSelect : public LInstructionHelper<1, 3, 1>
-{
-  public:
-    LIR_HEADER(SimdSelect);
-    const LAllocation* mask() {
-        return getOperand(0);
-    }
-    const LAllocation* lhs() {
-        return getOperand(1);
-    }
-    const LAllocation* rhs() {
-        return getOperand(2);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    MSimdSelect* mir() const {
-        return mir_->toSimdSelect();
-    }
-};
-
-// Constant 32-bit integer.
-class LInteger : public LInstructionHelper<1, 0, 0>
-{
-    int32_t i32_;
-
-  public:
-    LIR_HEADER(Integer)
-
-    explicit LInteger(int32_t i32)
-      : i32_(i32)
-    { }
-
-    int32_t getValue() const {
-        return i32_;
-    }
-};
-
-// Constant pointer.
-class LPointer : public LInstructionHelper<1, 0, 0>
-{
-  public:
-    enum Kind {
-        GC_THING,
-        NON_GC_THING
-    };
-
-  private:
-    void* ptr_;
-    Kind kind_;
-
-  public:
-    LIR_HEADER(Pointer)
-
-    explicit LPointer(gc::Cell* ptr)
-      : ptr_(ptr), kind_(GC_THING)
-    { }
-
-    LPointer(void* ptr, Kind kind)
-      : ptr_(ptr), kind_(kind)
-    { }
-
-    void* ptr() const {
-        return ptr_;
-    }
-    Kind kind() const {
-        return kind_;
-    }
-    const char* extraName() const {
-        return kind_ == GC_THING ? "GC_THING" : "NON_GC_THING";
-    }
-
-    gc::Cell* gcptr() const {
-        MOZ_ASSERT(kind() == GC_THING);
-        return (gc::Cell*) ptr_;
-    }
-};
-
-// Constant double.
-class LDouble : public LInstructionHelper<1, 0, 0>
-{
-    double d_;
-  public:
-    LIR_HEADER(Double);
-
-    explicit LDouble(double d) : d_(d)
-    { }
-    double getDouble() const {
-        return d_;
-    }
-};
-
-// Constant float32.
-class LFloat32 : public LInstructionHelper<1, 0, 0>
-{
-    float f_;
-  public:
-    LIR_HEADER(Float32);
-
-    explicit LFloat32(float f)
-      : f_(f)
-    { }
-
-    float getFloat() const {
-        return f_;
-    }
-};
-
-// Constant SIMD int32x4
-class LInt32x4 : public LInstructionHelper<1, 0, 0>
-{
-  public:
-    LIR_HEADER(Int32x4);
-
-    explicit LInt32x4() {}
-    const SimdConstant& getValue() const { return mir_->toSimdConstant()->value(); }
-};
-
-// Constant SIMD float32x4
-class LFloat32x4 : public LInstructionHelper<1, 0, 0>
-{
-  public:
-    LIR_HEADER(Float32x4);
-
-    explicit LFloat32x4() {}
-    const SimdConstant& getValue() const { return mir_->toSimdConstant()->value(); }
-};
-
-// A constant Value.
-class LValue : public LInstructionHelper<BOX_PIECES, 0, 0>
-{
-    Value v_;
-
-  public:
-    LIR_HEADER(Value)
-
-    explicit LValue(const Value& v)
-      : v_(v)
-    { }
-
-    Value value() const {
-        return v_;
-    }
-};
-
-// Clone an object literal such as we are not modifying the object contained in
-// the sources.
-class LCloneLiteral : public LCallInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(CloneLiteral)
-
-    explicit LCloneLiteral(const LAllocation& obj)
-    {
-        setOperand(0, obj);
-    }
-
-    const LAllocation* getObjectLiteral() {
-        return getOperand(0);
-    }
-
-    MCloneLiteral* mir() const {
-        return mir_->toCloneLiteral();
-    }
-};
-
-// Formal argument for a function, returning a box. Formal arguments are
-// initially read from the stack.
-class LParameter : public LInstructionHelper<BOX_PIECES, 0, 0>
-{
-  public:
-    LIR_HEADER(Parameter)
-};
-
-// Stack offset for a word-sized immutable input value to a frame.
-class LCallee : public LInstructionHelper<1, 0, 0>
-{
-  public:
-    LIR_HEADER(Callee)
-};
-
-class LIsConstructing : public LInstructionHelper<1, 0, 0>
-{
-  public:
-    LIR_HEADER(IsConstructing)
-};
-
-// Base class for control instructions (goto, branch, etc.)
-template <size_t Succs, size_t Operands, size_t Temps>
-class LControlInstructionHelper : public LInstructionHelper<0, Operands, Temps> {
-
-    mozilla::Array<MBasicBlock*, Succs> successors_;
-
-  public:
-    virtual size_t numSuccessors() const final override { return Succs; }
-
-    virtual MBasicBlock* getSuccessor(size_t i) const final override {
-        return successors_[i];
-    }
-
-    virtual void setSuccessor(size_t i, MBasicBlock* successor) final override {
-        successors_[i] = successor;
-    }
-};
-
-// Jumps to the start of a basic block.
-class LGoto : public LControlInstructionHelper<1, 0, 0>
-{
-  public:
-    LIR_HEADER(Goto)
-
-    explicit LGoto(MBasicBlock* block)
-    {
-         setSuccessor(0, block);
-    }
-
-    MBasicBlock* target() const {
-        return getSuccessor(0);
-    }
-};
-
-class LNewArray : public LInstructionHelper<1, 0, 1>
-{
-  public:
-    LIR_HEADER(NewArray)
-
-    explicit LNewArray(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-
-    const char* extraName() const {
-        return mir()->shouldUseVM() ? "VMCall" : nullptr;
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MNewArray* mir() const {
-        return mir_->toNewArray();
-    }
-};
-
-class LNewArrayCopyOnWrite : public LInstructionHelper<1, 0, 1>
-{
-  public:
-    LIR_HEADER(NewArrayCopyOnWrite)
-
-    explicit LNewArrayCopyOnWrite(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MNewArrayCopyOnWrite* mir() const {
-        return mir_->toNewArrayCopyOnWrite();
-    }
-};
-
-class LNewArrayDynamicLength : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(NewArrayDynamicLength)
-
-    explicit LNewArrayDynamicLength(const LAllocation& length, const LDefinition& temp) {
-        setOperand(0, length);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* length() {
-        return getOperand(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MNewArrayDynamicLength* mir() const {
-        return mir_->toNewArrayDynamicLength();
-    }
-};
-
-class LNewObject : public LInstructionHelper<1, 0, 1>
-{
-  public:
-    LIR_HEADER(NewObject)
-
-    explicit LNewObject(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-
-    const char* extraName() const {
-        return mir()->shouldUseVM() ? "VMCall" : nullptr;
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MNewObject* mir() const {
-        return mir_->toNewObject();
-    }
-};
-
-class LNewTypedObject : public LInstructionHelper<1, 0, 1>
-{
-  public:
-    LIR_HEADER(NewTypedObject)
-
-    explicit LNewTypedObject(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MNewTypedObject* mir() const {
-        return mir_->toNewTypedObject();
-    }
-};
-
-// Allocates a new DeclEnvObject.
-//
-// This instruction generates two possible instruction sets:
-//   (1) An inline allocation of the call object is attempted.
-//   (2) Otherwise, a callVM create a new object.
-//
-class LNewDeclEnvObject : public LInstructionHelper<1, 0, 1>
-{
-  public:
-    LIR_HEADER(NewDeclEnvObject);
-
-    explicit LNewDeclEnvObject(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MNewDeclEnvObject* mir() const {
-        return mir_->toNewDeclEnvObject();
-    }
-};
-
-// Allocates a new CallObject.
-//
-// This instruction generates two possible instruction sets:
-//   (1) If the call object is extensible, this is a callVM to create the
-//       call object.
-//   (2) Otherwise, an inline allocation of the call object is attempted.
-//
-class LNewCallObject : public LInstructionHelper<1, 0, 1>
-{
-  public:
-    LIR_HEADER(NewCallObject)
-
-    explicit LNewCallObject(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-
-    MNewCallObject* mir() const {
-        return mir_->toNewCallObject();
-    }
-};
-
-// Allocates a new CallObject with singleton type.
-//
-// This instruction generates two possible instruction sets:
-//   (1) If the call object is extensible, this is a callVM to create the
-//       call object.
-//   (2) Otherwise, an inline allocation of the call object is attempted.
-//
-class LNewSingletonCallObject : public LInstructionHelper<1, 0, 1>
-{
-  public:
-    LIR_HEADER(NewSingletonCallObject)
-
-    explicit LNewSingletonCallObject(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MNewCallObjectBase* mir() const {
-        MOZ_ASSERT(mir_->isNewCallObject() || mir_->isNewRunOnceCallObject());
-        return static_cast<MNewCallObjectBase*>(mir_);
-    }
-};
-
-class LNewDerivedTypedObject : public LCallInstructionHelper<1, 3, 0>
-{
-  public:
-    LIR_HEADER(NewDerivedTypedObject);
-
-    LNewDerivedTypedObject(const LAllocation& type,
-                           const LAllocation& owner,
-                           const LAllocation& offset) {
-        setOperand(0, type);
-        setOperand(1, owner);
-        setOperand(2, offset);
-    }
-
-    const LAllocation* type() {
-        return getOperand(0);
-    }
-
-    const LAllocation* owner() {
-        return getOperand(1);
-    }
-
-    const LAllocation* offset() {
-        return getOperand(2);
-    }
-};
-
-class LNewStringObject : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(NewStringObject)
-
-    LNewStringObject(const LAllocation& input, const LDefinition& temp) {
-        setOperand(0, input);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* input() {
-        return getOperand(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    MNewStringObject* mir() const {
-        return mir_->toNewStringObject();
-    }
-};
-
-class LInitElem : public LCallInstructionHelper<0, 1 + 2*BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(InitElem)
-
-    explicit LInitElem(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    static const size_t IdIndex = 1;
-    static const size_t ValueIndex = 1 + BOX_PIECES;
-
-    const LAllocation* getObject() {
-        return getOperand(0);
-    }
-    MInitElem* mir() const {
-        return mir_->toInitElem();
-    }
-};
-
-class LInitElemGetterSetter : public LCallInstructionHelper<0, 2 + BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(InitElemGetterSetter)
-
-    LInitElemGetterSetter(const LAllocation& object, const LAllocation& value) {
-        setOperand(0, object);
-        setOperand(1, value);
-    }
-
-    static const size_t IdIndex = 2;
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-    MInitElemGetterSetter* mir() const {
-        return mir_->toInitElemGetterSetter();
-    }
-};
-
-// Takes in an Object and a Value.
-class LMutateProto : public LCallInstructionHelper<0, 1 + BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(MutateProto)
-
-    explicit LMutateProto(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    static const size_t ValueIndex = 1;
-
-    const LAllocation* getObject() {
-        return getOperand(0);
-    }
-    const LAllocation* getValue() {
-        return getOperand(1);
-    }
-};
-
-// Takes in an Object and a Value.
-class LInitProp : public LCallInstructionHelper<0, 1 + BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(InitProp)
-
-    explicit LInitProp(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    static const size_t ValueIndex = 1;
-
-    const LAllocation* getObject() {
-        return getOperand(0);
-    }
-    const LAllocation* getValue() {
-        return getOperand(1);
-    }
-
-    MInitProp* mir() const {
-        return mir_->toInitProp();
-    }
-};
-
-class LInitPropGetterSetter : public LCallInstructionHelper<0, 2, 0>
-{
-  public:
-    LIR_HEADER(InitPropGetterSetter)
-
-    LInitPropGetterSetter(const LAllocation& object, const LAllocation& value) {
-        setOperand(0, object);
-        setOperand(1, value);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-
-    MInitPropGetterSetter* mir() const {
-        return mir_->toInitPropGetterSetter();
-    }
-};
-
-class LCheckOverRecursed : public LInstructionHelper<0, 0, 0>
-{
-  public:
-    LIR_HEADER(CheckOverRecursed)
-
-    LCheckOverRecursed()
-    { }
-
-    MCheckOverRecursed* mir() const {
-        return mir_->toCheckOverRecursed();
-    }
-};
-
-class LAsmJSInterruptCheck : public LInstructionHelper<0, 0, 0>
-{
-    Label* interruptExit_;
-    const CallSiteDesc& funcDesc_;
-
-  public:
-    LIR_HEADER(AsmJSInterruptCheck);
-
-    LAsmJSInterruptCheck(Label* interruptExit, const CallSiteDesc& funcDesc)
-      : interruptExit_(interruptExit), funcDesc_(funcDesc)
-    {
-    }
-
-    bool isCall() const {
-        return true;
-    }
-
-    Label* interruptExit() const {
-        return interruptExit_;
-    }
-    const CallSiteDesc& funcDesc() const {
-        return funcDesc_;
-    }
-};
-
-class LInterruptCheck : public LInstructionHelper<0, 0, 0>
-{
-  public:
-    LIR_HEADER(InterruptCheck)
-};
-
-// Alternative to LInterruptCheck which does not emit an explicit check of the
-// interrupt flag but relies on the loop backedge being patched via a signal
-// handler.
-class LInterruptCheckImplicit : public LInstructionHelper<0, 0, 0>
-{
-    Label* oolEntry_;
-
-  public:
-    LIR_HEADER(InterruptCheckImplicit)
-
-    LInterruptCheckImplicit()
-      : oolEntry_(nullptr)
-    {}
-
-    Label* oolEntry() {
-        return oolEntry_;
-    }
-
-    void setOolEntry(Label* oolEntry) {
-        oolEntry_ = oolEntry;
-    }
-    MInterruptCheck* mir() const {
-        return mir_->toInterruptCheck();
-    }
-};
-
-class LDefVar : public LCallInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(DefVar)
-
-    explicit LDefVar(const LAllocation& scopeChain)
-    {
-        setOperand(0, scopeChain);
-    }
-
-    const LAllocation* scopeChain() {
-        return getOperand(0);
-    }
-    MDefVar* mir() const {
-        return mir_->toDefVar();
-    }
-};
-
-class LDefFun : public LCallInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(DefFun)
-
-    explicit LDefFun(const LAllocation& scopeChain)
-    {
-        setOperand(0, scopeChain);
-    }
-
-    const LAllocation* scopeChain() {
-        return getOperand(0);
-    }
-    MDefFun* mir() const {
-        return mir_->toDefFun();
-    }
-};
-
-class LTypeOfV : public LInstructionHelper<1, BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(TypeOfV)
-
-    explicit LTypeOfV(const LDefinition& tempToUnbox) {
-        setTemp(0, tempToUnbox);
-    }
-
-    static const size_t Input = 0;
-
-    const LDefinition* tempToUnbox() {
-        return getTemp(0);
-    }
-
-    MTypeOf* mir() const {
-        return mir_->toTypeOf();
-    }
-};
-
-class LToIdV : public LInstructionHelper<BOX_PIECES, 2 * BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(ToIdV)
-
-    explicit LToIdV(const LDefinition& temp)
-    {
-        setTemp(0, temp);
-    }
-
-    static const size_t Object = 0;
-    static const size_t Index = BOX_PIECES;
-
-    MToId* mir() const {
-        return mir_->toToId();
-    }
-
-    const LDefinition* tempFloat() {
-        return getTemp(0);
-    }
-};
-
-// Allocate an object for |new| on the caller-side,
-// when there is no templateObject or prototype known
-class LCreateThis : public LCallInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    LIR_HEADER(CreateThis)
-
-    explicit LCreateThis(const LAllocation& callee)
-    {
-        setOperand(0, callee);
-    }
-
-    const LAllocation* getCallee() {
-        return getOperand(0);
-    }
-
-    MCreateThis* mir() const {
-        return mir_->toCreateThis();
-    }
-};
-
-// Allocate an object for |new| on the caller-side,
-// when the prototype is known.
-class LCreateThisWithProto : public LCallInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(CreateThisWithProto)
-
-    LCreateThisWithProto(const LAllocation& callee, const LAllocation& prototype)
-    {
-        setOperand(0, callee);
-        setOperand(1, prototype);
-    }
-
-    const LAllocation* getCallee() {
-        return getOperand(0);
-    }
-    const LAllocation* getPrototype() {
-        return getOperand(1);
-    }
-
-    MCreateThis* mir() const {
-        return mir_->toCreateThis();
-    }
-};
-
-// Allocate an object for |new| on the caller-side.
-// Always performs object initialization with a fast path.
-class LCreateThisWithTemplate : public LInstructionHelper<1, 0, 1>
-{
-  public:
-    LIR_HEADER(CreateThisWithTemplate)
-
-    explicit LCreateThisWithTemplate(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-
-    MCreateThisWithTemplate* mir() const {
-        return mir_->toCreateThisWithTemplate();
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Allocate a new arguments object for the frame.
-class LCreateArgumentsObject : public LCallInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(CreateArgumentsObject)
-
-    LCreateArgumentsObject(const LAllocation& callObj, const LDefinition& temp)
-    {
-        setOperand(0, callObj);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* getCallObject() {
-        return getOperand(0);
-    }
-
-    MCreateArgumentsObject* mir() const {
-        return mir_->toCreateArgumentsObject();
-    }
-};
-
-// Get argument from arguments object.
-class LGetArgumentsObjectArg : public LInstructionHelper<BOX_PIECES, 1, 1>
-{
-  public:
-    LIR_HEADER(GetArgumentsObjectArg)
-
-    LGetArgumentsObjectArg(const LAllocation& argsObj, const LDefinition& temp)
-    {
-        setOperand(0, argsObj);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* getArgsObject() {
-        return getOperand(0);
-    }
-
-    MGetArgumentsObjectArg* mir() const {
-        return mir_->toGetArgumentsObjectArg();
-    }
-};
-
-// Set argument on arguments object.
-class LSetArgumentsObjectArg : public LInstructionHelper<0, 1 + BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(SetArgumentsObjectArg)
-
-    LSetArgumentsObjectArg(const LAllocation& argsObj, const LDefinition& temp)
-    {
-        setOperand(0, argsObj);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* getArgsObject() {
-        return getOperand(0);
-    }
-
-    MSetArgumentsObjectArg* mir() const {
-        return mir_->toSetArgumentsObjectArg();
-    }
-
-    static const size_t ValueIndex = 1;
-};
-
-// If the Value is an Object, return unbox(Value).
-// Otherwise, return the other Object.
-class LReturnFromCtor : public LInstructionHelper<1, BOX_PIECES + 1, 0>
-{
-  public:
-    LIR_HEADER(ReturnFromCtor)
-
-    explicit LReturnFromCtor(const LAllocation& object)
-    {
-        // Value set by useBox() during lowering.
-        setOperand(LReturnFromCtor::ObjectIndex, object);
-    }
-
-    const LAllocation* getObject() {
-        return getOperand(LReturnFromCtor::ObjectIndex);
-    }
-
-    static const size_t ValueIndex = 0;
-    static const size_t ObjectIndex = BOX_PIECES;
-};
-
-class LComputeThis : public LInstructionHelper<1, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(ComputeThis)
-
-    static const size_t ValueIndex = 0;
-
-    const LDefinition* output() {
-        return getDef(0);
-    }
-
-    MComputeThis* mir() const {
-        return mir_->toComputeThis();
-    }
-};
-
-class LLoadArrowThis : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    explicit LLoadArrowThis(const LAllocation& callee) {
-        setOperand(0, callee);
-    }
-
-    LIR_HEADER(LoadArrowThis)
-
-    const LAllocation* callee() {
-        return getOperand(0);
-    }
-};
-
-// Writes a typed argument for a function call to the frame's argument vector.
-class LStackArgT : public LInstructionHelper<0, 1, 0>
-{
-    uint32_t argslot_; // Index into frame-scope argument vector.
-    MIRType type_;
-
-  public:
-    LIR_HEADER(StackArgT)
-
-    LStackArgT(uint32_t argslot, MIRType type, const LAllocation& arg)
-      : argslot_(argslot),
-        type_(type)
-    {
-        setOperand(0, arg);
-    }
-    uint32_t argslot() const {
-        return argslot_;
-    }
-    MIRType type() const {
-        return type_;
-    }
-    const LAllocation* getArgument() {
-        return getOperand(0);
-    }
-};
-
-// Writes an untyped argument for a function call to the frame's argument vector.
-class LStackArgV : public LInstructionHelper<0, BOX_PIECES, 0>
-{
-    uint32_t argslot_; // Index into frame-scope argument vector.
-
-  public:
-    LIR_HEADER(StackArgV)
-
-    explicit LStackArgV(uint32_t argslot)
-      : argslot_(argslot)
-    { }
-
-    uint32_t argslot() const {
-        return argslot_;
-    }
-};
-
-// Common code for LIR descended from MCall.
-template <size_t Defs, size_t Operands, size_t Temps>
-class LJSCallInstructionHelper : public LCallInstructionHelper<Defs, Operands, Temps>
-{
-  public:
-    uint32_t argslot() const {
-        if (JitStackValueAlignment > 1)
-            return AlignBytes(mir()->numStackArgs(), JitStackValueAlignment);
-        return mir()->numStackArgs();
-    }
-    MCall* mir() const {
-        return this->mir_->toCall();
-    }
-
-    bool hasSingleTarget() const {
-        return getSingleTarget() != nullptr;
-    }
-    JSFunction* getSingleTarget() const {
-        return mir()->getSingleTarget();
-    }
-
-    // Does not include |this|.
-    uint32_t numActualArgs() const {
-        return mir()->numActualArgs();
-    }
-
-    bool isConstructing() const {
-        return mir()->isConstructing();
-    }
-};
-
-// Generates a polymorphic callsite, wherein the function being called is
-// unknown and anticipated to vary.
-class LCallGeneric : public LJSCallInstructionHelper<BOX_PIECES, 1, 2>
-{
-  public:
-    LIR_HEADER(CallGeneric)
-
-    LCallGeneric(const LAllocation& func, const LDefinition& nargsreg,
-                 const LDefinition& tmpobjreg)
-    {
-        setOperand(0, func);
-        setTemp(0, nargsreg);
-        setTemp(1, tmpobjreg);
-    }
-
-    const LAllocation* getFunction() {
-        return getOperand(0);
-    }
-    const LDefinition* getNargsReg() {
-        return getTemp(0);
-    }
-    const LDefinition* getTempObject() {
-        return getTemp(1);
-    }
-};
-
-// Generates a hardcoded callsite for a known, non-native target.
-class LCallKnown : public LJSCallInstructionHelper<BOX_PIECES, 1, 1>
-{
-  public:
-    LIR_HEADER(CallKnown)
-
-    LCallKnown(const LAllocation& func, const LDefinition& tmpobjreg)
-    {
-        setOperand(0, func);
-        setTemp(0, tmpobjreg);
-    }
-
-    const LAllocation* getFunction() {
-        return getOperand(0);
-    }
-    const LDefinition* getTempObject() {
-        return getTemp(0);
-    }
-};
-
-// Generates a hardcoded callsite for a known, native target.
-class LCallNative : public LJSCallInstructionHelper<BOX_PIECES, 0, 4>
-{
-  public:
-    LIR_HEADER(CallNative)
-
-    LCallNative(const LDefinition& argContext, const LDefinition& argUintN,
-                const LDefinition& argVp, const LDefinition& tmpreg)
-    {
-        // Registers used for callWithABI().
-        setTemp(0, argContext);
-        setTemp(1, argUintN);
-        setTemp(2, argVp);
-
-        // Temporary registers.
-        setTemp(3, tmpreg);
-    }
-
-    const LDefinition* getArgContextReg() {
-        return getTemp(0);
-    }
-    const LDefinition* getArgUintNReg() {
-        return getTemp(1);
-    }
-    const LDefinition* getArgVpReg() {
-        return getTemp(2);
-    }
-    const LDefinition* getTempReg() {
-        return getTemp(3);
-    }
-};
-
-// Generates a hardcoded callsite for a known, DOM-native target.
-class LCallDOMNative : public LJSCallInstructionHelper<BOX_PIECES, 0, 4>
-{
-  public:
-    LIR_HEADER(CallDOMNative)
-
-    LCallDOMNative(const LDefinition& argJSContext, const LDefinition& argObj,
-                   const LDefinition& argPrivate, const LDefinition& argArgs)
-    {
-        setTemp(0, argJSContext);
-        setTemp(1, argObj);
-        setTemp(2, argPrivate);
-        setTemp(3, argArgs);
-    }
-
-    const LDefinition* getArgJSContext() {
-        return getTemp(0);
-    }
-    const LDefinition* getArgObj() {
-        return getTemp(1);
-    }
-    const LDefinition* getArgPrivate() {
-        return getTemp(2);
-    }
-    const LDefinition* getArgArgs() {
-        return getTemp(3);
-    }
-};
-
-class LBail : public LInstructionHelper<0, 0, 0>
-{
-  public:
-    LIR_HEADER(Bail)
-};
-
-class LUnreachable : public LControlInstructionHelper<0, 0, 0>
-{
-  public:
-    LIR_HEADER(Unreachable)
-};
-
-class LEncodeSnapshot : public LInstructionHelper<0, 0, 0>
-{
-  public:
-    LIR_HEADER(EncodeSnapshot)
-};
-
-template <size_t defs, size_t ops>
-class LDOMPropertyInstructionHelper : public LCallInstructionHelper<defs, 1 + ops, 3>
-{
-  protected:
-    LDOMPropertyInstructionHelper(const LDefinition& JSContextReg, const LAllocation& ObjectReg,
-                                  const LDefinition& PrivReg, const LDefinition& ValueReg)
-    {
-        this->setOperand(0, ObjectReg);
-        this->setTemp(0, JSContextReg);
-        this->setTemp(1, PrivReg);
-        this->setTemp(2, ValueReg);
-    }
-
-  public:
-    const LDefinition* getJSContextReg() {
-        return this->getTemp(0);
-    }
-    const LAllocation* getObjectReg() {
-        return this->getOperand(0);
-    }
-    const LDefinition* getPrivReg() {
-        return this->getTemp(1);
-    }
-    const LDefinition* getValueReg() {
-        return this->getTemp(2);
-    }
-};
-
-
-class LGetDOMProperty : public LDOMPropertyInstructionHelper<BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(GetDOMProperty)
-
-    LGetDOMProperty(const LDefinition& JSContextReg, const LAllocation& ObjectReg,
-                    const LDefinition& PrivReg, const LDefinition& ValueReg)
-      : LDOMPropertyInstructionHelper<BOX_PIECES, 0>(JSContextReg, ObjectReg,
-                                                     PrivReg, ValueReg)
-    { }
-
-    MGetDOMProperty* mir() const {
-        return mir_->toGetDOMProperty();
-    }
-};
-
-class LGetDOMMemberV : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    LIR_HEADER(GetDOMMemberV);
-    explicit LGetDOMMemberV(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-
-    MGetDOMMember* mir() const {
-        return mir_->toGetDOMMember();
-    }
-};
-
-class LGetDOMMemberT : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(GetDOMMemberT);
-    explicit LGetDOMMemberT(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-
-    MGetDOMMember* mir() const {
-        return mir_->toGetDOMMember();
-    }
-};
-
-class LSetDOMProperty : public LDOMPropertyInstructionHelper<0, BOX_PIECES>
-{
-  public:
-    LIR_HEADER(SetDOMProperty)
-
-    LSetDOMProperty(const LDefinition& JSContextReg, const LAllocation& ObjectReg,
-                    const LDefinition& PrivReg, const LDefinition& ValueReg)
-      : LDOMPropertyInstructionHelper<0, BOX_PIECES>(JSContextReg, ObjectReg,
-                                                     PrivReg, ValueReg)
-    { }
-
-    static const size_t Value = 1;
-
-    MSetDOMProperty* mir() const {
-        return mir_->toSetDOMProperty();
-    }
-};
-
-// Generates a polymorphic callsite, wherein the function being called is
-// unknown and anticipated to vary.
-class LApplyArgsGeneric : public LCallInstructionHelper<BOX_PIECES, BOX_PIECES + 2, 2>
-{
-  public:
-    LIR_HEADER(ApplyArgsGeneric)
-
-    LApplyArgsGeneric(const LAllocation& func, const LAllocation& argc,
-                      const LDefinition& tmpobjreg, const LDefinition& tmpcopy)
-    {
-        setOperand(0, func);
-        setOperand(1, argc);
-        setTemp(0, tmpobjreg);
-        setTemp(1, tmpcopy);
-    }
-
-    MApplyArgs* mir() const {
-        return mir_->toApplyArgs();
-    }
-
-    bool hasSingleTarget() const {
-        return getSingleTarget() != nullptr;
-    }
-    JSFunction* getSingleTarget() const {
-        return mir()->getSingleTarget();
-    }
-
-    const LAllocation* getFunction() {
-        return getOperand(0);
-    }
-    const LAllocation* getArgc() {
-        return getOperand(1);
-    }
-    static const size_t ThisIndex = 2;
-
-    const LDefinition* getTempObject() {
-        return getTemp(0);
-    }
-    const LDefinition* getTempStackCounter() {
-        return getTemp(1);
-    }
-};
-
-class LArraySplice : public LCallInstructionHelper<0, 3, 0>
-{
-  public:
-    LIR_HEADER(ArraySplice)
-
-    LArraySplice(const LAllocation& object, const LAllocation& start,
-                 const LAllocation& deleteCount)
-    {
-        setOperand(0, object);
-        setOperand(1, start);
-        setOperand(2, deleteCount);
-    }
-
-    MArraySplice* mir() const {
-        return mir_->toArraySplice();
-    }
-
-    const LAllocation* getObject() {
-        return getOperand(0);
-    }
-    const LAllocation* getStart() {
-        return getOperand(1);
-    }
-    const LAllocation* getDeleteCount() {
-        return getOperand(2);
-    }
-};
-
-class LGetDynamicName : public LCallInstructionHelper<BOX_PIECES, 2, 3>
-{
-  public:
-    LIR_HEADER(GetDynamicName)
-
-    LGetDynamicName(const LAllocation& scopeChain, const LAllocation& name,
-                    const LDefinition& temp1, const LDefinition& temp2, const LDefinition& temp3)
-    {
-        setOperand(0, scopeChain);
-        setOperand(1, name);
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-        setTemp(2, temp3);
-    }
-
-    MGetDynamicName* mir() const {
-        return mir_->toGetDynamicName();
-    }
-
-    const LAllocation* getScopeChain() {
-        return getOperand(0);
-    }
-    const LAllocation* getName() {
-        return getOperand(1);
-    }
-
-    const LDefinition* temp1() {
-        return getTemp(0);
-    }
-    const LDefinition* temp2() {
-        return getTemp(1);
-    }
-    const LDefinition* temp3() {
-        return getTemp(2);
-    }
-};
-
-class LFilterArgumentsOrEvalS : public LCallInstructionHelper<0, 1, 2>
-{
-  public:
-    LIR_HEADER(FilterArgumentsOrEvalS)
-
-    LFilterArgumentsOrEvalS(const LAllocation& string, const LDefinition& temp1,
-                            const LDefinition& temp2)
-    {
-        setOperand(0, string);
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-    }
-
-    MFilterArgumentsOrEval* mir() const {
-        return mir_->toFilterArgumentsOrEval();
-    }
-
-    const LAllocation* getString() {
-        return getOperand(0);
-    }
-    const LDefinition* temp1() {
-        return getTemp(0);
-    }
-    const LDefinition* temp2() {
-        return getTemp(1);
-    }
-};
-
-class LFilterArgumentsOrEvalV : public LCallInstructionHelper<0, BOX_PIECES, 3>
-{
-  public:
-    LIR_HEADER(FilterArgumentsOrEvalV)
-
-    LFilterArgumentsOrEvalV(const LDefinition& temp1, const LDefinition& temp2,
-                            const LDefinition& temp3)
-    {
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-        setTemp(2, temp3);
-    }
-
-    static const size_t Input = 0;
-
-    MFilterArgumentsOrEval* mir() const {
-        return mir_->toFilterArgumentsOrEval();
-    }
-
-    const LDefinition* temp1() {
-        return getTemp(0);
-    }
-    const LDefinition* temp2() {
-        return getTemp(1);
-    }
-    const LDefinition* temp3() {
-        return getTemp(2);
-    }
-};
-
-class LCallDirectEval : public LCallInstructionHelper<BOX_PIECES, 2 + (2 * BOX_PIECES), 0>
-{
-  public:
-    LIR_HEADER(CallDirectEval)
-
-    LCallDirectEval(const LAllocation& scopeChain, const LAllocation& string)
-    {
-        setOperand(0, scopeChain);
-        setOperand(1, string);
-    }
-
-    static const size_t ThisValue = 2;
-    static const size_t NewTarget = 2 + BOX_PIECES;
-
-    MCallDirectEval* mir() const {
-        return mir_->toCallDirectEval();
-    }
-
-    const LAllocation* getScopeChain() {
-        return getOperand(0);
-    }
-    const LAllocation* getString() {
-        return getOperand(1);
-    }
-};
-
-// Takes in either an integer or boolean input and tests it for truthiness.
-class LTestIAndBranch : public LControlInstructionHelper<2, 1, 0>
-{
-  public:
-    LIR_HEADER(TestIAndBranch)
-
-    LTestIAndBranch(const LAllocation& in, MBasicBlock* ifTrue, MBasicBlock* ifFalse)
-    {
-        setOperand(0, in);
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-};
-
-// Takes in either an integer or boolean input and tests it for truthiness.
-class LTestDAndBranch : public LControlInstructionHelper<2, 1, 0>
-{
-  public:
-    LIR_HEADER(TestDAndBranch)
-
-    LTestDAndBranch(const LAllocation& in, MBasicBlock* ifTrue, MBasicBlock* ifFalse)
-    {
-        setOperand(0, in);
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-};
-
-// Takes in either an integer or boolean input and tests it for truthiness.
-class LTestFAndBranch : public LControlInstructionHelper<2, 1, 0>
-{
-  public:
-    LIR_HEADER(TestFAndBranch)
-
-    LTestFAndBranch(const LAllocation& in, MBasicBlock* ifTrue, MBasicBlock* ifFalse)
-    {
-        setOperand(0, in);
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-};
-
-// Takes an object and tests it for truthiness.  An object is falsy iff it
-// emulates |undefined|; see js::EmulatesUndefined.
-class LTestOAndBranch : public LControlInstructionHelper<2, 1, 1>
-{
-  public:
-    LIR_HEADER(TestOAndBranch)
-
-    LTestOAndBranch(const LAllocation& input, MBasicBlock* ifTruthy, MBasicBlock* ifFalsy,
-                    const LDefinition& temp)
-    {
-        setOperand(0, input);
-        setSuccessor(0, ifTruthy);
-        setSuccessor(1, ifFalsy);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MBasicBlock* ifTruthy() {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalsy() {
-        return getSuccessor(1);
-    }
-
-    MTest* mir() {
-        return mir_->toTest();
-    }
-};
-
-// Takes in a boxed value and tests it for truthiness.
-class LTestVAndBranch : public LControlInstructionHelper<2, BOX_PIECES, 3>
-{
-  public:
-    LIR_HEADER(TestVAndBranch)
-
-    LTestVAndBranch(MBasicBlock* ifTruthy, MBasicBlock* ifFalsy, const LDefinition& temp0,
-                    const LDefinition& temp1, const LDefinition& temp2)
-    {
-        setSuccessor(0, ifTruthy);
-        setSuccessor(1, ifFalsy);
-        setTemp(0, temp0);
-        setTemp(1, temp1);
-        setTemp(2, temp2);
-    }
-
-    const char* extraName() const {
-        return mir()->operandMightEmulateUndefined() ? "MightEmulateUndefined" : nullptr;
-    }
-
-    static const size_t Input = 0;
-
-    const LDefinition* tempFloat() {
-        return getTemp(0);
-    }
-
-    const LDefinition* temp1() {
-        return getTemp(1);
-    }
-
-    const LDefinition* temp2() {
-        return getTemp(2);
-    }
-
-    MBasicBlock* ifTruthy() {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalsy() {
-        return getSuccessor(1);
-    }
-
-    MTest* mir() const {
-        return mir_->toTest();
-    }
-};
-
-// Dispatches control flow to a successor based on incoming JSFunction*.
-// Used to implemenent polymorphic inlining.
-class LFunctionDispatch : public LInstructionHelper<0, 1, 0>
-{
-    // Dispatch is performed based on a function -> block map
-    // stored in the MIR.
-
-  public:
-    LIR_HEADER(FunctionDispatch);
-
-    explicit LFunctionDispatch(const LAllocation& in) {
-        setOperand(0, in);
-    }
-
-    MFunctionDispatch* mir() const {
-        return mir_->toFunctionDispatch();
-    }
-};
-
-class LObjectGroupDispatch : public LInstructionHelper<0, 1, 1>
-{
-    // Dispatch is performed based on an ObjectGroup -> block
-    // map inferred by the MIR.
-
-  public:
-    LIR_HEADER(ObjectGroupDispatch);
-
-    const char* extraName() const {
-        return mir()->hasFallback() ? "HasFallback" : "NoFallback";
-    }
-
-    LObjectGroupDispatch(const LAllocation& in, const LDefinition& temp) {
-        setOperand(0, in);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MObjectGroupDispatch* mir() const {
-        return mir_->toObjectGroupDispatch();
-    }
-};
-
-// Compares two integral values of the same JS type, either integer or object.
-// For objects, both operands are in registers.
-class LCompare : public LInstructionHelper<1, 2, 0>
-{
-    JSOp jsop_;
-
-  public:
-    LIR_HEADER(Compare)
-    LCompare(JSOp jsop, const LAllocation& left, const LAllocation& right)
-      : jsop_(jsop)
-    {
-        setOperand(0, left);
-        setOperand(1, right);
-    }
-
-    JSOp jsop() const {
-        return jsop_;
-    }
-    const LAllocation* left() {
-        return getOperand(0);
-    }
-    const LAllocation* right() {
-        return getOperand(1);
-    }
-    MCompare* mir() {
-        return mir_->toCompare();
-    }
-    const char* extraName() const {
-        return js_CodeName[jsop_];
-    }
-};
-
-// Compares two integral values of the same JS type, either integer or object.
-// For objects, both operands are in registers.
-class LCompareAndBranch : public LControlInstructionHelper<2, 2, 0>
-{
-    MCompare* cmpMir_;
-    JSOp jsop_;
-
-  public:
-    LIR_HEADER(CompareAndBranch)
-    LCompareAndBranch(MCompare* cmpMir, JSOp jsop,
-                      const LAllocation& left, const LAllocation& right,
-                      MBasicBlock* ifTrue, MBasicBlock* ifFalse)
-      : cmpMir_(cmpMir), jsop_(jsop)
-    {
-        setOperand(0, left);
-        setOperand(1, right);
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    JSOp jsop() const {
-        return jsop_;
-    }
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-    const LAllocation* left() {
-        return getOperand(0);
-    }
-    const LAllocation* right() {
-        return getOperand(1);
-    }
-    MTest* mir() const {
-        return mir_->toTest();
-    }
-    MCompare* cmpMir() const {
-        return cmpMir_;
-    }
-    const char* extraName() const {
-        return js_CodeName[jsop_];
-    }
-};
-
-class LCompareD : public LInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(CompareD)
-    LCompareD(const LAllocation& left, const LAllocation& right) {
-        setOperand(0, left);
-        setOperand(1, right);
-    }
-
-    const LAllocation* left() {
-        return getOperand(0);
-    }
-    const LAllocation* right() {
-        return getOperand(1);
-    }
-    MCompare* mir() {
-        return mir_->toCompare();
-    }
-};
-
-class LCompareF : public LInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(CompareF)
-    LCompareF(const LAllocation& left, const LAllocation& right) {
-        setOperand(0, left);
-        setOperand(1, right);
-    }
-
-    const LAllocation* left() {
-        return getOperand(0);
-    }
-    const LAllocation* right() {
-        return getOperand(1);
-    }
-    MCompare* mir() {
-        return mir_->toCompare();
-    }
-};
-
-class LCompareDAndBranch : public LControlInstructionHelper<2, 2, 0>
-{
-    MCompare* cmpMir_;
-
-  public:
-    LIR_HEADER(CompareDAndBranch)
-    LCompareDAndBranch(MCompare* cmpMir, const LAllocation& left, const LAllocation& right,
-                       MBasicBlock* ifTrue, MBasicBlock* ifFalse)
-      : cmpMir_(cmpMir)
-    {
-        setOperand(0, left);
-        setOperand(1, right);
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-    const LAllocation* left() {
-        return getOperand(0);
-    }
-    const LAllocation* right() {
-        return getOperand(1);
-    }
-    MTest* mir() const {
-        return mir_->toTest();
-    }
-    MCompare* cmpMir() const {
-        return cmpMir_;
-    }
-};
-
-class LCompareFAndBranch : public LControlInstructionHelper<2, 2, 0>
-{
-    MCompare* cmpMir_;
-
-  public:
-    LIR_HEADER(CompareFAndBranch)
-    LCompareFAndBranch(MCompare* cmpMir, const LAllocation& left, const LAllocation& right,
-                       MBasicBlock* ifTrue, MBasicBlock* ifFalse)
-      : cmpMir_(cmpMir)
-    {
-        setOperand(0, left);
-        setOperand(1, right);
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-    const LAllocation* left() {
-        return getOperand(0);
-    }
-    const LAllocation* right() {
-        return getOperand(1);
-    }
-    MTest* mir() const {
-        return mir_->toTest();
-    }
-    MCompare* cmpMir() const {
-        return cmpMir_;
-    }
-};
-
-class LCompareS : public LInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(CompareS)
-    LCompareS(const LAllocation& left, const LAllocation& right) {
-        setOperand(0, left);
-        setOperand(1, right);
-    }
-
-    const LAllocation* left() {
-        return getOperand(0);
-    }
-    const LAllocation* right() {
-        return getOperand(1);
-    }
-    MCompare* mir() {
-        return mir_->toCompare();
-    }
-};
-
-// strict-equality between value and string.
-class LCompareStrictS : public LInstructionHelper<1, BOX_PIECES + 1, 1>
-{
-  public:
-    LIR_HEADER(CompareStrictS)
-    LCompareStrictS(const LAllocation& rhs, const LDefinition& temp) {
-        setOperand(BOX_PIECES, rhs);
-        setTemp(0, temp);
-    }
-
-    static const size_t Lhs = 0;
-
-    const LAllocation* right() {
-        return getOperand(BOX_PIECES);
-    }
-    const LDefinition* tempToUnbox() {
-        return getTemp(0);
-    }
-    MCompare* mir() {
-        return mir_->toCompare();
-    }
-};
-
-// Used for strict-equality comparisons where one side is a boolean
-// and the other is a value. Note that CompareI is used to compare
-// two booleans.
-class LCompareB : public LInstructionHelper<1, BOX_PIECES + 1, 0>
-{
-  public:
-    LIR_HEADER(CompareB)
-
-    explicit LCompareB(const LAllocation& rhs) {
-        setOperand(BOX_PIECES, rhs);
-    }
-
-    static const size_t Lhs = 0;
-
-    const LAllocation* rhs() {
-        return getOperand(BOX_PIECES);
-    }
-
-    MCompare* mir() {
-        return mir_->toCompare();
-    }
-};
-
-class LCompareBAndBranch : public LControlInstructionHelper<2, BOX_PIECES + 1, 0>
-{
-    MCompare* cmpMir_;
-
-  public:
-    LIR_HEADER(CompareBAndBranch)
-
-    LCompareBAndBranch(MCompare* cmpMir, const LAllocation& rhs,
-                       MBasicBlock* ifTrue, MBasicBlock* ifFalse)
-      : cmpMir_(cmpMir)
-    {
-        setOperand(BOX_PIECES, rhs);
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    static const size_t Lhs = 0;
-
-    const LAllocation* rhs() {
-        return getOperand(BOX_PIECES);
-    }
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-    MTest* mir() const {
-        return mir_->toTest();
-    }
-    MCompare* cmpMir() const {
-        return cmpMir_;
-    }
-};
-
-class LCompareV : public LInstructionHelper<1, 2 * BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(CompareV)
-
-    static const size_t LhsInput = 0;
-    static const size_t RhsInput = BOX_PIECES;
-
-    MCompare* mir() const {
-        return mir_->toCompare();
-    }
-};
-
-class LCompareVAndBranch : public LControlInstructionHelper<2, 2 * BOX_PIECES, 0>
-{
-    MCompare* cmpMir_;
-
-  public:
-    LIR_HEADER(CompareVAndBranch)
-
-    static const size_t LhsInput = 0;
-    static const size_t RhsInput = BOX_PIECES;
-
-    LCompareVAndBranch(MCompare* cmpMir, MBasicBlock* ifTrue, MBasicBlock* ifFalse)
-      : cmpMir_(cmpMir)
-    {
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-    MTest* mir() const {
-        return mir_->toTest();
-    }
-    MCompare* cmpMir() const {
-        return cmpMir_;
-    }
-};
-
-class LCompareVM : public LCallInstructionHelper<1, 2 * BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(CompareVM)
-
-    static const size_t LhsInput = 0;
-    static const size_t RhsInput = BOX_PIECES;
-
-    MCompare* mir() const {
-        return mir_->toCompare();
-    }
-};
-
-class LBitAndAndBranch : public LControlInstructionHelper<2, 2, 0>
-{
-  public:
-    LIR_HEADER(BitAndAndBranch)
-    LBitAndAndBranch(MBasicBlock* ifTrue, MBasicBlock* ifFalse)
-    {
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-    const LAllocation* left() {
-        return getOperand(0);
-    }
-    const LAllocation* right() {
-        return getOperand(1);
-    }
-};
-
-// Takes a value and tests whether it is null, undefined, or is an object that
-// emulates |undefined|, as determined by the JSCLASS_EMULATES_UNDEFINED class
-// flag on unwrapped objects.  See also js::EmulatesUndefined.
-class LIsNullOrLikeUndefinedV : public LInstructionHelper<1, BOX_PIECES, 2>
-{
-  public:
-    LIR_HEADER(IsNullOrLikeUndefinedV)
-
-    LIsNullOrLikeUndefinedV(const LDefinition& temp, const LDefinition& tempToUnbox)
-    {
-        setTemp(0, temp);
-        setTemp(1, tempToUnbox);
-    }
-
-    static const size_t Value = 0;
-
-    MCompare* mir() {
-        return mir_->toCompare();
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    const LDefinition* tempToUnbox() {
-        return getTemp(1);
-    }
-};
-
-// Takes an object or object-or-null pointer and tests whether it is null or is
-// an object that emulates |undefined|, as above.
-class LIsNullOrLikeUndefinedT : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(IsNullOrLikeUndefinedT)
-
-    explicit LIsNullOrLikeUndefinedT(const LAllocation& input)
-    {
-        setOperand(0, input);
-    }
-
-    MCompare* mir() {
-        return mir_->toCompare();
-    }
-};
-
-class LIsNullOrLikeUndefinedAndBranchV : public LControlInstructionHelper<2, BOX_PIECES, 2>
-{
-    MCompare* cmpMir_;
-
-  public:
-    LIR_HEADER(IsNullOrLikeUndefinedAndBranchV)
-
-    LIsNullOrLikeUndefinedAndBranchV(MCompare* cmpMir, MBasicBlock* ifTrue, MBasicBlock* ifFalse,
-                                     const LDefinition& temp, const LDefinition& tempToUnbox)
-      : cmpMir_(cmpMir)
-    {
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-        setTemp(0, temp);
-        setTemp(1, tempToUnbox);
-    }
-
-    static const size_t Value = 0;
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-    MTest* mir() const {
-        return mir_->toTest();
-    }
-    MCompare* cmpMir() const {
-        return cmpMir_;
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    const LDefinition* tempToUnbox() {
-        return getTemp(1);
-    }
-};
-
-class LIsNullOrLikeUndefinedAndBranchT : public LControlInstructionHelper<2, 1, 1>
-{
-    MCompare* cmpMir_;
-
-  public:
-    LIR_HEADER(IsNullOrLikeUndefinedAndBranchT)
-
-    LIsNullOrLikeUndefinedAndBranchT(MCompare* cmpMir, const LAllocation& input,
-                                     MBasicBlock* ifTrue, MBasicBlock* ifFalse,
-                                     const LDefinition& temp)
-      : cmpMir_(cmpMir)
-    {
-        setOperand(0, input);
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-        setTemp(0, temp);
-    }
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-    MTest* mir() const {
-        return mir_->toTest();
-    }
-    MCompare* cmpMir() const {
-        return cmpMir_;
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Not operation on an integer.
-class LNotI : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(NotI)
-
-    explicit LNotI(const LAllocation& input) {
-        setOperand(0, input);
-    }
-};
-
-// Not operation on a double.
-class LNotD : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(NotD)
-
-    explicit LNotD(const LAllocation& input) {
-        setOperand(0, input);
-    }
-
-    MNot* mir() {
-        return mir_->toNot();
-    }
-};
-
-// Not operation on a float32.
-class LNotF : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(NotF)
-
-    explicit LNotF(const LAllocation& input) {
-        setOperand(0, input);
-    }
-
-    MNot* mir() {
-        return mir_->toNot();
-    }
-};
-
-// Boolean complement operation on an object.
-class LNotO : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(NotO)
-
-    explicit LNotO(const LAllocation& input)
-    {
-        setOperand(0, input);
-    }
-
-    MNot* mir() {
-        return mir_->toNot();
-    }
-};
-
-// Boolean complement operation on a value.
-class LNotV : public LInstructionHelper<1, BOX_PIECES, 3>
-{
-  public:
-    LIR_HEADER(NotV)
-
-    static const size_t Input = 0;
-    LNotV(const LDefinition& temp0, const LDefinition& temp1, const LDefinition& temp2)
-    {
-        setTemp(0, temp0);
-        setTemp(1, temp1);
-        setTemp(2, temp2);
-    }
-
-    const LDefinition* tempFloat() {
-        return getTemp(0);
-    }
-
-    const LDefinition* temp1() {
-        return getTemp(1);
-    }
-
-    const LDefinition* temp2() {
-        return getTemp(2);
-    }
-
-    MNot* mir() {
-        return mir_->toNot();
-    }
-};
-
-// Bitwise not operation, takes a 32-bit integer as input and returning
-// a 32-bit integer result as an output.
-class LBitNotI : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(BitNotI)
-};
-
-// Call a VM function to perform a BITNOT operation.
-class LBitNotV : public LCallInstructionHelper<1, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(BitNotV)
-
-    static const size_t Input = 0;
-};
-
-// Binary bitwise operation, taking two 32-bit integers as inputs and returning
-// a 32-bit integer result as an output.
-class LBitOpI : public LInstructionHelper<1, 2, 0>
-{
-    JSOp op_;
-
-  public:
-    LIR_HEADER(BitOpI)
-
-    explicit LBitOpI(JSOp op)
-      : op_(op)
-    { }
-
-    const char* extraName() const {
-        if (bitop() == JSOP_URSH && mir_->toUrsh()->bailoutsDisabled())
-            return "ursh:BailoutsDisabled";
-        return js_CodeName[op_];
-    }
-
-    JSOp bitop() const {
-        return op_;
-    }
-};
-
-// Call a VM function to perform a bitwise operation.
-class LBitOpV : public LCallInstructionHelper<1, 2 * BOX_PIECES, 0>
-{
-    JSOp jsop_;
-
-  public:
-    LIR_HEADER(BitOpV)
-
-    explicit LBitOpV(JSOp jsop)
-      : jsop_(jsop)
-    { }
-
-    JSOp jsop() const {
-        return jsop_;
-    }
-
-    const char* extraName() const {
-        return js_CodeName[jsop_];
-    }
-
-    static const size_t LhsInput = 0;
-    static const size_t RhsInput = BOX_PIECES;
-};
-
-// Shift operation, taking two 32-bit integers as inputs and returning
-// a 32-bit integer result as an output.
-class LShiftI : public LBinaryMath<0>
-{
-    JSOp op_;
-
-  public:
-    LIR_HEADER(ShiftI)
-
-    explicit LShiftI(JSOp op)
-      : op_(op)
-    { }
-
-    JSOp bitop() {
-        return op_;
-    }
-
-    MInstruction* mir() {
-        return mir_->toInstruction();
-    }
-
-    const char* extraName() const {
-        return js_CodeName[op_];
-    }
-};
-
-class LUrshD : public LBinaryMath<1>
-{
-  public:
-    LIR_HEADER(UrshD)
-
-    LUrshD(const LAllocation& lhs, const LAllocation& rhs, const LDefinition& temp) {
-        setOperand(0, lhs);
-        setOperand(1, rhs);
-        setTemp(0, temp);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Returns from the function being compiled (not used in inlined frames). The
-// input must be a box.
-class LReturn : public LInstructionHelper<0, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(Return)
-};
-
-class LThrow : public LCallInstructionHelper<0, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(Throw)
-
-    static const size_t Value = 0;
-};
-
-class LMinMaxBase : public LInstructionHelper<1, 2, 0>
-{
-  protected:
-    LMinMaxBase(const LAllocation& first, const LAllocation& second)
-    {
-        setOperand(0, first);
-        setOperand(1, second);
-    }
-
-  public:
-    const LAllocation* first() {
-        return this->getOperand(0);
-    }
-    const LAllocation* second() {
-        return this->getOperand(1);
-    }
-    const LDefinition* output() {
-        return this->getDef(0);
-    }
-    MMinMax* mir() const {
-        return mir_->toMinMax();
-    }
-    const char* extraName() const {
-        return mir()->isMax() ? "Max" : "Min";
-    }
-};
-
-class LMinMaxI : public LMinMaxBase
-{
-  public:
-    LIR_HEADER(MinMaxI)
-    LMinMaxI(const LAllocation& first, const LAllocation& second) : LMinMaxBase(first, second)
-    {}
-};
-
-class LMinMaxD : public LMinMaxBase
-{
-  public:
-    LIR_HEADER(MinMaxD)
-    LMinMaxD(const LAllocation& first, const LAllocation& second) : LMinMaxBase(first, second)
-    {}
-};
-
-class LMinMaxF : public LMinMaxBase
-{
-  public:
-    LIR_HEADER(MinMaxF)
-    LMinMaxF(const LAllocation& first, const LAllocation& second) : LMinMaxBase(first, second)
-    {}
-};
-
-// Negative of an integer
-class LNegI : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(NegI);
-    explicit LNegI(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Negative of a double.
-class LNegD : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(NegD)
-    explicit LNegD(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Negative of a float32.
-class LNegF : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(NegF)
-    explicit LNegF(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Absolute value of an integer.
-class LAbsI : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(AbsI)
-    explicit LAbsI(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Absolute value of a double.
-class LAbsD : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(AbsD)
-    explicit LAbsD(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Absolute value of a float32.
-class LAbsF : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(AbsF)
-    explicit LAbsF(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Count leading zeroes
-class LClzI : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(ClzI)
-    explicit LClzI(const LAllocation& num) {
-        setOperand(0, num);
-    }
-
-    MClz* mir() const {
-        return mir_->toClz();
-    }
-};
-
-// Square root of a double.
-class LSqrtD : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(SqrtD)
-    explicit LSqrtD(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Square root of a float32.
-class LSqrtF : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(SqrtF)
-    explicit LSqrtF(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-class LAtan2D : public LCallInstructionHelper<1, 2, 1>
-{
-  public:
-    LIR_HEADER(Atan2D)
-    LAtan2D(const LAllocation& y, const LAllocation& x, const LDefinition& temp) {
-        setOperand(0, y);
-        setOperand(1, x);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* y() {
-        return getOperand(0);
-    }
-
-    const LAllocation* x() {
-        return getOperand(1);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    const LDefinition* output() {
-        return getDef(0);
-    }
-};
-
-class LHypot : public LCallInstructionHelper<1, 4, 1>
-{
-    uint32_t numOperands_;
-  public:
-    LIR_HEADER(Hypot)
-    LHypot(const LAllocation& x, const LAllocation& y, const LDefinition& temp)
-      : numOperands_(2)
-    {
-        setOperand(0, x);
-        setOperand(1, y);
-        setTemp(0, temp);
-    }
-
-    LHypot(const LAllocation& x, const LAllocation& y, const LAllocation& z, const LDefinition& temp)
-      : numOperands_(3)
-    {
-        setOperand(0, x);
-        setOperand(1, y);
-        setOperand(2, z);
-        setTemp(0, temp);
-    }
-
-    LHypot(const LAllocation& x, const LAllocation& y, const LAllocation& z, const LAllocation& w, const LDefinition& temp)
-      : numOperands_(4)
-    {
-        setOperand(0, x);
-        setOperand(1, y);
-        setOperand(2, z);
-        setOperand(3, w);
-        setTemp(0, temp);
-    }
-
-    uint32_t numArgs() const { return numOperands_; }
-
-    const LAllocation* x() {
-        return getOperand(0);
-    }
-
-    const LAllocation* y() {
-        return getOperand(1);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    const LDefinition* output() {
-        return getDef(0);
-    }
-};
-
-// Double raised to an integer power.
-class LPowI : public LCallInstructionHelper<1, 2, 1>
-{
-  public:
-    LIR_HEADER(PowI)
-    LPowI(const LAllocation& value, const LAllocation& power, const LDefinition& temp) {
-        setOperand(0, value);
-        setOperand(1, power);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* value() {
-        return getOperand(0);
-    }
-    const LAllocation* power() {
-        return getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Double raised to a double power.
-class LPowD : public LCallInstructionHelper<1, 2, 1>
-{
-  public:
-    LIR_HEADER(PowD)
-    LPowD(const LAllocation& value, const LAllocation& power, const LDefinition& temp) {
-        setOperand(0, value);
-        setOperand(1, power);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* value() {
-        return getOperand(0);
-    }
-    const LAllocation* power() {
-        return getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-class LMathFunctionD : public LCallInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(MathFunctionD)
-    LMathFunctionD(const LAllocation& input, const LDefinition& temp) {
-        setOperand(0, input);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    MMathFunction* mir() const {
-        return mir_->toMathFunction();
-    }
-    const char* extraName() const {
-        return MMathFunction::FunctionName(mir()->function());
-    }
-};
-
-class LMathFunctionF : public LCallInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(MathFunctionF)
-    LMathFunctionF(const LAllocation& input, const LDefinition& temp) {
-        setOperand(0, input);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    MMathFunction* mir() const {
-        return mir_->toMathFunction();
-    }
-    const char* extraName() const {
-        return MMathFunction::FunctionName(mir()->function());
-    }
-};
-
-// Adds two integers, returning an integer value.
-class LAddI : public LBinaryMath<0>
-{
-    bool recoversInput_;
-
-  public:
-    LIR_HEADER(AddI)
-
-    LAddI()
-      : recoversInput_(false)
-    { }
-
-    const char* extraName() const {
-        return snapshot() ? "OverflowCheck" : nullptr;
-    }
-
-    virtual bool recoversInput() const {
-        return recoversInput_;
-    }
-    void setRecoversInput() {
-        recoversInput_ = true;
-    }
-
-    MAdd* mir() const {
-        return mir_->toAdd();
-    }
-};
-
-// Subtracts two integers, returning an integer value.
-class LSubI : public LBinaryMath<0>
-{
-    bool recoversInput_;
-
-  public:
-    LIR_HEADER(SubI)
-
-    LSubI()
-      : recoversInput_(false)
-    { }
-
-    const char* extraName() const {
-        return snapshot() ? "OverflowCheck" : nullptr;
-    }
-
-    virtual bool recoversInput() const {
-        return recoversInput_;
-    }
-    void setRecoversInput() {
-        recoversInput_ = true;
-    }
-    MSub* mir() const {
-        return mir_->toSub();
-    }
-};
-
-// Performs an add, sub, mul, or div on two double values.
-class LMathD : public LBinaryMath<0>
-{
-    JSOp jsop_;
-
-  public:
-    LIR_HEADER(MathD)
-
-    explicit LMathD(JSOp jsop)
-      : jsop_(jsop)
-    { }
-
-    JSOp jsop() const {
-        return jsop_;
-    }
-
-    const char* extraName() const {
-        return js_CodeName[jsop_];
-    }
-};
-
-// Performs an add, sub, mul, or div on two double values.
-class LMathF: public LBinaryMath<0>
-{
-    JSOp jsop_;
-
-  public:
-    LIR_HEADER(MathF)
-
-    explicit LMathF(JSOp jsop)
-      : jsop_(jsop)
-    { }
-
-    JSOp jsop() const {
-        return jsop_;
-    }
-
-    const char* extraName() const {
-        return js_CodeName[jsop_];
-    }
-};
-
-class LModD : public LBinaryMath<1>
-{
-  public:
-    LIR_HEADER(ModD)
-
-    LModD(const LAllocation& lhs, const LAllocation& rhs, const LDefinition& temp) {
-        setOperand(0, lhs);
-        setOperand(1, rhs);
-        setTemp(0, temp);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    bool isCall() const {
-        return true;
-    }
-};
-
-// Call a VM function to perform a binary operation.
-class LBinaryV : public LCallInstructionHelper<BOX_PIECES, 2 * BOX_PIECES, 0>
-{
-    JSOp jsop_;
-
-  public:
-    LIR_HEADER(BinaryV)
-
-    explicit LBinaryV(JSOp jsop)
-      : jsop_(jsop)
-    { }
-
-    JSOp jsop() const {
-        return jsop_;
-    }
-
-    const char* extraName() const {
-        return js_CodeName[jsop_];
-    }
-
-    static const size_t LhsInput = 0;
-    static const size_t RhsInput = BOX_PIECES;
-};
-
-// Adds two string, returning a string.
-class LConcat : public LInstructionHelper<1, 2, 5>
-{
-  public:
-    LIR_HEADER(Concat)
-
-    LConcat(const LAllocation& lhs, const LAllocation& rhs, const LDefinition& temp1,
-            const LDefinition& temp2, const LDefinition& temp3, const LDefinition& temp4,
-            const LDefinition& temp5)
-    {
-        setOperand(0, lhs);
-        setOperand(1, rhs);
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-        setTemp(2, temp3);
-        setTemp(3, temp4);
-        setTemp(4, temp5);
-    }
-
-    const LAllocation* lhs() {
-        return this->getOperand(0);
-    }
-    const LAllocation* rhs() {
-        return this->getOperand(1);
-    }
-    const LDefinition* temp1() {
-        return this->getTemp(0);
-    }
-    const LDefinition* temp2() {
-        return this->getTemp(1);
-    }
-    const LDefinition* temp3() {
-        return this->getTemp(2);
-    }
-    const LDefinition* temp4() {
-        return this->getTemp(3);
-    }
-    const LDefinition* temp5() {
-        return this->getTemp(4);
-    }
-};
-
-// Get uint16 character code from a string.
-class LCharCodeAt : public LInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(CharCodeAt)
-
-    LCharCodeAt(const LAllocation& str, const LAllocation& index) {
-        setOperand(0, str);
-        setOperand(1, index);
-    }
-
-    const LAllocation* str() {
-        return this->getOperand(0);
-    }
-    const LAllocation* index() {
-        return this->getOperand(1);
-    }
-};
-
-// Convert uint16 character code to a string.
-class LFromCharCode : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(FromCharCode)
-
-    explicit LFromCharCode(const LAllocation& code) {
-        setOperand(0, code);
-    }
-
-    const LAllocation* code() {
-        return this->getOperand(0);
-    }
-};
-
-class LStringSplit : public LCallInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(StringSplit)
-
-    LStringSplit(const LAllocation& string, const LAllocation& separator) {
-        setOperand(0, string);
-        setOperand(1, separator);
-    }
-    const LAllocation* string() {
-        return getOperand(0);
-    }
-    const LAllocation* separator() {
-        return getOperand(1);
-    }
-    const MStringSplit* mir() const {
-        return mir_->toStringSplit();
-    }
-};
-
-class LSubstr : public LInstructionHelper<1, 3, 3>
-{
-  public:
-    LIR_HEADER(Substr)
-
-    LSubstr(const LAllocation& string, const LAllocation& begin, const LAllocation& length,
-            const LDefinition& temp, const LDefinition& temp2, const LDefinition& temp3)
-    {
-        setOperand(0, string);
-        setOperand(1, begin);
-        setOperand(2, length);
-        setTemp(0, temp);
-        setTemp(1, temp2);
-        setTemp(2, temp3);
-    }
-    const LAllocation* string() {
-        return getOperand(0);
-    }
-    const LAllocation* begin() {
-        return getOperand(1);
-    }
-    const LAllocation* length() {
-        return getOperand(2);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    const LDefinition* temp2() {
-        return getTemp(1);
-    }
-    const LDefinition* temp3() {
-        return getTemp(2);
-    }
-    const MStringSplit* mir() const {
-        return mir_->toStringSplit();
-    }
-};
-
-// Convert a 32-bit integer to a double.
-class LInt32ToDouble : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(Int32ToDouble)
-
-    explicit LInt32ToDouble(const LAllocation& input) {
-        setOperand(0, input);
-    }
-};
-
-// Convert a 32-bit float to a double.
-class LFloat32ToDouble : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(Float32ToDouble)
-
-    explicit LFloat32ToDouble(const LAllocation& input) {
-        setOperand(0, input);
-    }
-};
-
-// Convert a double to a 32-bit float.
-class LDoubleToFloat32 : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(DoubleToFloat32)
-
-    explicit LDoubleToFloat32(const LAllocation& input) {
-        setOperand(0, input);
-    }
-};
-
-// Convert a 32-bit integer to a float32.
-class LInt32ToFloat32 : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(Int32ToFloat32)
-
-    explicit LInt32ToFloat32(const LAllocation& input) {
-        setOperand(0, input);
-    }
-};
-
-// Convert a value to a double.
-class LValueToDouble : public LInstructionHelper<1, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(ValueToDouble)
-    static const size_t Input = 0;
-
-    MToDouble* mir() {
-        return mir_->toToDouble();
-    }
-};
-
-// Convert a value to a float32.
-class LValueToFloat32 : public LInstructionHelper<1, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(ValueToFloat32)
-    static const size_t Input = 0;
-
-    MToFloat32* mir() {
-        return mir_->toToFloat32();
-    }
-};
-
-// Convert a value to an int32.
-//   Input: components of a Value
-//   Output: 32-bit integer
-//   Bailout: undefined, string, object, or non-int32 double
-//   Temps: one float register, one GP register
-//
-// This instruction requires a temporary float register.
-class LValueToInt32 : public LInstructionHelper<1, BOX_PIECES, 2>
-{
-  public:
-    enum Mode {
-        NORMAL,
-        TRUNCATE
-    };
-
-  private:
-    Mode mode_;
-
-  public:
-    LIR_HEADER(ValueToInt32)
-
-    LValueToInt32(const LDefinition& temp0, const LDefinition& temp1, Mode mode)
-      : mode_(mode)
-    {
-        setTemp(0, temp0);
-        setTemp(1, temp1);
-    }
-
-    const char* extraName() const {
-        return mode() == NORMAL ? "Normal" : "Truncate";
-    }
-
-    static const size_t Input = 0;
-
-    Mode mode() const {
-        return mode_;
-    }
-    const LDefinition* tempFloat() {
-        return getTemp(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(1);
-    }
-    MToInt32* mirNormal() const {
-        MOZ_ASSERT(mode_ == NORMAL);
-        return mir_->toToInt32();
-    }
-    MTruncateToInt32* mirTruncate() const {
-        MOZ_ASSERT(mode_ == TRUNCATE);
-        return mir_->toTruncateToInt32();
-    }
-    MInstruction* mir() const {
-        return mir_->toInstruction();
-    }
-};
-
-// Convert a double to an int32.
-//   Input: floating-point register
-//   Output: 32-bit integer
-//   Bailout: if the double cannot be converted to an integer.
-class LDoubleToInt32 : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(DoubleToInt32)
-
-    explicit LDoubleToInt32(const LAllocation& in) {
-        setOperand(0, in);
-    }
-
-    MToInt32* mir() const {
-        return mir_->toToInt32();
-    }
-};
-
-// Convert a float32 to an int32.
-//   Input: floating-point register
-//   Output: 32-bit integer
-//   Bailout: if the float32 cannot be converted to an integer.
-class LFloat32ToInt32 : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(Float32ToInt32)
-
-    explicit LFloat32ToInt32(const LAllocation& in) {
-        setOperand(0, in);
-    }
-
-    MToInt32* mir() const {
-        return mir_->toToInt32();
-    }
-};
-
-// Convert a double to a truncated int32.
-//   Input: floating-point register
-//   Output: 32-bit integer
-class LTruncateDToInt32 : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(TruncateDToInt32)
-
-    LTruncateDToInt32(const LAllocation& in, const LDefinition& temp) {
-        setOperand(0, in);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* tempFloat() {
-        return getTemp(0);
-    }
-
-    MTruncateToInt32* mir() const {
-        return mir_->toTruncateToInt32();
-    }
-};
-
-// Convert a float32 to a truncated int32.
-//   Input: floating-point register
-//   Output: 32-bit integer
-class LTruncateFToInt32 : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(TruncateFToInt32)
-
-    LTruncateFToInt32(const LAllocation& in, const LDefinition& temp) {
-        setOperand(0, in);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* tempFloat() {
-        return getTemp(0);
-    }
-
-    MTruncateToInt32* mir() const {
-        return mir_->toTruncateToInt32();
-    }
-};
-
-// Convert a boolean value to a string.
-class LBooleanToString : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(BooleanToString)
-
-    explicit LBooleanToString(const LAllocation& input) {
-        setOperand(0, input);
-    }
-
-    const MToString* mir() {
-        return mir_->toToString();
-    }
-};
-
-// Convert an integer hosted on one definition to a string with a function call.
-class LIntToString : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(IntToString)
-
-    explicit LIntToString(const LAllocation& input) {
-        setOperand(0, input);
-    }
-
-    const MToString* mir() {
-        return mir_->toToString();
-    }
-};
-
-// Convert a double hosted on one definition to a string with a function call.
-class LDoubleToString : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(DoubleToString)
-
-    LDoubleToString(const LAllocation& input, const LDefinition& temp) {
-        setOperand(0, input);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* tempInt() {
-        return getTemp(0);
-    }
-    const MToString* mir() {
-        return mir_->toToString();
-    }
-};
-
-// Convert a primitive to a string with a function call.
-class LValueToString : public LInstructionHelper<1, BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(ValueToString)
-
-    explicit LValueToString(const LDefinition& tempToUnbox)
-    {
-        setTemp(0, tempToUnbox);
-    }
-
-    static const size_t Input = 0;
-
-    const MToString* mir() {
-        return mir_->toToString();
-    }
-
-    const LDefinition* tempToUnbox() {
-        return getTemp(0);
-    }
-};
-
-// Convert a value to an object or null pointer.
-class LValueToObjectOrNull : public LInstructionHelper<1, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(ValueToObjectOrNull)
-
-    explicit LValueToObjectOrNull()
-    {}
-
-    static const size_t Input = 0;
-
-    const MToObjectOrNull* mir() {
-        return mir_->toToObjectOrNull();
-    }
-};
-
-class LInt32x4ToFloat32x4 : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(Int32x4ToFloat32x4);
-    explicit LInt32x4ToFloat32x4(const LAllocation& input) {
-        setOperand(0, input);
-    }
-};
-
-class LFloat32x4ToInt32x4 : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(Float32x4ToInt32x4);
-    explicit LFloat32x4ToInt32x4(const LAllocation& input, const LDefinition& temp) {
-        setOperand(0, input);
-        setTemp(0, temp);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    const MSimdConvert* mir() const {
-        return mir_->toSimdConvert();
-    }
-};
-
-// No-op instruction that is used to hold the entry snapshot. This simplifies
-// register allocation as it doesn't need to sniff the snapshot out of the
-// LIRGraph.
-class LStart : public LInstructionHelper<0, 0, 0>
-{
-  public:
-    LIR_HEADER(Start)
-};
-
-// Passed the BaselineFrame address in the OsrFrameReg by SideCannon().
-// Forwards this object to the LOsrValues for Value materialization.
-class LOsrEntry : public LInstructionHelper<1, 0, 1>
-{
-  protected:
-    Label label_;
-    uint32_t frameDepth_;
-
-  public:
-    LIR_HEADER(OsrEntry)
-
-    explicit LOsrEntry(const LDefinition& temp)
-      : frameDepth_(0)
-    {
-        setTemp(0, temp);
-    }
-
-    void setFrameDepth(uint32_t depth) {
-        frameDepth_ = depth;
-    }
-    uint32_t getFrameDepth() {
-        return frameDepth_;
-    }
-    Label* label() {
-        return &label_;
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Materialize a Value stored in an interpreter frame for OSR.
-class LOsrValue : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    LIR_HEADER(OsrValue)
-
-    explicit LOsrValue(const LAllocation& entry)
-    {
-        setOperand(0, entry);
-    }
-
-    const MOsrValue* mir() {
-        return mir_->toOsrValue();
-    }
-};
-
-// Materialize a JSObject scope chain stored in an interpreter frame for OSR.
-class LOsrScopeChain : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(OsrScopeChain)
-
-    explicit LOsrScopeChain(const LAllocation& entry)
-    {
-        setOperand(0, entry);
-    }
-
-    const MOsrScopeChain* mir() {
-        return mir_->toOsrScopeChain();
-    }
-};
-
-// Materialize a JSObject scope chain stored in an interpreter frame for OSR.
-class LOsrReturnValue : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    LIR_HEADER(OsrReturnValue)
-
-    explicit LOsrReturnValue(const LAllocation& entry)
-    {
-        setOperand(0, entry);
-    }
-
-    const MOsrReturnValue* mir() {
-        return mir_->toOsrReturnValue();
-    }
-};
-
-// Materialize a JSObject ArgumentsObject stored in an interpreter frame for OSR.
-class LOsrArgumentsObject : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(OsrArgumentsObject)
-
-    explicit LOsrArgumentsObject(const LAllocation& entry)
-    {
-        setOperand(0, entry);
-    }
-
-    const MOsrArgumentsObject* mir() {
-        return mir_->toOsrArgumentsObject();
-    }
-};
-
-class LRegExp : public LCallInstructionHelper<1, 0, 0>
-{
-  public:
-    LIR_HEADER(RegExp)
-
-    const MRegExp* mir() const {
-        return mir_->toRegExp();
-    }
-};
-
-class LRegExpExec : public LCallInstructionHelper<BOX_PIECES, 2, 0>
-{
-  public:
-    LIR_HEADER(RegExpExec)
-
-    LRegExpExec(const LAllocation& regexp, const LAllocation& string)
-    {
-        setOperand(0, regexp);
-        setOperand(1, string);
-    }
-
-    const LAllocation* regexp() {
-        return getOperand(0);
-    }
-    const LAllocation* string() {
-        return getOperand(1);
-    }
-
-    const MRegExpExec* mir() const {
-        return mir_->toRegExpExec();
-    }
-};
-
-class LRegExpTest : public LCallInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(RegExpTest)
-
-    LRegExpTest(const LAllocation& regexp, const LAllocation& string)
-    {
-        setOperand(0, regexp);
-        setOperand(1, string);
-    }
-
-    const LAllocation* regexp() {
-        return getOperand(0);
-    }
-    const LAllocation* string() {
-        return getOperand(1);
-    }
-
-    const MRegExpTest* mir() const {
-        return mir_->toRegExpTest();
-    }
-};
-
-
-class LStrReplace : public LCallInstructionHelper<1, 3, 0>
-{
-  public:
-    LStrReplace(const LAllocation& string, const LAllocation& pattern,
-                   const LAllocation& replacement)
-    {
-        setOperand(0, string);
-        setOperand(1, pattern);
-        setOperand(2, replacement);
-    }
-
-    const LAllocation* string() {
-        return getOperand(0);
-    }
-    const LAllocation* pattern() {
-        return getOperand(1);
-    }
-    const LAllocation* replacement() {
-        return getOperand(2);
-    }
-};
-
-class LRegExpReplace: public LStrReplace
-{
-  public:
-    LIR_HEADER(RegExpReplace);
-
-    LRegExpReplace(const LAllocation& string, const LAllocation& pattern,
-                   const LAllocation& replacement)
-      : LStrReplace(string, pattern, replacement)
-    {
-    }
-
-    const MRegExpReplace* mir() const {
-        return mir_->toRegExpReplace();
-    }
-};
-
-class LStringReplace: public LStrReplace
-{
-  public:
-    LIR_HEADER(StringReplace);
-
-    LStringReplace(const LAllocation& string, const LAllocation& pattern,
-                   const LAllocation& replacement)
-      : LStrReplace(string, pattern, replacement)
-    {
-    }
-
-    const MStringReplace* mir() const {
-        return mir_->toStringReplace();
-    }
-};
-
-class LLambdaForSingleton : public LCallInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(LambdaForSingleton)
-
-    explicit LLambdaForSingleton(const LAllocation& scopeChain)
-    {
-        setOperand(0, scopeChain);
-    }
-    const LAllocation* scopeChain() {
-        return getOperand(0);
-    }
-    const MLambda* mir() const {
-        return mir_->toLambda();
-    }
-};
-
-class LLambda : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(Lambda)
-
-    LLambda(const LAllocation& scopeChain, const LDefinition& temp) {
-        setOperand(0, scopeChain);
-        setTemp(0, temp);
-    }
-    const LAllocation* scopeChain() {
-        return getOperand(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    const MLambda* mir() const {
-        return mir_->toLambda();
-    }
-};
-
-class LLambdaArrow : public LInstructionHelper<1, 1 + (2 * BOX_PIECES), 0>
-{
-  public:
-    LIR_HEADER(LambdaArrow)
-
-    static const size_t ThisValue = 1;
-    static const size_t NewTargetValue = ThisValue + BOX_PIECES;
-
-    explicit LLambdaArrow(const LAllocation& scopeChain) {
-        setOperand(0, scopeChain);
-    }
-    const LAllocation* scopeChain() {
-        return getOperand(0);
-    }
-    const MLambdaArrow* mir() const {
-        return mir_->toLambdaArrow();
-    }
-};
-
-class LKeepAliveObject : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(KeepAliveObject)
-
-    explicit LKeepAliveObject(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-};
-
-// Load the "slots" member out of a JSObject.
-//   Input: JSObject pointer
-//   Output: slots pointer
-class LSlots : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(Slots)
-
-    explicit LSlots(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-};
-
-// Load the "elements" member out of a JSObject.
-//   Input: JSObject pointer
-//   Output: elements pointer
-class LElements : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(Elements)
-
-    explicit LElements(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-
-    const MElements* mir() const {
-        return mir_->toElements();
-    }
-};
-
-// If necessary, convert any int32 elements in a vector into doubles.
-class LConvertElementsToDoubles : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(ConvertElementsToDoubles)
-
-    explicit LConvertElementsToDoubles(const LAllocation& elements) {
-        setOperand(0, elements);
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-};
-
-// If |elements| has the CONVERT_DOUBLE_ELEMENTS flag, convert int32 value to
-// double. Else return the original value.
-class LMaybeToDoubleElement : public LInstructionHelper<BOX_PIECES, 2, 1>
-{
-  public:
-    LIR_HEADER(MaybeToDoubleElement)
-
-    LMaybeToDoubleElement(const LAllocation& elements, const LAllocation& value,
-                          const LDefinition& tempFloat) {
-        setOperand(0, elements);
-        setOperand(1, value);
-        setTemp(0, tempFloat);
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-    const LDefinition* tempFloat() {
-        return getTemp(0);
-    }
-};
-
-// If necessary, copy the elements in an object so they may be written to.
-class LMaybeCopyElementsForWrite : public LInstructionHelper<0, 1, 1>
-{
-  public:
-    LIR_HEADER(MaybeCopyElementsForWrite)
-
-    explicit LMaybeCopyElementsForWrite(const LAllocation& obj, const LDefinition& temp) {
-        setOperand(0, obj);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    const MMaybeCopyElementsForWrite* mir() const {
-        return mir_->toMaybeCopyElementsForWrite();
-    }
-};
-
-// Load the initialized length from an elements header.
-class LInitializedLength : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(InitializedLength)
-
-    explicit LInitializedLength(const LAllocation& elements) {
-        setOperand(0, elements);
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-};
-
-// Store to the initialized length in an elements header. Note the input is an
-// *index*, one less than the desired initialized length.
-class LSetInitializedLength : public LInstructionHelper<0, 2, 0>
-{
-  public:
-    LIR_HEADER(SetInitializedLength)
-
-    LSetInitializedLength(const LAllocation& elements, const LAllocation& index) {
-        setOperand(0, elements);
-        setOperand(1, index);
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-};
-
-class LUnboxedArrayLength : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(UnboxedArrayLength)
-
-    explicit LUnboxedArrayLength(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-};
-
-class LUnboxedArrayInitializedLength : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(UnboxedArrayInitializedLength)
-
-    explicit LUnboxedArrayInitializedLength(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-};
-
-class LIncrementUnboxedArrayInitializedLength : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(IncrementUnboxedArrayInitializedLength)
-
-    explicit LIncrementUnboxedArrayInitializedLength(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-};
-
-class LSetUnboxedArrayInitializedLength : public LInstructionHelper<0, 2, 1>
-{
-  public:
-    LIR_HEADER(SetUnboxedArrayInitializedLength)
-
-    explicit LSetUnboxedArrayInitializedLength(const LAllocation& object,
-                                               const LAllocation& length,
-                                               const LDefinition& temp) {
-        setOperand(0, object);
-        setOperand(1, length);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* length() {
-        return getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Load the length from an elements header.
-class LArrayLength : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(ArrayLength)
-
-    explicit LArrayLength(const LAllocation& elements) {
-        setOperand(0, elements);
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-};
-
-// Store to the length in an elements header. Note the input is an *index*,
-// one less than the desired length.
-class LSetArrayLength : public LInstructionHelper<0, 2, 0>
-{
-  public:
-    LIR_HEADER(SetArrayLength)
-
-    LSetArrayLength(const LAllocation& elements, const LAllocation& index) {
-        setOperand(0, elements);
-        setOperand(1, index);
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-};
-
-// Read the length of a typed array.
-class LTypedArrayLength : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(TypedArrayLength)
-
-    explicit LTypedArrayLength(const LAllocation& obj) {
-        setOperand(0, obj);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-};
-
-// Load a typed array's elements vector.
-class LTypedArrayElements : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(TypedArrayElements)
-
-    explicit LTypedArrayElements(const LAllocation& object) {
-        setOperand(0, object);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-};
-
-// Assign
-//
-//   target[targetOffset..targetOffset + source.length] = source[0..source.length]
-//
-// where the source element range doesn't overlap the target element range in
-// memory.
-class LSetDisjointTypedElements : public LCallInstructionHelper<0, 3, 1>
-{
-  public:
-    LIR_HEADER(SetDisjointTypedElements)
-
-    explicit LSetDisjointTypedElements(const LAllocation& target, const LAllocation& targetOffset,
-                                       const LAllocation& source, const LDefinition& temp)
-    {
-        setOperand(0, target);
-        setOperand(1, targetOffset);
-        setOperand(2, source);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* target() {
-        return getOperand(0);
-    }
-
-    const LAllocation* targetOffset() {
-        return getOperand(1);
-    }
-
-    const LAllocation* source() {
-        return getOperand(2);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Load a typed object's descriptor.
-class LTypedObjectDescr : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(TypedObjectDescr)
-
-    explicit LTypedObjectDescr(const LAllocation& object) {
-        setOperand(0, object);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-};
-
-// Load a typed object's elements vector.
-class LTypedObjectElements : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(TypedObjectElements)
-
-    explicit LTypedObjectElements(const LAllocation& object) {
-        setOperand(0, object);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const MTypedObjectElements* mir() const {
-        return mir_->toTypedObjectElements();
-    }
-};
-
-// Load a typed array's elements vector.
-class LSetTypedObjectOffset : public LInstructionHelper<0, 2, 2>
-{
-  public:
-    LIR_HEADER(SetTypedObjectOffset)
-
-    LSetTypedObjectOffset(const LAllocation& object,
-                          const LAllocation& offset,
-                          const LDefinition& temp0,
-                          const LDefinition& temp1)
-    {
-        setOperand(0, object);
-        setOperand(1, offset);
-        setTemp(0, temp0);
-        setTemp(1, temp1);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* offset() {
-        return getOperand(1);
-    }
-    const LDefinition* temp0() {
-        return getTemp(0);
-    }
-    const LDefinition* temp1() {
-        return getTemp(1);
-    }
-};
-
-// Bailout if index >= length.
-class LBoundsCheck : public LInstructionHelper<0, 2, 0>
-{
-  public:
-    LIR_HEADER(BoundsCheck)
-
-    LBoundsCheck(const LAllocation& index, const LAllocation& length) {
-        setOperand(0, index);
-        setOperand(1, length);
-    }
-    const MBoundsCheck* mir() const {
-        return mir_->toBoundsCheck();
-    }
-    const LAllocation* index() {
-        return getOperand(0);
-    }
-    const LAllocation* length() {
-        return getOperand(1);
-    }
-};
-
-// Bailout if index + minimum < 0 or index + maximum >= length.
-class LBoundsCheckRange : public LInstructionHelper<0, 2, 1>
-{
-  public:
-    LIR_HEADER(BoundsCheckRange)
-
-    LBoundsCheckRange(const LAllocation& index, const LAllocation& length,
-                      const LDefinition& temp)
-    {
-        setOperand(0, index);
-        setOperand(1, length);
-        setTemp(0, temp);
-    }
-    const MBoundsCheck* mir() const {
-        return mir_->toBoundsCheck();
-    }
-    const LAllocation* index() {
-        return getOperand(0);
-    }
-    const LAllocation* length() {
-        return getOperand(1);
-    }
-};
-
-// Bailout if index < minimum.
-class LBoundsCheckLower : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(BoundsCheckLower)
-
-    explicit LBoundsCheckLower(const LAllocation& index)
-    {
-        setOperand(0, index);
-    }
-    MBoundsCheckLower* mir() const {
-        return mir_->toBoundsCheckLower();
-    }
-    const LAllocation* index() {
-        return getOperand(0);
-    }
-};
-
-// Load a value from a dense array's elements vector. Bail out if it's the hole value.
-class LLoadElementV : public LInstructionHelper<BOX_PIECES, 2, 0>
-{
-  public:
-    LIR_HEADER(LoadElementV)
-
-    LLoadElementV(const LAllocation& elements, const LAllocation& index) {
-        setOperand(0, elements);
-        setOperand(1, index);
-    }
-
-    const char* extraName() const {
-        return mir()->needsHoleCheck() ? "HoleCheck" : nullptr;
-    }
-
-    const MLoadElement* mir() const {
-        return mir_->toLoadElement();
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-};
-
-class LInArray : public LInstructionHelper<1, 4, 0>
-{
-  public:
-    LIR_HEADER(InArray)
-
-    LInArray(const LAllocation& elements, const LAllocation& index,
-             const LAllocation& initLength, const LAllocation& object)
-    {
-        setOperand(0, elements);
-        setOperand(1, index);
-        setOperand(2, initLength);
-        setOperand(3, object);
-    }
-    const MInArray* mir() const {
-        return mir_->toInArray();
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LAllocation* initLength() {
-        return getOperand(2);
-    }
-    const LAllocation* object() {
-        return getOperand(3);
-    }
-};
-
-
-// Load a value from an array's elements vector, loading |undefined| if we hit a hole.
-// Bail out if we get a negative index.
-class LLoadElementHole : public LInstructionHelper<BOX_PIECES, 3, 0>
-{
-  public:
-    LIR_HEADER(LoadElementHole)
-
-    LLoadElementHole(const LAllocation& elements, const LAllocation& index, const LAllocation& initLength) {
-        setOperand(0, elements);
-        setOperand(1, index);
-        setOperand(2, initLength);
-    }
-
-    const char* extraName() const {
-        return mir()->needsHoleCheck() ? "HoleCheck" : nullptr;
-    }
-
-    const MLoadElementHole* mir() const {
-        return mir_->toLoadElementHole();
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LAllocation* initLength() {
-        return getOperand(2);
-    }
-};
-
-// Load a typed value from a dense array's elements vector. The array must be
-// known to be packed, so that we don't have to check for the hole value.
-// This instruction does not load the type tag and can directly load into a
-// FP register.
-class LLoadElementT : public LInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(LoadElementT)
-
-    LLoadElementT(const LAllocation& elements, const LAllocation& index) {
-        setOperand(0, elements);
-        setOperand(1, index);
-    }
-
-    const char* extraName() const {
-        return mir()->needsHoleCheck() ? "HoleCheck"
-                                       : (mir()->loadDoubles() ? "Doubles" : nullptr);
-    }
-
-    const MLoadElement* mir() const {
-        return mir_->toLoadElement();
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-};
-
-class LLoadUnboxedPointerV : public LInstructionHelper<BOX_PIECES, 2, 0>
-{
-  public:
-    LIR_HEADER(LoadUnboxedPointerV)
-
-    LLoadUnboxedPointerV(const LAllocation& elements, const LAllocation& index) {
-        setOperand(0, elements);
-        setOperand(1, index);
-    }
-
-    const MLoadUnboxedObjectOrNull* mir() const {
-        return mir_->toLoadUnboxedObjectOrNull();
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-};
-
-class LLoadUnboxedPointerT : public LInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(LoadUnboxedPointerT)
-
-    LLoadUnboxedPointerT(const LAllocation& elements, const LAllocation& index) {
-        setOperand(0, elements);
-        setOperand(1, index);
-    }
-
-    MDefinition* mir() {
-        MOZ_ASSERT(mir_->isLoadUnboxedObjectOrNull() || mir_->isLoadUnboxedString());
-        return mir_;
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-};
-
-class LUnboxObjectOrNull : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(UnboxObjectOrNull);
-
-    explicit LUnboxObjectOrNull(const LAllocation& input)
-    {
-        setOperand(0, input);
-    }
-
-    MUnbox* mir() const {
-        return mir_->toUnbox();
-    }
-    const LAllocation* input() {
-        return getOperand(0);
-    }
-};
-
-// Store a boxed value to a dense array's element vector.
-class LStoreElementV : public LInstructionHelper<0, 2 + BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(StoreElementV)
-
-    LStoreElementV(const LAllocation& elements, const LAllocation& index) {
-        setOperand(0, elements);
-        setOperand(1, index);
-    }
-
-    const char* extraName() const {
-        return mir()->needsHoleCheck() ? "HoleCheck" : nullptr;
-    }
-
-    static const size_t Value = 2;
-
-    const MStoreElement* mir() const {
-        return mir_->toStoreElement();
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-};
-
-// Store a typed value to a dense array's elements vector. Compared to
-// LStoreElementV, this instruction can store doubles and constants directly,
-// and does not store the type tag if the array is monomorphic and known to
-// be packed.
-class LStoreElementT : public LInstructionHelper<0, 3, 0>
-{
-  public:
-    LIR_HEADER(StoreElementT)
-
-    LStoreElementT(const LAllocation& elements, const LAllocation& index, const LAllocation& value) {
-        setOperand(0, elements);
-        setOperand(1, index);
-        setOperand(2, value);
-    }
-
-    const char* extraName() const {
-        return mir()->needsHoleCheck() ? "HoleCheck" : nullptr;
-    }
-
-    const MStoreElement* mir() const {
-        return mir_->toStoreElement();
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LAllocation* value() {
-        return getOperand(2);
-    }
-};
-
-// Like LStoreElementV, but supports indexes >= initialized length.
-class LStoreElementHoleV : public LInstructionHelper<0, 3 + BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(StoreElementHoleV)
-
-    LStoreElementHoleV(const LAllocation& object, const LAllocation& elements,
-                       const LAllocation& index, const LDefinition& temp) {
-        setOperand(0, object);
-        setOperand(1, elements);
-        setOperand(2, index);
-        setTemp(0, temp);
-    }
-
-    static const size_t Value = 3;
-
-    const MStoreElementHole* mir() const {
-        return mir_->toStoreElementHole();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* elements() {
-        return getOperand(1);
-    }
-    const LAllocation* index() {
-        return getOperand(2);
-    }
-};
-
-// Like LStoreElementT, but supports indexes >= initialized length.
-class LStoreElementHoleT : public LInstructionHelper<0, 4, 1>
-{
-  public:
-    LIR_HEADER(StoreElementHoleT)
-
-    LStoreElementHoleT(const LAllocation& object, const LAllocation& elements,
-                       const LAllocation& index, const LAllocation& value,
-                       const LDefinition& temp) {
-        setOperand(0, object);
-        setOperand(1, elements);
-        setOperand(2, index);
-        setOperand(3, value);
-        setTemp(0, temp);
-    }
-
-    const MStoreElementHole* mir() const {
-        return mir_->toStoreElementHole();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* elements() {
-        return getOperand(1);
-    }
-    const LAllocation* index() {
-        return getOperand(2);
-    }
-    const LAllocation* value() {
-        return getOperand(3);
-    }
-};
-
-class LStoreUnboxedPointer : public LInstructionHelper<0, 3, 0>
-{
-  public:
-    LIR_HEADER(StoreUnboxedPointer)
-
-    LStoreUnboxedPointer(LAllocation elements, LAllocation index, LAllocation value) {
-        setOperand(0, elements);
-        setOperand(1, index);
-        setOperand(2, value);
-    }
-
-    MDefinition* mir() {
-        MOZ_ASSERT(mir_->isStoreUnboxedObjectOrNull() || mir_->isStoreUnboxedString());
-        return mir_;
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LAllocation* value() {
-        return getOperand(2);
-    }
-};
-
-// If necessary, convert an unboxed object in a particular group to its native
-// representation.
-class LConvertUnboxedObjectToNative : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(ConvertUnboxedObjectToNative)
-
-    explicit LConvertUnboxedObjectToNative(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    MConvertUnboxedObjectToNative* mir() {
-        return mir_->toConvertUnboxedObjectToNative();
-    }
-};
-
-class LArrayPopShiftV : public LInstructionHelper<BOX_PIECES, 1, 2>
-{
-  public:
-    LIR_HEADER(ArrayPopShiftV)
-
-    LArrayPopShiftV(const LAllocation& object, const LDefinition& temp0, const LDefinition& temp1) {
-        setOperand(0, object);
-        setTemp(0, temp0);
-        setTemp(1, temp1);
-    }
-
-    const char* extraName() const {
-        return mir()->mode() == MArrayPopShift::Pop ? "Pop" : "Shift";
-    }
-
-    const MArrayPopShift* mir() const {
-        return mir_->toArrayPopShift();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LDefinition* temp0() {
-        return getTemp(0);
-    }
-    const LDefinition* temp1() {
-        return getTemp(1);
-    }
-};
-
-class LArrayPopShiftT : public LInstructionHelper<1, 1, 2>
-{
-  public:
-    LIR_HEADER(ArrayPopShiftT)
-
-    LArrayPopShiftT(const LAllocation& object, const LDefinition& temp0, const LDefinition& temp1) {
-        setOperand(0, object);
-        setTemp(0, temp0);
-        setTemp(1, temp1);
-    }
-
-    const char* extraName() const {
-        return mir()->mode() == MArrayPopShift::Pop ? "Pop" : "Shift";
-    }
-
-    const MArrayPopShift* mir() const {
-        return mir_->toArrayPopShift();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LDefinition* temp0() {
-        return getTemp(0);
-    }
-    const LDefinition* temp1() {
-        return getTemp(1);
-    }
-};
-
-class LArrayPushV : public LInstructionHelper<1, 1 + BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(ArrayPushV)
-
-    LArrayPushV(const LAllocation& object, const LDefinition& temp) {
-        setOperand(0, object);
-        setTemp(0, temp);
-    }
-
-    static const size_t Value = 1;
-
-    const MArrayPush* mir() const {
-        return mir_->toArrayPush();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-class LArrayPushT : public LInstructionHelper<1, 2, 1>
-{
-  public:
-    LIR_HEADER(ArrayPushT)
-
-    LArrayPushT(const LAllocation& object, const LAllocation& value, const LDefinition& temp) {
-        setOperand(0, object);
-        setOperand(1, value);
-        setTemp(0, temp);
-    }
-
-    const MArrayPush* mir() const {
-        return mir_->toArrayPush();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-class LArrayConcat : public LCallInstructionHelper<1, 2, 2>
-{
-  public:
-    LIR_HEADER(ArrayConcat)
-
-    LArrayConcat(const LAllocation& lhs, const LAllocation& rhs,
-                 const LDefinition& temp1, const LDefinition& temp2) {
-        setOperand(0, lhs);
-        setOperand(1, rhs);
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-    }
-    const MArrayConcat* mir() const {
-        return mir_->toArrayConcat();
-    }
-    const LAllocation* lhs() {
-        return getOperand(0);
-    }
-    const LAllocation* rhs() {
-        return getOperand(1);
-    }
-    const LDefinition* temp1() {
-        return getTemp(0);
-    }
-    const LDefinition* temp2() {
-        return getTemp(1);
-    }
-};
-
-class LArraySlice : public LCallInstructionHelper<1, 3, 2>
-{
-  public:
-    LIR_HEADER(ArraySlice)
-
-    LArraySlice(const LAllocation& obj, const LAllocation& begin, const LAllocation& end,
-                const LDefinition& temp1, const LDefinition& temp2) {
-        setOperand(0, obj);
-        setOperand(1, begin);
-        setOperand(2, end);
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-    }
-    const MArraySlice* mir() const {
-        return mir_->toArraySlice();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* begin() {
-        return getOperand(1);
-    }
-    const LAllocation* end() {
-        return getOperand(2);
-    }
-    const LDefinition* temp1() {
-        return getTemp(0);
-    }
-    const LDefinition* temp2() {
-        return getTemp(1);
-    }
-};
-
-class LArrayJoin : public LCallInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(ArrayJoin)
-
-    LArrayJoin(const LAllocation& array, const LAllocation& sep) {
-        setOperand(0, array);
-        setOperand(1, sep);
-    }
-
-    const MArrayJoin* mir() const {
-        return mir_->toArrayJoin();
-    }
-    const LAllocation* array() {
-        return getOperand(0);
-    }
-    const LAllocation* separator() {
-        return getOperand(1);
-    }
-};
-
-class LLoadUnboxedScalar : public LInstructionHelper<1, 2, 1>
-{
-  public:
-    LIR_HEADER(LoadUnboxedScalar)
-
-    LLoadUnboxedScalar(const LAllocation& elements, const LAllocation& index,
-                       const LDefinition& temp) {
-        setOperand(0, elements);
-        setOperand(1, index);
-        setTemp(0, temp);
-    }
-    const MLoadUnboxedScalar* mir() const {
-        return mir_->toLoadUnboxedScalar();
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-class LLoadTypedArrayElementHole : public LInstructionHelper<BOX_PIECES, 2, 0>
-{
-  public:
-    LIR_HEADER(LoadTypedArrayElementHole)
-
-    LLoadTypedArrayElementHole(const LAllocation& object, const LAllocation& index) {
-        setOperand(0, object);
-        setOperand(1, index);
-    }
-    const MLoadTypedArrayElementHole* mir() const {
-        return mir_->toLoadTypedArrayElementHole();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-};
-
-class LLoadTypedArrayElementStatic : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(LoadTypedArrayElementStatic);
-    explicit LLoadTypedArrayElementStatic(const LAllocation& ptr) {
-        setOperand(0, ptr);
-    }
-    MLoadTypedArrayElementStatic* mir() const {
-        return mir_->toLoadTypedArrayElementStatic();
-    }
-    const LAllocation* ptr() {
-        return getOperand(0);
-    }
-};
-
-class LStoreUnboxedScalar : public LInstructionHelper<0, 3, 0>
-{
-  public:
-    LIR_HEADER(StoreUnboxedScalar)
-
-    LStoreUnboxedScalar(const LAllocation& elements, const LAllocation& index,
-                        const LAllocation& value) {
-        setOperand(0, elements);
-        setOperand(1, index);
-        setOperand(2, value);
-    }
-
-    const MStoreUnboxedScalar* mir() const {
-        return mir_->toStoreUnboxedScalar();
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LAllocation* value() {
-        return getOperand(2);
-    }
-};
-
-class LStoreTypedArrayElementHole : public LInstructionHelper<0, 4, 0>
-{
-  public:
-    LIR_HEADER(StoreTypedArrayElementHole)
-
-    LStoreTypedArrayElementHole(const LAllocation& elements, const LAllocation& length,
-                                const LAllocation& index, const LAllocation& value)
-    {
-        setOperand(0, elements);
-        setOperand(1, length);
-        setOperand(2, index);
-        setOperand(3, value);
-    }
-
-    const MStoreTypedArrayElementHole* mir() const {
-        return mir_->toStoreTypedArrayElementHole();
-    }
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* length() {
-        return getOperand(1);
-    }
-    const LAllocation* index() {
-        return getOperand(2);
-    }
-    const LAllocation* value() {
-        return getOperand(3);
-    }
-};
-
-class LStoreTypedArrayElementStatic : public LInstructionHelper<0, 2, 0>
-{
-  public:
-    LIR_HEADER(StoreTypedArrayElementStatic);
-    LStoreTypedArrayElementStatic(const LAllocation& ptr, const LAllocation& value) {
-        setOperand(0, ptr);
-        setOperand(1, value);
-    }
-    MStoreTypedArrayElementStatic* mir() const {
-        return mir_->toStoreTypedArrayElementStatic();
-    }
-    const LAllocation* ptr() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-};
-
-class LAtomicIsLockFree : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(AtomicIsLockFree)
-
-    explicit LAtomicIsLockFree(const LAllocation& value) {
-        setOperand(0, value);
-    }
-    const LAllocation* value() {
-        return getOperand(0);
-    }
-};
-
-class LCompareExchangeTypedArrayElement : public LInstructionHelper<1, 4, 1>
-{
-  public:
-    LIR_HEADER(CompareExchangeTypedArrayElement)
-
-    LCompareExchangeTypedArrayElement(const LAllocation& elements, const LAllocation& index,
-                                      const LAllocation& oldval, const LAllocation& newval,
-                                      const LDefinition& temp)
-    {
-        setOperand(0, elements);
-        setOperand(1, index);
-        setOperand(2, oldval);
-        setOperand(3, newval);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LAllocation* oldval() {
-        return getOperand(2);
-    }
-    const LAllocation* newval() {
-        return getOperand(3);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    const MCompareExchangeTypedArrayElement* mir() const {
-        return mir_->toCompareExchangeTypedArrayElement();
-    }
-};
-
-class LAtomicExchangeTypedArrayElement : public LInstructionHelper<1, 3, 1>
-{
-  public:
-    LIR_HEADER(AtomicExchangeTypedArrayElement)
-
-    LAtomicExchangeTypedArrayElement(const LAllocation& elements, const LAllocation& index,
-                                     const LAllocation& value, const LDefinition& temp)
-    {
-        setOperand(0, elements);
-        setOperand(1, index);
-        setOperand(2, value);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LAllocation* value() {
-        return getOperand(2);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    const MAtomicExchangeTypedArrayElement* mir() const {
-        return mir_->toAtomicExchangeTypedArrayElement();
-    }
-};
-
-class LAtomicTypedArrayElementBinop : public LInstructionHelper<1, 3, 2>
-{
-  public:
-    LIR_HEADER(AtomicTypedArrayElementBinop)
-
-    static const int32_t valueOp = 2;
-
-    LAtomicTypedArrayElementBinop(const LAllocation& elements, const LAllocation& index,
-                                  const LAllocation& value, const LDefinition& temp1,
-                                  const LDefinition& temp2)
-    {
-        setOperand(0, elements);
-        setOperand(1, index);
-        setOperand(2, value);
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LAllocation* value() {
-        MOZ_ASSERT(valueOp == 2);
-        return getOperand(2);
-    }
-    const LDefinition* temp1() {
-        return getTemp(0);
-    }
-    const LDefinition* temp2() {
-        return getTemp(1);
-    }
-
-    const MAtomicTypedArrayElementBinop* mir() const {
-        return mir_->toAtomicTypedArrayElementBinop();
-    }
-};
-
-// Atomic binary operation where the result is discarded.
-class LAtomicTypedArrayElementBinopForEffect : public LInstructionHelper<0, 3, 0>
-{
-  public:
-    LIR_HEADER(AtomicTypedArrayElementBinopForEffect)
-
-    LAtomicTypedArrayElementBinopForEffect(const LAllocation& elements, const LAllocation& index,
-                                           const LAllocation& value)
-    {
-        setOperand(0, elements);
-        setOperand(1, index);
-        setOperand(2, value);
-    }
-
-    const LAllocation* elements() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LAllocation* value() {
-        return getOperand(2);
-    }
-
-    const MAtomicTypedArrayElementBinop* mir() const {
-        return mir_->toAtomicTypedArrayElementBinop();
-    }
-};
-
-class LEffectiveAddress : public LInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(EffectiveAddress);
-
-    LEffectiveAddress(const LAllocation& base, const LAllocation& index) {
-        setOperand(0, base);
-        setOperand(1, index);
-    }
-    const MEffectiveAddress* mir() const {
-        return mir_->toEffectiveAddress();
-    }
-    const LAllocation* base() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-};
-
-class LClampIToUint8 : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(ClampIToUint8)
-
-    explicit LClampIToUint8(const LAllocation& in) {
-        setOperand(0, in);
-    }
-};
-
-class LClampDToUint8 : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(ClampDToUint8)
-
-    LClampDToUint8(const LAllocation& in, const LDefinition& temp) {
-        setOperand(0, in);
-        setTemp(0, temp);
-    }
-};
-
-class LClampVToUint8 : public LInstructionHelper<1, BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(ClampVToUint8)
-
-    explicit LClampVToUint8(const LDefinition& tempFloat) {
-        setTemp(0, tempFloat);
-    }
-
-    static const size_t Input = 0;
-
-    const LDefinition* tempFloat() {
-        return getTemp(0);
-    }
-    const MClampToUint8* mir() const {
-        return mir_->toClampToUint8();
-    }
-};
-
-// Load a boxed value from an object's fixed slot.
-class LLoadFixedSlotV : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    LIR_HEADER(LoadFixedSlotV)
-
-    explicit LLoadFixedSlotV(const LAllocation& object) {
-        setOperand(0, object);
-    }
-    const MLoadFixedSlot* mir() const {
-        return mir_->toLoadFixedSlot();
-    }
-};
-
-// Load a typed value from an object's fixed slot.
-class LLoadFixedSlotT : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(LoadFixedSlotT)
-
-    explicit LLoadFixedSlotT(const LAllocation& object) {
-        setOperand(0, object);
-    }
-    const MLoadFixedSlot* mir() const {
-        return mir_->toLoadFixedSlot();
-    }
-};
-
-// Store a boxed value to an object's fixed slot.
-class LStoreFixedSlotV : public LInstructionHelper<0, 1 + BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(StoreFixedSlotV)
-
-    explicit LStoreFixedSlotV(const LAllocation& obj) {
-        setOperand(0, obj);
-    }
-
-    static const size_t Value = 1;
-
-    const MStoreFixedSlot* mir() const {
-        return mir_->toStoreFixedSlot();
-    }
-    const LAllocation* obj() {
-        return getOperand(0);
-    }
-};
-
-// Store a typed value to an object's fixed slot.
-class LStoreFixedSlotT : public LInstructionHelper<0, 2, 0>
-{
-  public:
-    LIR_HEADER(StoreFixedSlotT)
-
-    LStoreFixedSlotT(const LAllocation& obj, const LAllocation& value)
-    {
-        setOperand(0, obj);
-        setOperand(1, value);
-    }
-    const MStoreFixedSlot* mir() const {
-        return mir_->toStoreFixedSlot();
-    }
-    const LAllocation* obj() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-};
-
-// Note, Name ICs always return a Value. There are no V/T variants.
-class LGetNameCache : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    LIR_HEADER(GetNameCache)
-
-    explicit LGetNameCache(const LAllocation& scopeObj) {
-        setOperand(0, scopeObj);
-    }
-    const LAllocation* scopeObj() {
-        return getOperand(0);
-    }
-    const MGetNameCache* mir() const {
-        return mir_->toGetNameCache();
-    }
-};
-
-class LCallGetIntrinsicValue : public LCallInstructionHelper<BOX_PIECES, 0, 0>
-{
-  public:
-    LIR_HEADER(CallGetIntrinsicValue)
-
-    const MCallGetIntrinsicValue* mir() const {
-        return mir_->toCallGetIntrinsicValue();
-    }
-};
-
-// Patchable jump to stubs generated for a GetProperty cache, which loads a
-// boxed value.
-class LGetPropertyCacheV : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    LIR_HEADER(GetPropertyCacheV)
-
-    explicit LGetPropertyCacheV(const LAllocation& object) {
-        setOperand(0, object);
-    }
-    const MGetPropertyCache* mir() const {
-        return mir_->toGetPropertyCache();
-    }
-};
-
-// Patchable jump to stubs generated for a GetProperty cache, which loads a
-// value of a known type, possibly into an FP register.
-class LGetPropertyCacheT : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(GetPropertyCacheT)
-
-    explicit LGetPropertyCacheT(const LAllocation& object) {
-        setOperand(0, object);
-    }
-    const MGetPropertyCache* mir() const {
-        return mir_->toGetPropertyCache();
-    }
-};
-
-// Emit code to load a boxed value from an object's slots if its shape matches
-// one of the shapes observed by the baseline IC, else bails out.
-class LGetPropertyPolymorphicV : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    LIR_HEADER(GetPropertyPolymorphicV)
-
-    explicit LGetPropertyPolymorphicV(const LAllocation& obj) {
-        setOperand(0, obj);
-    }
-    const LAllocation* obj() {
-        return getOperand(0);
-    }
-    const MGetPropertyPolymorphic* mir() const {
-        return mir_->toGetPropertyPolymorphic();
-    }
-};
-
-// Emit code to load a typed value from an object's slots if its shape matches
-// one of the shapes observed by the baseline IC, else bails out.
-class LGetPropertyPolymorphicT : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(GetPropertyPolymorphicT)
-
-    LGetPropertyPolymorphicT(const LAllocation& obj, const LDefinition& temp) {
-        setOperand(0, obj);
-        setTemp(0, temp);
-    }
-    const LAllocation* obj() {
-        return getOperand(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    const MGetPropertyPolymorphic* mir() const {
-        return mir_->toGetPropertyPolymorphic();
-    }
-};
-
-// Emit code to store a boxed value to an object's slots if its shape matches
-// one of the shapes observed by the baseline IC, else bails out.
-class LSetPropertyPolymorphicV : public LInstructionHelper<0, 1 + BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(SetPropertyPolymorphicV)
-
-    LSetPropertyPolymorphicV(const LAllocation& obj, const LDefinition& temp) {
-        setOperand(0, obj);
-        setTemp(0, temp);
-    }
-
-    static const size_t Value = 1;
-
-    const LAllocation* obj() {
-        return getOperand(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    const MSetPropertyPolymorphic* mir() const {
-        return mir_->toSetPropertyPolymorphic();
-    }
-};
-
-// Emit code to store a typed value to an object's slots if its shape matches
-// one of the shapes observed by the baseline IC, else bails out.
-class LSetPropertyPolymorphicT : public LInstructionHelper<0, 2, 1>
-{
-    MIRType valueType_;
-
-  public:
-    LIR_HEADER(SetPropertyPolymorphicT)
-
-    LSetPropertyPolymorphicT(const LAllocation& obj, const LAllocation& value, MIRType valueType,
-                             const LDefinition& temp)
-      : valueType_(valueType)
-    {
-        setOperand(0, obj);
-        setOperand(1, value);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* obj() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    MIRType valueType() const {
-        return valueType_;
-    }
-    const MSetPropertyPolymorphic* mir() const {
-        return mir_->toSetPropertyPolymorphic();
-    }
-    const char* extraName() const {
-        return StringFromMIRType(valueType_);
-    }
-};
-
-class LGetElementCacheV : public LInstructionHelper<BOX_PIECES, 1 + BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(GetElementCacheV)
-
-    static const size_t Index = 1;
-
-    explicit LGetElementCacheV(const LAllocation& object) {
-        setOperand(0, object);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const MGetElementCache* mir() const {
-        return mir_->toGetElementCache();
-    }
-};
-
-class LGetElementCacheT : public LInstructionHelper<1, 2, 0>
-{
-  public:
-    LIR_HEADER(GetElementCacheT)
-
-    LGetElementCacheT(const LAllocation& object, const LAllocation& index) {
-        setOperand(0, object);
-        setOperand(1, index);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* index() {
-        return getOperand(1);
-    }
-    const LDefinition* output() {
-        return getDef(0);
-    }
-    const MGetElementCache* mir() const {
-        return mir_->toGetElementCache();
-    }
-};
-
-class LBindNameCache : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(BindNameCache)
-
-    explicit LBindNameCache(const LAllocation& scopeChain) {
-        setOperand(0, scopeChain);
-    }
-    const LAllocation* scopeChain() {
-        return getOperand(0);
-    }
-    const MBindNameCache* mir() const {
-        return mir_->toBindNameCache();
-    }
-};
-
-// Load a value from an object's dslots or a slots vector.
-class LLoadSlotV : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    LIR_HEADER(LoadSlotV)
-
-    explicit LLoadSlotV(const LAllocation& in) {
-        setOperand(0, in);
-    }
-    const MLoadSlot* mir() const {
-        return mir_->toLoadSlot();
-    }
-};
-
-// Load a typed value from an object's dslots or a slots vector. Unlike
-// LLoadSlotV, this can bypass extracting a type tag, directly retrieving a
-// pointer, integer, or double.
-class LLoadSlotT : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(LoadSlotT)
-
-    explicit LLoadSlotT(const LAllocation& slots) {
-        setOperand(0, slots);
-    }
-    const LAllocation* slots() {
-        return getOperand(0);
-    }
-    const LDefinition* output() {
-        return this->getDef(0);
-    }
-    const MLoadSlot* mir() const {
-        return mir_->toLoadSlot();
-    }
-};
-
-// Store a value to an object's dslots or a slots vector.
-class LStoreSlotV : public LInstructionHelper<0, 1 + BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(StoreSlotV)
-
-    explicit LStoreSlotV(const LAllocation& slots) {
-        setOperand(0, slots);
-    }
-
-    static const size_t Value = 1;
-
-    const MStoreSlot* mir() const {
-        return mir_->toStoreSlot();
-    }
-    const LAllocation* slots() {
-        return getOperand(0);
-    }
-};
-
-// Store a typed value to an object's dslots or a slots vector. This has a
-// few advantages over LStoreSlotV:
-// 1) We can bypass storing the type tag if the slot has the same type as
-//    the value.
-// 2) Better register allocation: we can store constants and FP regs directly
-//    without requiring a second register for the value.
-class LStoreSlotT : public LInstructionHelper<0, 2, 0>
-{
-  public:
-    LIR_HEADER(StoreSlotT)
-
-    LStoreSlotT(const LAllocation& slots, const LAllocation& value) {
-        setOperand(0, slots);
-        setOperand(1, value);
-    }
-    const MStoreSlot* mir() const {
-        return mir_->toStoreSlot();
-    }
-    const LAllocation* slots() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-};
-
-// Read length field of a JSString*.
-class LStringLength : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(StringLength)
-
-    explicit LStringLength(const LAllocation& string) {
-        setOperand(0, string);
-    }
-
-    const LAllocation* string() {
-        return getOperand(0);
-    }
-};
-
-// Take the floor of a double precision number. Implements Math.floor().
-class LFloor : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(Floor)
-
-    explicit LFloor(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Take the floor of a single precision number. Implements Math.floor().
-class LFloorF : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(FloorF)
-
-    explicit LFloorF(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Take the ceiling of a double precision number. Implements Math.ceil().
-class LCeil : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(Ceil)
-
-    explicit LCeil(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Take the ceiling of a single precision number. Implements Math.ceil().
-class LCeilF : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(CeilF)
-
-    explicit LCeilF(const LAllocation& num) {
-        setOperand(0, num);
-    }
-};
-
-// Round a double precision number. Implements Math.round().
-class LRound : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(Round)
-
-    LRound(const LAllocation& num, const LDefinition& temp) {
-        setOperand(0, num);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    MRound* mir() const {
-        return mir_->toRound();
-    }
-};
-
-// Round a single precision number. Implements Math.round().
-class LRoundF : public LInstructionHelper<1, 1, 1>
-{
-  public:
-    LIR_HEADER(RoundF)
-
-    LRoundF(const LAllocation& num, const LDefinition& temp) {
-        setOperand(0, num);
-        setTemp(0, temp);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    MRound* mir() const {
-        return mir_->toRound();
-    }
-};
-
-// Load a function's call environment.
-class LFunctionEnvironment : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(FunctionEnvironment)
-
-    explicit LFunctionEnvironment(const LAllocation& function) {
-        setOperand(0, function);
-    }
-    const LAllocation* function() {
-        return getOperand(0);
-    }
-};
-
-class LCallGetProperty : public LCallInstructionHelper<BOX_PIECES, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(CallGetProperty)
-
-    static const size_t Value = 0;
-
-    MCallGetProperty* mir() const {
-        return mir_->toCallGetProperty();
-    }
-};
-
-// Call js::GetElement.
-class LCallGetElement : public LCallInstructionHelper<BOX_PIECES, 2 * BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(CallGetElement)
-
-    static const size_t LhsInput = 0;
-    static const size_t RhsInput = BOX_PIECES;
-
-    MCallGetElement* mir() const {
-        return mir_->toCallGetElement();
-    }
-};
-
-// Call js::SetElement.
-class LCallSetElement : public LCallInstructionHelper<0, 1 + 2 * BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(CallSetElement)
-
-    static const size_t Index = 1;
-    static const size_t Value = 1 + BOX_PIECES;
-
-    const MCallSetElement* mir() const {
-        return mir_->toCallSetElement();
-    }
-};
-
-// Call js::InitElementArray.
-class LCallInitElementArray : public LCallInstructionHelper<0, 1 + BOX_PIECES, 0>
-{
-public:
-    LIR_HEADER(CallInitElementArray)
-
-    static const size_t Value = 1;
-
-    const MCallInitElementArray* mir() const {
-        return mir_->toCallInitElementArray();
-    }
-};
-
-// Call a VM function to perform a property or name assignment of a generic value.
-class LCallSetProperty : public LCallInstructionHelper<0, 1 + BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(CallSetProperty)
-
-    explicit LCallSetProperty(const LAllocation& obj) {
-        setOperand(0, obj);
-    }
-
-    static const size_t Value = 1;
-
-    const MCallSetProperty* mir() const {
-        return mir_->toCallSetProperty();
-    }
-};
-
-class LCallDeleteProperty : public LCallInstructionHelper<1, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(CallDeleteProperty)
-
-    static const size_t Value = 0;
-
-    MDeleteProperty* mir() const {
-        return mir_->toDeleteProperty();
-    }
-};
-
-class LCallDeleteElement : public LCallInstructionHelper<1, 2 * BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(CallDeleteElement)
-
-    static const size_t Value = 0;
-    static const size_t Index = BOX_PIECES;
-
-    MDeleteElement* mir() const {
-        return mir_->toDeleteElement();
-    }
-};
-
-// Patchable jump to stubs generated for a SetProperty cache, which stores a
-// boxed value.
-class LSetPropertyCacheV : public LInstructionHelper<0, 1 + BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(SetPropertyCacheV)
-
-    LSetPropertyCacheV(const LAllocation& object, const LDefinition& slots) {
-        setOperand(0, object);
-        setTemp(0, slots);
-    }
-
-    static const size_t Value = 1;
-
-    const MSetPropertyCache* mir() const {
-        return mir_->toSetPropertyCache();
-    }
-};
-
-// Patchable jump to stubs generated for a SetProperty cache, which stores a
-// value of a known type.
-class LSetPropertyCacheT : public LInstructionHelper<0, 2, 1>
-{
-    MIRType valueType_;
-
-  public:
-    LIR_HEADER(SetPropertyCacheT)
-
-    LSetPropertyCacheT(const LAllocation& object, const LDefinition& slots,
-                       const LAllocation& value, MIRType valueType)
-        : valueType_(valueType)
-    {
-        setOperand(0, object);
-        setOperand(1, value);
-        setTemp(0, slots);
-    }
-
-    const MSetPropertyCache* mir() const {
-        return mir_->toSetPropertyCache();
-    }
-    MIRType valueType() {
-        return valueType_;
-    }
-    const char* extraName() const {
-        return StringFromMIRType(valueType_);
-    }
-};
-
-class LSetElementCacheV : public LInstructionHelper<0, 1 + 2 * BOX_PIECES, 4>
-{
-  public:
-    LIR_HEADER(SetElementCacheV);
-
-    static const size_t Index = 1;
-    static const size_t Value = 1 + BOX_PIECES;
-
-    LSetElementCacheV(const LAllocation& object, const LDefinition& tempToUnboxIndex,
-                      const LDefinition& temp, const LDefinition& tempDouble,
-                      const LDefinition& tempFloat32)
-    {
-        setOperand(0, object);
-        setTemp(0, tempToUnboxIndex);
-        setTemp(1, temp);
-        setTemp(2, tempDouble);
-        setTemp(3, tempFloat32);
-    }
-    const MSetElementCache* mir() const {
-        return mir_->toSetElementCache();
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LDefinition* tempToUnboxIndex() {
-        return getTemp(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(1);
-    }
-    const LDefinition* tempDouble() {
-        return getTemp(2);
-    }
-    const LDefinition* tempFloat32() {
-        if (hasUnaliasedDouble())
-            return getTemp(3);
-        return getTemp(2);
-    }
-
-};
-
-class LSetElementCacheT : public LInstructionHelper<0, 2 + BOX_PIECES, 4>
-{
-  public:
-    LIR_HEADER(SetElementCacheT);
-
-    static const size_t Index = 2;
-
-    LSetElementCacheT(const LAllocation& object, const LAllocation& value,
-                      const LDefinition& tempToUnboxIndex,
-                      const LDefinition& temp, const LDefinition& tempDouble,
-                      const LDefinition& tempFloat32) {
-        setOperand(0, object);
-        setOperand(1, value);
-        setTemp(0, tempToUnboxIndex);
-        setTemp(1, temp);
-        setTemp(2, tempDouble);
-        setTemp(3, tempFloat32);
-    }
-    const MSetElementCache* mir() const {
-        return mir_->toSetElementCache();
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-    const LDefinition* tempToUnboxIndex() {
-        return getTemp(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(1);
-    }
-    const LDefinition* tempDouble() {
-        return getTemp(2);
-    }
-    const LDefinition* tempFloat32() {
-        if (hasUnaliasedDouble())
-            return getTemp(3);
-        return getTemp(2);
-    }
-
-};
-
-class LCallIteratorStart : public LCallInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(CallIteratorStart)
-
-    explicit LCallIteratorStart(const LAllocation& object) {
-        setOperand(0, object);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    MIteratorStart* mir() const {
-        return mir_->toIteratorStart();
-    }
-};
-
-class LIteratorStart : public LInstructionHelper<1, 1, 3>
-{
-  public:
-    LIR_HEADER(IteratorStart)
-
-    LIteratorStart(const LAllocation& object, const LDefinition& temp1,
-                   const LDefinition& temp2, const LDefinition& temp3) {
-        setOperand(0, object);
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-        setTemp(2, temp3);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LDefinition* temp1() {
-        return getTemp(0);
-    }
-    const LDefinition* temp2() {
-        return getTemp(1);
-    }
-    const LDefinition* temp3() {
-        return getTemp(2);
-    }
-    MIteratorStart* mir() const {
-        return mir_->toIteratorStart();
-    }
-};
-
-class LIteratorMore : public LInstructionHelper<BOX_PIECES, 1, 1>
-{
-  public:
-    LIR_HEADER(IteratorMore)
-
-    LIteratorMore(const LAllocation& iterator, const LDefinition& temp) {
-        setOperand(0, iterator);
-        setTemp(0, temp);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    MIteratorMore* mir() const {
-        return mir_->toIteratorMore();
-    }
-};
-
-class LIsNoIterAndBranch : public LControlInstructionHelper<2, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(IsNoIterAndBranch)
-
-    LIsNoIterAndBranch(MBasicBlock* ifTrue, MBasicBlock* ifFalse) {
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    static const size_t Input = 0;
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-};
-
-class LIteratorEnd : public LInstructionHelper<0, 1, 3>
-{
-  public:
-    LIR_HEADER(IteratorEnd)
-
-    LIteratorEnd(const LAllocation& iterator, const LDefinition& temp1,
-                 const LDefinition& temp2, const LDefinition& temp3) {
-        setOperand(0, iterator);
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-        setTemp(2, temp3);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LDefinition* temp1() {
-        return getTemp(0);
-    }
-    const LDefinition* temp2() {
-        return getTemp(1);
-    }
-    const LDefinition* temp3() {
-        return getTemp(2);
-    }
-    MIteratorEnd* mir() const {
-        return mir_->toIteratorEnd();
-    }
-};
-
-// Read the number of actual arguments.
-class LArgumentsLength : public LInstructionHelper<1, 0, 0>
-{
-  public:
-    LIR_HEADER(ArgumentsLength)
-};
-
-// Load a value from the actual arguments.
-class LGetFrameArgument : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    LIR_HEADER(GetFrameArgument)
-
-    explicit LGetFrameArgument(const LAllocation& index) {
-        setOperand(0, index);
-    }
-    const LAllocation* index() {
-        return getOperand(0);
-    }
-};
-
-// Load a value from the actual arguments.
-class LSetFrameArgumentT : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(SetFrameArgumentT)
-
-    explicit LSetFrameArgumentT(const LAllocation& input) {
-        setOperand(0, input);
-    }
-    MSetFrameArgument* mir() const {
-        return mir_->toSetFrameArgument();
-    }
-    const LAllocation* input() {
-        return getOperand(0);
-    }
-};
-
-// Load a value from the actual arguments.
-class LSetFrameArgumentC : public LInstructionHelper<0, 0, 0>
-{
-    Value val_;
-
-  public:
-    LIR_HEADER(SetFrameArgumentC)
-
-    explicit LSetFrameArgumentC(const Value& val) {
-        val_ = val;
-    }
-    MSetFrameArgument* mir() const {
-        return mir_->toSetFrameArgument();
-    }
-    const Value& val() const {
-        return val_;
-    }
-};
-
-// Load a value from the actual arguments.
-class LSetFrameArgumentV : public LInstructionHelper<0, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(SetFrameArgumentV)
-
-    LSetFrameArgumentV() {}
-
-    static const size_t Input = 0;
-
-    MSetFrameArgument* mir() const {
-        return mir_->toSetFrameArgument();
-    }
-};
-
-class LRunOncePrologue : public LCallInstructionHelper<0, 0, 0>
-{
-  public:
-    LIR_HEADER(RunOncePrologue)
-
-    MRunOncePrologue* mir() const {
-        return mir_->toRunOncePrologue();
-    }
-};
-
-// Create the rest parameter.
-class LRest : public LCallInstructionHelper<1, 1, 3>
-{
-  public:
-    LIR_HEADER(Rest)
-
-    LRest(const LAllocation& numActuals, const LDefinition& temp1, const LDefinition& temp2,
-          const LDefinition& temp3)
-    {
-        setOperand(0, numActuals);
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-        setTemp(2, temp3);
-    }
-    const LAllocation* numActuals() {
-        return getOperand(0);
-    }
-    MRest* mir() const {
-        return mir_->toRest();
-    }
-};
-
-class LGuardReceiverPolymorphic : public LInstructionHelper<0, 1, 1>
-{
-  public:
-    LIR_HEADER(GuardReceiverPolymorphic)
-
-    LGuardReceiverPolymorphic(const LAllocation& in, const LDefinition& temp) {
-        setOperand(0, in);
-        setTemp(0, temp);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    const MGuardReceiverPolymorphic* mir() const {
-        return mir_->toGuardReceiverPolymorphic();
-    }
-};
-
-class LGuardUnboxedExpando : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(GuardUnboxedExpando)
-
-    explicit LGuardUnboxedExpando(const LAllocation& in) {
-        setOperand(0, in);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const MGuardUnboxedExpando* mir() const {
-        return mir_->toGuardUnboxedExpando();
-    }
-};
-
-class LLoadUnboxedExpando : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(LoadUnboxedExpando)
-
-    explicit LLoadUnboxedExpando(const LAllocation& in) {
-        setOperand(0, in);
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const MLoadUnboxedExpando* mir() const {
-        return mir_->toLoadUnboxedExpando();
-    }
-};
-
-// Guard that a value is in a TypeSet.
-class LTypeBarrierV : public LInstructionHelper<0, BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(TypeBarrierV)
-
-    explicit LTypeBarrierV(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-
-    static const size_t Input = 0;
-
-    const MTypeBarrier* mir() const {
-        return mir_->toTypeBarrier();
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Guard that a object is in a TypeSet.
-class LTypeBarrierO : public LInstructionHelper<0, 1, 1>
-{
-  public:
-    LIR_HEADER(TypeBarrierO)
-
-    LTypeBarrierO(const LAllocation& obj, const LDefinition& temp) {
-        setOperand(0, obj);
-        setTemp(0, temp);
-    }
-    const MTypeBarrier* mir() const {
-        return mir_->toTypeBarrier();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Guard that a value is in a TypeSet.
-class LMonitorTypes : public LInstructionHelper<0, BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(MonitorTypes)
-
-    explicit LMonitorTypes(const LDefinition& temp) {
-        setTemp(0, temp);
-    }
-
-    static const size_t Input = 0;
-
-    const MMonitorTypes* mir() const {
-        return mir_->toMonitorTypes();
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Generational write barrier used when writing an object to another object.
-class LPostWriteBarrierO : public LInstructionHelper<0, 2, 1>
-{
-  public:
-    LIR_HEADER(PostWriteBarrierO)
-
-    LPostWriteBarrierO(const LAllocation& obj, const LAllocation& value,
-                       const LDefinition& temp) {
-        setOperand(0, obj);
-        setOperand(1, value);
-        setTemp(0, temp);
-    }
-
-    const MPostWriteBarrier* mir() const {
-        return mir_->toPostWriteBarrier();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Generational write barrier used when writing a value to another object.
-class LPostWriteBarrierV : public LInstructionHelper<0, 1 + BOX_PIECES, 1>
-{
-  public:
-    LIR_HEADER(PostWriteBarrierV)
-
-    LPostWriteBarrierV(const LAllocation& obj, const LDefinition& temp) {
-        setOperand(0, obj);
-        setTemp(0, temp);
-    }
-
-    static const size_t Input = 1;
-
-    const MPostWriteBarrier* mir() const {
-        return mir_->toPostWriteBarrier();
-    }
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-};
-
-// Guard against an object's identity.
-class LGuardObjectIdentity : public LInstructionHelper<0, 2, 0>
-{
-  public:
-    LIR_HEADER(GuardObjectIdentity)
-
-    explicit LGuardObjectIdentity(const LAllocation& in, const LAllocation& expected) {
-        setOperand(0, in);
-        setOperand(1, expected);
-    }
-    const LAllocation* input() {
-        return getOperand(0);
-    }
-    const LAllocation* expected() {
-        return getOperand(1);
-    }
-    const MGuardObjectIdentity* mir() const {
-        return mir_->toGuardObjectIdentity();
-    }
-};
-
-// Guard against an object's class.
-class LGuardClass : public LInstructionHelper<0, 1, 1>
-{
-  public:
-    LIR_HEADER(GuardClass)
-
-    LGuardClass(const LAllocation& in, const LDefinition& temp) {
-        setOperand(0, in);
-        setTemp(0, temp);
-    }
-    const MGuardClass* mir() const {
-        return mir_->toGuardClass();
-    }
-    const LDefinition* tempInt() {
-        return getTemp(0);
-    }
-};
-
-class LIn : public LCallInstructionHelper<1, BOX_PIECES+1, 0>
-{
-  public:
-    LIR_HEADER(In)
-    explicit LIn(const LAllocation& rhs) {
-        setOperand(RHS, rhs);
-    }
-
-    const LAllocation* lhs() {
-        return getOperand(LHS);
-    }
-    const LAllocation* rhs() {
-        return getOperand(RHS);
-    }
-
-    static const size_t LHS = 0;
-    static const size_t RHS = BOX_PIECES;
-};
-
-class LInstanceOfO : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(InstanceOfO)
-    explicit LInstanceOfO(const LAllocation& lhs) {
-        setOperand(0, lhs);
-    }
-
-    MInstanceOf* mir() const {
-        return mir_->toInstanceOf();
-    }
-
-    const LAllocation* lhs() {
-        return getOperand(0);
-    }
-};
-
-class LInstanceOfV : public LInstructionHelper<1, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(InstanceOfV)
-    LInstanceOfV() {
-    }
-
-    MInstanceOf* mir() const {
-        return mir_->toInstanceOf();
-    }
-
-    const LAllocation* lhs() {
-        return getOperand(LHS);
-    }
-
-    static const size_t LHS = 0;
-};
-
-class LCallInstanceOf : public LCallInstructionHelper<1, BOX_PIECES+1, 0>
-{
-  public:
-    LIR_HEADER(CallInstanceOf)
-    explicit LCallInstanceOf(const LAllocation& rhs) {
-        setOperand(RHS, rhs);
-    }
-
-    const LDefinition* output() {
-        return this->getDef(0);
-    }
-    const LAllocation* lhs() {
-        return getOperand(LHS);
-    }
-    const LAllocation* rhs() {
-        return getOperand(RHS);
-    }
-
-    static const size_t LHS = 0;
-    static const size_t RHS = BOX_PIECES;
-};
-
-class LIsCallable : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(IsCallable);
-    explicit LIsCallable(const LAllocation& object) {
-        setOperand(0, object);
-    }
-
-    const LAllocation* object() {
-        return getOperand(0);
-    }
-    MIsCallable* mir() const {
-        return mir_->toIsCallable();
-    }
-};
-
-class LIsObject : public LInstructionHelper<1, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(IsObject);
-    static const size_t Input = 0;
-    MIsObject* mir() const {
-        return mir_->toIsObject();
-    }
-};
-
-class LIsObjectAndBranch : public LControlInstructionHelper<2, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(IsObjectAndBranch)
-
-    LIsObjectAndBranch(MBasicBlock* ifTrue, MBasicBlock* ifFalse) {
-        setSuccessor(0, ifTrue);
-        setSuccessor(1, ifFalse);
-    }
-
-    static const size_t Input = 0;
-
-    MBasicBlock* ifTrue() const {
-        return getSuccessor(0);
-    }
-    MBasicBlock* ifFalse() const {
-        return getSuccessor(1);
-    }
-};
-
-class LHasClass : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(HasClass);
-    explicit LHasClass(const LAllocation& lhs) {
-        setOperand(0, lhs);
-    }
-
-    const LAllocation* lhs() {
-        return getOperand(0);
-    }
-    MHasClass* mir() const {
-        return mir_->toHasClass();
-    }
-};
-
-class LAsmJSLoadHeap : public LInstructionHelper<1, 1, 0>
-{
-  public:
-    LIR_HEADER(AsmJSLoadHeap);
-    explicit LAsmJSLoadHeap(const LAllocation& ptr) {
-        setOperand(0, ptr);
-    }
-    MAsmJSLoadHeap* mir() const {
-        return mir_->toAsmJSLoadHeap();
-    }
-    const LAllocation* ptr() {
-        return getOperand(0);
-    }
-};
-
-class LAsmJSStoreHeap : public LInstructionHelper<0, 2, 0>
-{
-  public:
-    LIR_HEADER(AsmJSStoreHeap);
-    LAsmJSStoreHeap(const LAllocation& ptr, const LAllocation& value) {
-        setOperand(0, ptr);
-        setOperand(1, value);
-    }
-    MAsmJSStoreHeap* mir() const {
-        return mir_->toAsmJSStoreHeap();
-    }
-    const LAllocation* ptr() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-};
-
-class LAsmJSCompareExchangeHeap : public LInstructionHelper<1, 3, 1>
-{
-  public:
-    LIR_HEADER(AsmJSCompareExchangeHeap);
-
-    LAsmJSCompareExchangeHeap(const LAllocation& ptr, const LAllocation& oldValue,
-                              const LAllocation& newValue)
-    {
-        setOperand(0, ptr);
-        setOperand(1, oldValue);
-        setOperand(2, newValue);
-        setTemp(0, LDefinition::BogusTemp());
-    }
-
-    const LAllocation* ptr() {
-        return getOperand(0);
-    }
-    const LAllocation* oldValue() {
-        return getOperand(1);
-    }
-    const LAllocation* newValue() {
-        return getOperand(2);
-    }
-    const LDefinition* addrTemp() {
-        return getTemp(0);
-    }
-
-    void setAddrTemp(const LDefinition& addrTemp) {
-        setTemp(0, addrTemp);
-    }
-
-    MAsmJSCompareExchangeHeap* mir() const {
-        return mir_->toAsmJSCompareExchangeHeap();
-    }
-};
-
-class LAsmJSAtomicExchangeHeap : public LInstructionHelper<1, 2, 1>
-{
-  public:
-    LIR_HEADER(AsmJSAtomicExchangeHeap);
-
-    LAsmJSAtomicExchangeHeap(const LAllocation& ptr, const LAllocation& value)
-    {
-        setOperand(0, ptr);
-        setOperand(1, value);
-        setTemp(0, LDefinition::BogusTemp());
-    }
-
-    const LAllocation* ptr() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-    const LDefinition* addrTemp() {
-        return getTemp(0);
-    }
-
-    void setAddrTemp(const LDefinition& addrTemp) {
-        setTemp(0, addrTemp);
-    }
-
-    MAsmJSAtomicExchangeHeap* mir() const {
-        return mir_->toAsmJSAtomicExchangeHeap();
-    }
-};
-
-class LAsmJSAtomicBinopHeap : public LInstructionHelper<1, 2, 2>
-{
-  public:
-    LIR_HEADER(AsmJSAtomicBinopHeap);
-
-    static const int32_t valueOp = 1;
-
-    LAsmJSAtomicBinopHeap(const LAllocation& ptr, const LAllocation& value,
-                          const LDefinition& temp)
-    {
-        setOperand(0, ptr);
-        setOperand(1, value);
-        setTemp(0, temp);
-        setTemp(1, LDefinition::BogusTemp());
-    }
-    const LAllocation* ptr() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        MOZ_ASSERT(valueOp == 1);
-        return getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    const LDefinition* addrTemp() {
-        return getTemp(1);
-    }
-
-    void setAddrTemp(const LDefinition& addrTemp) {
-        setTemp(1, addrTemp);
-    }
-
-    MAsmJSAtomicBinopHeap* mir() const {
-        return mir_->toAsmJSAtomicBinopHeap();
-    }
-};
-
-// Atomic binary operation where the result is discarded.
-class LAsmJSAtomicBinopHeapForEffect : public LInstructionHelper<0, 2, 1>
-{
-  public:
-    LIR_HEADER(AsmJSAtomicBinopHeapForEffect);
-    LAsmJSAtomicBinopHeapForEffect(const LAllocation& ptr, const LAllocation& value)
-    {
-        setOperand(0, ptr);
-        setOperand(1, value);
-        setTemp(0, LDefinition::BogusTemp());
-    }
-    const LAllocation* ptr() {
-        return getOperand(0);
-    }
-    const LAllocation* value() {
-        return getOperand(1);
-    }
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    const LDefinition* addrTemp() {
-        return getTemp(0);
-    }
-
-    void setAddrTemp(const LDefinition& addrTemp) {
-        setTemp(0, addrTemp);
-    }
-
-    MAsmJSAtomicBinopHeap* mir() const {
-        return mir_->toAsmJSAtomicBinopHeap();
-    }
-};
-
-class LAsmJSLoadGlobalVar : public LInstructionHelper<1, 0, 0>
-{
-  public:
-    LIR_HEADER(AsmJSLoadGlobalVar);
-    MAsmJSLoadGlobalVar* mir() const {
-        return mir_->toAsmJSLoadGlobalVar();
-    }
-};
-
-class LAsmJSStoreGlobalVar : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(AsmJSStoreGlobalVar);
-    explicit LAsmJSStoreGlobalVar(const LAllocation& value) {
-        setOperand(0, value);
-    }
-    MAsmJSStoreGlobalVar* mir() const {
-        return mir_->toAsmJSStoreGlobalVar();
-    }
-    const LAllocation* value() {
-        return getOperand(0);
-    }
-};
-
-class LAsmJSLoadFFIFunc : public LInstructionHelper<1, 0, 0>
-{
-  public:
-    LIR_HEADER(AsmJSLoadFFIFunc);
-    MAsmJSLoadFFIFunc* mir() const {
-        return mir_->toAsmJSLoadFFIFunc();
-    }
-};
-
-class LAsmJSParameter : public LInstructionHelper<1, 0, 0>
-{
-  public:
-    LIR_HEADER(AsmJSParameter);
-};
-
-class LAsmJSReturn : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(AsmJSReturn);
-};
-
-class LAsmJSVoidReturn : public LInstructionHelper<0, 0, 0>
-{
-  public:
-    LIR_HEADER(AsmJSVoidReturn);
-};
-
-class LAsmJSPassStackArg : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(AsmJSPassStackArg);
-    explicit LAsmJSPassStackArg(const LAllocation& arg) {
-        setOperand(0, arg);
-    }
-    MAsmJSPassStackArg* mir() const {
-        return mirRaw()->toAsmJSPassStackArg();
-    }
-    const LAllocation* arg() {
-        return getOperand(0);
-    }
-};
-
-class LAsmJSCall final : public LInstruction
-{
-    LAllocation* operands_;
-    uint32_t numOperands_;
-    LDefinition def_;
-
-  public:
-    LIR_HEADER(AsmJSCall);
-
-    LAsmJSCall(LAllocation* operands, uint32_t numOperands)
-      : operands_(operands),
-        numOperands_(numOperands),
-        def_(LDefinition::BogusTemp())
-    {}
-
-    MAsmJSCall* mir() const {
-        return mir_->toAsmJSCall();
-    }
-
-    bool isCall() const {
-        return true;
-    }
-
-    // LInstruction interface
-    size_t numDefs() const {
-        return def_.isBogusTemp() ? 0 : 1;
-    }
-    LDefinition* getDef(size_t index) {
-        MOZ_ASSERT(numDefs() == 1);
-        MOZ_ASSERT(index == 0);
-        return &def_;
-    }
-    void setDef(size_t index, const LDefinition& def) {
-        MOZ_ASSERT(index == 0);
-        def_ = def;
-    }
-    size_t numOperands() const {
-        return numOperands_;
-    }
-    LAllocation* getOperand(size_t index) {
-        MOZ_ASSERT(index < numOperands_);
-        return &operands_[index];
-    }
-    void setOperand(size_t index, const LAllocation& a) {
-        MOZ_ASSERT(index < numOperands_);
-        operands_[index] = a;
-    }
-    size_t numTemps() const {
-        return 0;
-    }
-    LDefinition* getTemp(size_t index) {
-        MOZ_CRASH("no temps");
-    }
-    void setTemp(size_t index, const LDefinition& a) {
-        MOZ_CRASH("no temps");
-    }
-    size_t numSuccessors() const {
-        return 0;
-    }
-    MBasicBlock* getSuccessor(size_t i) const {
-        MOZ_CRASH("no successors");
-    }
-    void setSuccessor(size_t i, MBasicBlock*) {
-        MOZ_CRASH("no successors");
-    }
-};
-
-class LAssertRangeI : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(AssertRangeI)
-
-    explicit LAssertRangeI(const LAllocation& input) {
-        setOperand(0, input);
-    }
-
-    const LAllocation* input() {
-        return getOperand(0);
-    }
-
-    MAssertRange* mir() {
-        return mir_->toAssertRange();
-    }
-    const Range* range() {
-        return mir()->assertedRange();
-    }
-};
-
-class LAssertRangeD : public LInstructionHelper<0, 1, 1>
-{
-  public:
-    LIR_HEADER(AssertRangeD)
-
-    LAssertRangeD(const LAllocation& input, const LDefinition& temp) {
-        setOperand(0, input);
-        setTemp(0, temp);
-    }
-
-    const LAllocation* input() {
-        return getOperand(0);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MAssertRange* mir() {
-        return mir_->toAssertRange();
-    }
-    const Range* range() {
-        return mir()->assertedRange();
-    }
-};
-
-class LAssertRangeF : public LInstructionHelper<0, 1, 2>
-{
-  public:
-    LIR_HEADER(AssertRangeF)
-    LAssertRangeF(const LAllocation& input, const LDefinition& temp, const LDefinition& armtemp) {
-        setOperand(0, input);
-        setTemp(0, temp);
-        setTemp(1, armtemp);
-    }
-    const LDefinition* armtemp() {
-        return getTemp(1);
-    }
-
-    const LAllocation* input() {
-        return getOperand(0);
-    }
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-
-    MAssertRange* mir() {
-        return mir_->toAssertRange();
-    }
-    const Range* range() {
-        return mir()->assertedRange();
-    }
-};
-
-class LAssertRangeV : public LInstructionHelper<0, BOX_PIECES, 3>
-{
-  public:
-    LIR_HEADER(AssertRangeV)
-
-    LAssertRangeV(const LDefinition& temp, const LDefinition& floatTemp1,
-                  const LDefinition& floatTemp2)
-    {
-        setTemp(0, temp);
-        setTemp(1, floatTemp1);
-        setTemp(2, floatTemp2);
-    }
-
-    static const size_t Input = 0;
-
-    const LDefinition* temp() {
-        return getTemp(0);
-    }
-    const LDefinition* floatTemp1() {
-        return getTemp(1);
-    }
-    const LDefinition* floatTemp2() {
-        return getTemp(2);
-    }
-
-    MAssertRange* mir() {
-        return mir_->toAssertRange();
-    }
-    const Range* range() {
-        return mir()->assertedRange();
-    }
-};
-
-class LAssertResultT : public LInstructionHelper<0, 1, 0>
-{
-  public:
-    LIR_HEADER(AssertResultT)
-
-    explicit LAssertResultT(const LAllocation& input) {
-        setOperand(0, input);
-    }
-
-    const LAllocation* input() {
-        return getOperand(0);
-    }
-};
-
-class LAssertResultV : public LInstructionHelper<0, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(AssertResultV)
-
-    static const size_t Input = 0;
-};
-
-class LRecompileCheck : public LInstructionHelper<0, 0, 1>
-{
-  public:
-    LIR_HEADER(RecompileCheck)
-
-    explicit LRecompileCheck(const LDefinition& scratch) {
-        setTemp(0, scratch);
-    }
-
-    const LDefinition* scratch() {
-        return getTemp(0);
-    }
-    MRecompileCheck* mir() {
-        return mir_->toRecompileCheck();
-    }
-};
-
-class LLexicalCheck : public LInstructionHelper<0, BOX_PIECES, 0>
-{
-  public:
-    LIR_HEADER(LexicalCheck)
-
-    MLexicalCheck* mir() {
-        return mir_->toLexicalCheck();
-    }
-
-    static const size_t Input = 0;
-};
-
-class LThrowUninitializedLexical : public LCallInstructionHelper<0, 0, 0>
-{
-  public:
-    LIR_HEADER(ThrowUninitializedLexical)
-
-    MLexicalCheck* mir() {
-        return mir_->toLexicalCheck();
-    }
-};
-
-class LMemoryBarrier : public LInstructionHelper<0, 0, 0>
-{
-  private:
-    const MemoryBarrierBits type_;
-
-  public:
-    LIR_HEADER(MemoryBarrier)
-
-    // The parameter 'type' is a bitwise 'or' of the barrier types needed,
-    // see AtomicOp.h.
-    explicit LMemoryBarrier(MemoryBarrierBits type) : type_(type)
-    {
-        MOZ_ASSERT((type_ & ~MembarAllbits) == MembarNobits);
-    }
-
-    MemoryBarrierBits type() const {
-        return type_;
-    }
-
-    const MMemoryBarrier* mir() const {
-        return mir_->toMemoryBarrier();
-    }
-};
-
-class LDebugger : public LCallInstructionHelper<0, 0, 2>
-{
-  public:
-    LIR_HEADER(Debugger)
-
-    LDebugger(const LDefinition& temp1, const LDefinition& temp2) {
-        setTemp(0, temp1);
-        setTemp(1, temp2);
-    }
-};
-
-class LNewTarget : public LInstructionHelper<BOX_PIECES, 0, 0>
-{
-  public:
-    LIR_HEADER(NewTarget)
-};
-
-class LArrowNewTarget : public LInstructionHelper<BOX_PIECES, 1, 0>
-{
-  public:
-    explicit LArrowNewTarget(const LAllocation& callee) {
-        setOperand(0, callee);
-    }
-
-    LIR_HEADER(ArrowNewTarget)
-
-    const LAllocation* callee() {
-        return getOperand(0);
-    }
-};
-
-} // namespace jit
-} // namespace js
-
-#endif /* jit_LIR_Common_h */
--- a/js/src/jit/LIR.h
+++ b/js/src/jit/LIR.h
@@ -1810,17 +1810,17 @@ LAllocation::toRegister() const
     if (isFloatReg())
         return AnyRegister(toFloatReg()->reg());
     return AnyRegister(toGeneralReg()->reg());
 }
 
 } // namespace jit
 } // namespace js
 
-#include "jit/LIR-Common.h"
+#include "jit/shared/LIR-shared.h"
 #if defined(JS_CODEGEN_X86) || defined(JS_CODEGEN_X64)
 # if defined(JS_CODEGEN_X86)
 #  include "jit/x86/LIR-x86.h"
 # elif defined(JS_CODEGEN_X64)
 #  include "jit/x64/LIR-x64.h"
 # endif
 # include "jit/x86-shared/LIR-x86-shared.h"
 #elif defined(JS_CODEGEN_ARM)
new file mode 100644
--- /dev/null
+++ b/js/src/jit/shared/LIR-shared.h
@@ -0,0 +1,7124 @@
+/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
+ * vim: set ts=8 sts=4 et sw=4 tw=99:
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+#ifndef jit_shared_LIR_shared_h
+#define jit_shared_LIR_shared_h
+
+#include "jsutil.h"
+
+#include "jit/AtomicOp.h"
+#include "jit/shared/Assembler-shared.h"
+
+// This file declares LIR instructions that are common to every platform.
+
+namespace js {
+namespace jit {
+
+class Range;
+
+template <size_t Temps, size_t ExtraUses = 0>
+class LBinaryMath : public LInstructionHelper<1, 2 + ExtraUses, Temps>
+{
+  public:
+    const LAllocation* lhs() {
+        return this->getOperand(0);
+    }
+    const LAllocation* rhs() {
+        return this->getOperand(1);
+    }
+};
+
+// An LOsiPoint captures a snapshot after a call and ensures enough space to
+// patch in a call to the invalidation mechanism.
+//
+// Note: LSafepoints are 1:1 with LOsiPoints, so it holds a reference to the
+// corresponding LSafepoint to inform it of the LOsiPoint's masm offset when it
+// gets CG'd.
+class LOsiPoint : public LInstructionHelper<0, 0, 0>
+{
+    LSafepoint* safepoint_;
+
+  public:
+    LOsiPoint(LSafepoint* safepoint, LSnapshot* snapshot)
+      : safepoint_(safepoint)
+    {
+        MOZ_ASSERT(safepoint && snapshot);
+        assignSnapshot(snapshot);
+    }
+
+    LSafepoint* associatedSafepoint() {
+        return safepoint_;
+    }
+
+    LIR_HEADER(OsiPoint)
+};
+
+class LMove
+{
+    LAllocation from_;
+    LAllocation to_;
+    LDefinition::Type type_;
+
+  public:
+    LMove(LAllocation from, LAllocation to, LDefinition::Type type)
+      : from_(from),
+        to_(to),
+        type_(type)
+    { }
+
+    LAllocation from() const {
+        return from_;
+    }
+    LAllocation to() const {
+        return to_;
+    }
+    LDefinition::Type type() const {
+        return type_;
+    }
+};
+
+class LMoveGroup : public LInstructionHelper<0, 0, 0>
+{
+    js::Vector<LMove, 2, JitAllocPolicy> moves_;
+
+#ifdef JS_CODEGEN_X86
+    // Optional general register available for use when executing moves.
+    LAllocation scratchRegister_;
+#endif
+
+    explicit LMoveGroup(TempAllocator& alloc)
+      : moves_(alloc)
+    { }
+
+  public:
+    LIR_HEADER(MoveGroup)
+
+    static LMoveGroup* New(TempAllocator& alloc) {
+        return new(alloc) LMoveGroup(alloc);
+    }
+
+    void printOperands(GenericPrinter& out);
+
+    // Add a move which takes place simultaneously with all others in the group.
+    bool add(LAllocation from, LAllocation to, LDefinition::Type type);
+
+    // Add a move which takes place after existing moves in the group.
+    bool addAfter(LAllocation from, LAllocation to, LDefinition::Type type);
+
+    size_t numMoves() const {
+        return moves_.length();
+    }
+    const LMove& getMove(size_t i) const {
+        return moves_[i];
+    }
+
+#ifdef JS_CODEGEN_X86
+    void setScratchRegister(Register reg) {
+        scratchRegister_ = LGeneralReg(reg);
+    }
+    LAllocation maybeScratchRegister() {
+        return scratchRegister_;
+    }
+#endif
+
+    bool uses(Register reg) {
+        for (size_t i = 0; i < numMoves(); i++) {
+            LMove move = getMove(i);
+            if (move.from() == LGeneralReg(reg) || move.to() == LGeneralReg(reg))
+                return true;
+        }
+        return false;
+    }
+};
+
+
+// Constructs a SIMD object (value type) based on the MIRType of its input.
+class LSimdBox : public LInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(SimdBox)
+
+    explicit LSimdBox(const LAllocation& simd, const LDefinition& temp)
+    {
+        setOperand(0, simd);
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MSimdBox* mir() const {
+        return mir_->toSimdBox();
+    }
+};
+
+class LSimdUnbox : public LInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(SimdUnbox)
+
+    LSimdUnbox(const LAllocation& obj, const LDefinition& temp)
+    {
+        setOperand(0, obj);
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MSimdUnbox* mir() const {
+        return mir_->toSimdUnbox();
+    }
+};
+
+// Constructs a SIMD value with 4 equal components (e.g. int32x4, float32x4).
+class LSimdSplatX4 : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(SimdSplatX4)
+    explicit LSimdSplatX4(const LAllocation& v)
+    {
+        setOperand(0, v);
+    }
+
+    MSimdSplatX4* mir() const {
+        return mir_->toSimdSplatX4();
+    }
+};
+
+// Reinterpret the bits of a SIMD value with a different type.
+class LSimdReinterpretCast : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(SimdReinterpretCast)
+    explicit LSimdReinterpretCast(const LAllocation& v)
+    {
+        setOperand(0, v);
+    }
+
+    MSimdReinterpretCast* mir() const {
+        return mir_->toSimdReinterpretCast();
+    }
+};
+
+class LSimdExtractElementBase : public LInstructionHelper<1, 1, 0>
+{
+  protected:
+    explicit LSimdExtractElementBase(const LAllocation& base) {
+        setOperand(0, base);
+    }
+
+  public:
+    const LAllocation* getBase() {
+        return getOperand(0);
+    }
+    SimdLane lane() const {
+        return mir_->toSimdExtractElement()->lane();
+    }
+    const char* extraName() const {
+        switch (lane()) {
+          case LaneX: return "lane x";
+          case LaneY: return "lane y";
+          case LaneZ: return "lane z";
+          case LaneW: return "lane w";
+        }
+        return "unknown lane";
+    }
+};
+
+// Extracts an element from a given SIMD int32x4 lane.
+class LSimdExtractElementI : public LSimdExtractElementBase
+{
+  public:
+    LIR_HEADER(SimdExtractElementI);
+    explicit LSimdExtractElementI(const LAllocation& base)
+      : LSimdExtractElementBase(base)
+    {}
+};
+// Extracts an element from a given SIMD float32x4 lane.
+class LSimdExtractElementF : public LSimdExtractElementBase
+{
+  public:
+    LIR_HEADER(SimdExtractElementF);
+    explicit LSimdExtractElementF(const LAllocation& base)
+      : LSimdExtractElementBase(base)
+    {}
+};
+
+class LSimdInsertElementBase : public LInstructionHelper<1, 2, 0>
+{
+  protected:
+    LSimdInsertElementBase(const LAllocation& vec, const LAllocation& val)
+    {
+        setOperand(0, vec);
+        setOperand(1, val);
+    }
+
+  public:
+    const LAllocation* vector() {
+        return getOperand(0);
+    }
+    const LAllocation* value() {
+        return getOperand(1);
+    }
+    SimdLane lane() const {
+        return mir_->toSimdInsertElement()->lane();
+    }
+    const char* extraName() const {
+        return MSimdInsertElement::LaneName(lane());
+    }
+};
+
+// Replace an element from a given SIMD int32x4 lane with a given value.
+class LSimdInsertElementI : public LSimdInsertElementBase
+{
+  public:
+    LIR_HEADER(SimdInsertElementI);
+    LSimdInsertElementI(const LAllocation& vec, const LAllocation& val)
+      : LSimdInsertElementBase(vec, val)
+    {}
+};
+
+// Replace an element from a given SIMD float32x4 lane with a given value.
+class LSimdInsertElementF : public LSimdInsertElementBase
+{
+  public:
+    LIR_HEADER(SimdInsertElementF);
+    LSimdInsertElementF(const LAllocation& vec, const LAllocation& val)
+      : LSimdInsertElementBase(vec, val)
+    {}
+};
+
+class LSimdSignMaskX4 : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(SimdSignMaskX4);
+
+    explicit LSimdSignMaskX4(const LAllocation& input) {
+        setOperand(0, input);
+    }
+};
+
+// Base class for both int32x4 and float32x4 shuffle instructions.
+class LSimdSwizzleBase : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    explicit LSimdSwizzleBase(const LAllocation& base)
+    {
+        setOperand(0, base);
+    }
+
+    const LAllocation* getBase() {
+        return getOperand(0);
+    }
+
+    uint32_t laneX() const { return mir_->toSimdSwizzle()->laneX(); }
+    uint32_t laneY() const { return mir_->toSimdSwizzle()->laneY(); }
+    uint32_t laneZ() const { return mir_->toSimdSwizzle()->laneZ(); }
+    uint32_t laneW() const { return mir_->toSimdSwizzle()->laneW(); }
+
+    bool lanesMatch(uint32_t x, uint32_t y, uint32_t z, uint32_t w) const {
+        return mir_->toSimdSwizzle()->lanesMatch(x, y, z, w);
+    }
+};
+
+// Shuffles a int32x4 into another int32x4 vector.
+class LSimdSwizzleI : public LSimdSwizzleBase
+{
+  public:
+    LIR_HEADER(SimdSwizzleI);
+    explicit LSimdSwizzleI(const LAllocation& base) : LSimdSwizzleBase(base)
+    {}
+};
+// Shuffles a float32x4 into another float32x4 vector.
+class LSimdSwizzleF : public LSimdSwizzleBase
+{
+  public:
+    LIR_HEADER(SimdSwizzleF);
+    explicit LSimdSwizzleF(const LAllocation& base) : LSimdSwizzleBase(base)
+    {}
+};
+
+class LSimdGeneralShuffleBase : public LVariadicInstruction<1, 1>
+{
+  public:
+    explicit LSimdGeneralShuffleBase(const LDefinition& temp) {
+        setTemp(0, temp);
+    }
+    const LAllocation* vector(unsigned i) {
+        MOZ_ASSERT(i < mir()->numVectors());
+        return getOperand(i);
+    }
+    const LAllocation* lane(unsigned i) {
+        MOZ_ASSERT(i < mir()->numLanes());
+        return getOperand(mir()->numVectors() + i);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+    MSimdGeneralShuffle* mir() const {
+        return mir_->toSimdGeneralShuffle();
+    }
+};
+
+class LSimdGeneralShuffleI : public LSimdGeneralShuffleBase
+{
+  public:
+    LIR_HEADER(SimdGeneralShuffleI);
+    explicit LSimdGeneralShuffleI(const LDefinition& temp)
+      : LSimdGeneralShuffleBase(temp)
+    {}
+};
+
+class LSimdGeneralShuffleF : public LSimdGeneralShuffleBase
+{
+  public:
+    LIR_HEADER(SimdGeneralShuffleF);
+    explicit LSimdGeneralShuffleF(const LDefinition& temp)
+      : LSimdGeneralShuffleBase(temp)
+    {}
+};
+
+// Base class for both int32x4 and float32x4 shuffle instructions.
+class LSimdShuffle : public LInstructionHelper<1, 2, 1>
+{
+  public:
+    LIR_HEADER(SimdShuffle);
+    LSimdShuffle()
+    {}
+
+    const LAllocation* lhs() {
+        return getOperand(0);
+    }
+    const LAllocation* rhs() {
+        return getOperand(1);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    uint32_t laneX() const { return mir_->toSimdShuffle()->laneX(); }
+    uint32_t laneY() const { return mir_->toSimdShuffle()->laneY(); }
+    uint32_t laneZ() const { return mir_->toSimdShuffle()->laneZ(); }
+    uint32_t laneW() const { return mir_->toSimdShuffle()->laneW(); }
+
+    bool lanesMatch(uint32_t x, uint32_t y, uint32_t z, uint32_t w) const {
+        return mir_->toSimdShuffle()->lanesMatch(x, y, z, w);
+    }
+};
+
+// Binary SIMD comparison operation between two SIMD operands
+class LSimdBinaryComp: public LInstructionHelper<1, 2, 0>
+{
+  protected:
+    LSimdBinaryComp() {}
+
+public:
+    const LAllocation* lhs() {
+        return getOperand(0);
+    }
+    const LAllocation* rhs() {
+        return getOperand(1);
+    }
+    MSimdBinaryComp::Operation operation() const {
+        return mir_->toSimdBinaryComp()->operation();
+    }
+    const char* extraName() const {
+        return MSimdBinaryComp::OperationName(operation());
+    }
+};
+
+// Binary SIMD comparison operation between two Int32x4 operands
+class LSimdBinaryCompIx4 : public LSimdBinaryComp
+{
+  public:
+    LIR_HEADER(SimdBinaryCompIx4);
+    LSimdBinaryCompIx4() : LSimdBinaryComp() {}
+};
+
+// Binary SIMD comparison operation between two Float32x4 operands
+class LSimdBinaryCompFx4 : public LSimdBinaryComp
+{
+  public:
+    LIR_HEADER(SimdBinaryCompFx4);
+    LSimdBinaryCompFx4() : LSimdBinaryComp() {}
+};
+
+// Binary SIMD arithmetic operation between two SIMD operands
+class LSimdBinaryArith : public LInstructionHelper<1, 2, 1>
+{
+  public:
+    LSimdBinaryArith() {}
+
+    const LAllocation* lhs() {
+        return this->getOperand(0);
+    }
+    const LAllocation* rhs() {
+        return this->getOperand(1);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MSimdBinaryArith::Operation operation() const {
+        return this->mir_->toSimdBinaryArith()->operation();
+    }
+    const char* extraName() const {
+        return MSimdBinaryArith::OperationName(operation());
+    }
+};
+
+// Binary SIMD arithmetic operation between two Int32x4 operands
+class LSimdBinaryArithIx4 : public LSimdBinaryArith
+{
+  public:
+    LIR_HEADER(SimdBinaryArithIx4);
+    LSimdBinaryArithIx4() : LSimdBinaryArith() {}
+};
+
+// Binary SIMD arithmetic operation between two Float32x4 operands
+class LSimdBinaryArithFx4 : public LSimdBinaryArith
+{
+  public:
+    LIR_HEADER(SimdBinaryArithFx4);
+    LSimdBinaryArithFx4() : LSimdBinaryArith() {}
+};
+
+// Unary SIMD arithmetic operation on a SIMD operand
+class LSimdUnaryArith : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    explicit LSimdUnaryArith(const LAllocation& in) {
+        setOperand(0, in);
+    }
+    MSimdUnaryArith::Operation operation() const {
+        return mir_->toSimdUnaryArith()->operation();
+    }
+};
+
+// Unary SIMD arithmetic operation on a Int32x4 operand
+class LSimdUnaryArithIx4 : public LSimdUnaryArith
+{
+  public:
+    LIR_HEADER(SimdUnaryArithIx4);
+    explicit LSimdUnaryArithIx4(const LAllocation& in) : LSimdUnaryArith(in) {}
+};
+
+// Unary SIMD arithmetic operation on a Float32x4 operand
+class LSimdUnaryArithFx4 : public LSimdUnaryArith
+{
+  public:
+    LIR_HEADER(SimdUnaryArithFx4);
+    explicit LSimdUnaryArithFx4(const LAllocation& in) : LSimdUnaryArith(in) {}
+};
+
+// Binary SIMD bitwise operation between two int32x4 or float32x4 operands
+class LSimdBinaryBitwiseX4 : public LInstructionHelper<1, 2, 0>
+{
+  public:
+    LIR_HEADER(SimdBinaryBitwiseX4);
+    const LAllocation* lhs() {
+        return getOperand(0);
+    }
+    const LAllocation* rhs() {
+        return getOperand(1);
+    }
+    MSimdBinaryBitwise::Operation operation() const {
+        return mir_->toSimdBinaryBitwise()->operation();
+    }
+    const char* extraName() const {
+        return MSimdBinaryBitwise::OperationName(operation());
+    }
+    MIRType type() const {
+        return mir_->type();
+    }
+};
+
+class LSimdShift : public LInstructionHelper<1, 2, 0>
+{
+  public:
+    LIR_HEADER(SimdShift)
+    LSimdShift(const LAllocation& vec, const LAllocation& val) {
+        setOperand(0, vec);
+        setOperand(1, val);
+    }
+    const LAllocation* vector() {
+        return getOperand(0);
+    }
+    const LAllocation* value() {
+        return getOperand(1);
+    }
+    MSimdShift::Operation operation() const {
+        return mir_->toSimdShift()->operation();
+    }
+    const char* extraName() const {
+        return MSimdShift::OperationName(operation());
+    }
+    MSimdShift* mir() const {
+        return mir_->toSimdShift();
+    }
+};
+
+// SIMD selection of lanes from two int32x4 or float32x4 arguments based on a
+// int32x4 argument.
+class LSimdSelect : public LInstructionHelper<1, 3, 1>
+{
+  public:
+    LIR_HEADER(SimdSelect);
+    const LAllocation* mask() {
+        return getOperand(0);
+    }
+    const LAllocation* lhs() {
+        return getOperand(1);
+    }
+    const LAllocation* rhs() {
+        return getOperand(2);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+    MSimdSelect* mir() const {
+        return mir_->toSimdSelect();
+    }
+};
+
+// Constant 32-bit integer.
+class LInteger : public LInstructionHelper<1, 0, 0>
+{
+    int32_t i32_;
+
+  public:
+    LIR_HEADER(Integer)
+
+    explicit LInteger(int32_t i32)
+      : i32_(i32)
+    { }
+
+    int32_t getValue() const {
+        return i32_;
+    }
+};
+
+// Constant pointer.
+class LPointer : public LInstructionHelper<1, 0, 0>
+{
+  public:
+    enum Kind {
+        GC_THING,
+        NON_GC_THING
+    };
+
+  private:
+    void* ptr_;
+    Kind kind_;
+
+  public:
+    LIR_HEADER(Pointer)
+
+    explicit LPointer(gc::Cell* ptr)
+      : ptr_(ptr), kind_(GC_THING)
+    { }
+
+    LPointer(void* ptr, Kind kind)
+      : ptr_(ptr), kind_(kind)
+    { }
+
+    void* ptr() const {
+        return ptr_;
+    }
+    Kind kind() const {
+        return kind_;
+    }
+    const char* extraName() const {
+        return kind_ == GC_THING ? "GC_THING" : "NON_GC_THING";
+    }
+
+    gc::Cell* gcptr() const {
+        MOZ_ASSERT(kind() == GC_THING);
+        return (gc::Cell*) ptr_;
+    }
+};
+
+// Constant double.
+class LDouble : public LInstructionHelper<1, 0, 0>
+{
+    double d_;
+  public:
+    LIR_HEADER(Double);
+
+    explicit LDouble(double d) : d_(d)
+    { }
+    double getDouble() const {
+        return d_;
+    }
+};
+
+// Constant float32.
+class LFloat32 : public LInstructionHelper<1, 0, 0>
+{
+    float f_;
+  public:
+    LIR_HEADER(Float32);
+
+    explicit LFloat32(float f)
+      : f_(f)
+    { }
+
+    float getFloat() const {
+        return f_;
+    }
+};
+
+// Constant SIMD int32x4
+class LInt32x4 : public LInstructionHelper<1, 0, 0>
+{
+  public:
+    LIR_HEADER(Int32x4);
+
+    explicit LInt32x4() {}
+    const SimdConstant& getValue() const { return mir_->toSimdConstant()->value(); }
+};
+
+// Constant SIMD float32x4
+class LFloat32x4 : public LInstructionHelper<1, 0, 0>
+{
+  public:
+    LIR_HEADER(Float32x4);
+
+    explicit LFloat32x4() {}
+    const SimdConstant& getValue() const { return mir_->toSimdConstant()->value(); }
+};
+
+// A constant Value.
+class LValue : public LInstructionHelper<BOX_PIECES, 0, 0>
+{
+    Value v_;
+
+  public:
+    LIR_HEADER(Value)
+
+    explicit LValue(const Value& v)
+      : v_(v)
+    { }
+
+    Value value() const {
+        return v_;
+    }
+};
+
+// Clone an object literal such as we are not modifying the object contained in
+// the sources.
+class LCloneLiteral : public LCallInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(CloneLiteral)
+
+    explicit LCloneLiteral(const LAllocation& obj)
+    {
+        setOperand(0, obj);
+    }
+
+    const LAllocation* getObjectLiteral() {
+        return getOperand(0);
+    }
+
+    MCloneLiteral* mir() const {
+        return mir_->toCloneLiteral();
+    }
+};
+
+// Formal argument for a function, returning a box. Formal arguments are
+// initially read from the stack.
+class LParameter : public LInstructionHelper<BOX_PIECES, 0, 0>
+{
+  public:
+    LIR_HEADER(Parameter)
+};
+
+// Stack offset for a word-sized immutable input value to a frame.
+class LCallee : public LInstructionHelper<1, 0, 0>
+{
+  public:
+    LIR_HEADER(Callee)
+};
+
+class LIsConstructing : public LInstructionHelper<1, 0, 0>
+{
+  public:
+    LIR_HEADER(IsConstructing)
+};
+
+// Base class for control instructions (goto, branch, etc.)
+template <size_t Succs, size_t Operands, size_t Temps>
+class LControlInstructionHelper : public LInstructionHelper<0, Operands, Temps> {
+
+    mozilla::Array<MBasicBlock*, Succs> successors_;
+
+  public:
+    virtual size_t numSuccessors() const final override { return Succs; }
+
+    virtual MBasicBlock* getSuccessor(size_t i) const final override {
+        return successors_[i];
+    }
+
+    virtual void setSuccessor(size_t i, MBasicBlock* successor) final override {
+        successors_[i] = successor;
+    }
+};
+
+// Jumps to the start of a basic block.
+class LGoto : public LControlInstructionHelper<1, 0, 0>
+{
+  public:
+    LIR_HEADER(Goto)
+
+    explicit LGoto(MBasicBlock* block)
+    {
+         setSuccessor(0, block);
+    }
+
+    MBasicBlock* target() const {
+        return getSuccessor(0);
+    }
+};
+
+class LNewArray : public LInstructionHelper<1, 0, 1>
+{
+  public:
+    LIR_HEADER(NewArray)
+
+    explicit LNewArray(const LDefinition& temp) {
+        setTemp(0, temp);
+    }
+
+    const char* extraName() const {
+        return mir()->shouldUseVM() ? "VMCall" : nullptr;
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MNewArray* mir() const {
+        return mir_->toNewArray();
+    }
+};
+
+class LNewArrayCopyOnWrite : public LInstructionHelper<1, 0, 1>
+{
+  public:
+    LIR_HEADER(NewArrayCopyOnWrite)
+
+    explicit LNewArrayCopyOnWrite(const LDefinition& temp) {
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MNewArrayCopyOnWrite* mir() const {
+        return mir_->toNewArrayCopyOnWrite();
+    }
+};
+
+class LNewArrayDynamicLength : public LInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(NewArrayDynamicLength)
+
+    explicit LNewArrayDynamicLength(const LAllocation& length, const LDefinition& temp) {
+        setOperand(0, length);
+        setTemp(0, temp);
+    }
+
+    const LAllocation* length() {
+        return getOperand(0);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MNewArrayDynamicLength* mir() const {
+        return mir_->toNewArrayDynamicLength();
+    }
+};
+
+class LNewObject : public LInstructionHelper<1, 0, 1>
+{
+  public:
+    LIR_HEADER(NewObject)
+
+    explicit LNewObject(const LDefinition& temp) {
+        setTemp(0, temp);
+    }
+
+    const char* extraName() const {
+        return mir()->shouldUseVM() ? "VMCall" : nullptr;
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MNewObject* mir() const {
+        return mir_->toNewObject();
+    }
+};
+
+class LNewTypedObject : public LInstructionHelper<1, 0, 1>
+{
+  public:
+    LIR_HEADER(NewTypedObject)
+
+    explicit LNewTypedObject(const LDefinition& temp) {
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MNewTypedObject* mir() const {
+        return mir_->toNewTypedObject();
+    }
+};
+
+// Allocates a new DeclEnvObject.
+//
+// This instruction generates two possible instruction sets:
+//   (1) An inline allocation of the call object is attempted.
+//   (2) Otherwise, a callVM create a new object.
+//
+class LNewDeclEnvObject : public LInstructionHelper<1, 0, 1>
+{
+  public:
+    LIR_HEADER(NewDeclEnvObject);
+
+    explicit LNewDeclEnvObject(const LDefinition& temp) {
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MNewDeclEnvObject* mir() const {
+        return mir_->toNewDeclEnvObject();
+    }
+};
+
+// Allocates a new CallObject.
+//
+// This instruction generates two possible instruction sets:
+//   (1) If the call object is extensible, this is a callVM to create the
+//       call object.
+//   (2) Otherwise, an inline allocation of the call object is attempted.
+//
+class LNewCallObject : public LInstructionHelper<1, 0, 1>
+{
+  public:
+    LIR_HEADER(NewCallObject)
+
+    explicit LNewCallObject(const LDefinition& temp) {
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+
+    MNewCallObject* mir() const {
+        return mir_->toNewCallObject();
+    }
+};
+
+// Allocates a new CallObject with singleton type.
+//
+// This instruction generates two possible instruction sets:
+//   (1) If the call object is extensible, this is a callVM to create the
+//       call object.
+//   (2) Otherwise, an inline allocation of the call object is attempted.
+//
+class LNewSingletonCallObject : public LInstructionHelper<1, 0, 1>
+{
+  public:
+    LIR_HEADER(NewSingletonCallObject)
+
+    explicit LNewSingletonCallObject(const LDefinition& temp) {
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MNewCallObjectBase* mir() const {
+        MOZ_ASSERT(mir_->isNewCallObject() || mir_->isNewRunOnceCallObject());
+        return static_cast<MNewCallObjectBase*>(mir_);
+    }
+};
+
+class LNewDerivedTypedObject : public LCallInstructionHelper<1, 3, 0>
+{
+  public:
+    LIR_HEADER(NewDerivedTypedObject);
+
+    LNewDerivedTypedObject(const LAllocation& type,
+                           const LAllocation& owner,
+                           const LAllocation& offset) {
+        setOperand(0, type);
+        setOperand(1, owner);
+        setOperand(2, offset);
+    }
+
+    const LAllocation* type() {
+        return getOperand(0);
+    }
+
+    const LAllocation* owner() {
+        return getOperand(1);
+    }
+
+    const LAllocation* offset() {
+        return getOperand(2);
+    }
+};
+
+class LNewStringObject : public LInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(NewStringObject)
+
+    LNewStringObject(const LAllocation& input, const LDefinition& temp) {
+        setOperand(0, input);
+        setTemp(0, temp);
+    }
+
+    const LAllocation* input() {
+        return getOperand(0);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+    MNewStringObject* mir() const {
+        return mir_->toNewStringObject();
+    }
+};
+
+class LInitElem : public LCallInstructionHelper<0, 1 + 2*BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(InitElem)
+
+    explicit LInitElem(const LAllocation& object) {
+        setOperand(0, object);
+    }
+
+    static const size_t IdIndex = 1;
+    static const size_t ValueIndex = 1 + BOX_PIECES;
+
+    const LAllocation* getObject() {
+        return getOperand(0);
+    }
+    MInitElem* mir() const {
+        return mir_->toInitElem();
+    }
+};
+
+class LInitElemGetterSetter : public LCallInstructionHelper<0, 2 + BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(InitElemGetterSetter)
+
+    LInitElemGetterSetter(const LAllocation& object, const LAllocation& value) {
+        setOperand(0, object);
+        setOperand(1, value);
+    }
+
+    static const size_t IdIndex = 2;
+
+    const LAllocation* object() {
+        return getOperand(0);
+    }
+    const LAllocation* value() {
+        return getOperand(1);
+    }
+    MInitElemGetterSetter* mir() const {
+        return mir_->toInitElemGetterSetter();
+    }
+};
+
+// Takes in an Object and a Value.
+class LMutateProto : public LCallInstructionHelper<0, 1 + BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(MutateProto)
+
+    explicit LMutateProto(const LAllocation& object) {
+        setOperand(0, object);
+    }
+
+    static const size_t ValueIndex = 1;
+
+    const LAllocation* getObject() {
+        return getOperand(0);
+    }
+    const LAllocation* getValue() {
+        return getOperand(1);
+    }
+};
+
+// Takes in an Object and a Value.
+class LInitProp : public LCallInstructionHelper<0, 1 + BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(InitProp)
+
+    explicit LInitProp(const LAllocation& object) {
+        setOperand(0, object);
+    }
+
+    static const size_t ValueIndex = 1;
+
+    const LAllocation* getObject() {
+        return getOperand(0);
+    }
+    const LAllocation* getValue() {
+        return getOperand(1);
+    }
+
+    MInitProp* mir() const {
+        return mir_->toInitProp();
+    }
+};
+
+class LInitPropGetterSetter : public LCallInstructionHelper<0, 2, 0>
+{
+  public:
+    LIR_HEADER(InitPropGetterSetter)
+
+    LInitPropGetterSetter(const LAllocation& object, const LAllocation& value) {
+        setOperand(0, object);
+        setOperand(1, value);
+    }
+
+    const LAllocation* object() {
+        return getOperand(0);
+    }
+    const LAllocation* value() {
+        return getOperand(1);
+    }
+
+    MInitPropGetterSetter* mir() const {
+        return mir_->toInitPropGetterSetter();
+    }
+};
+
+class LCheckOverRecursed : public LInstructionHelper<0, 0, 0>
+{
+  public:
+    LIR_HEADER(CheckOverRecursed)
+
+    LCheckOverRecursed()
+    { }
+
+    MCheckOverRecursed* mir() const {
+        return mir_->toCheckOverRecursed();
+    }
+};
+
+class LAsmJSInterruptCheck : public LInstructionHelper<0, 0, 0>
+{
+    Label* interruptExit_;
+    const CallSiteDesc& funcDesc_;
+
+  public:
+    LIR_HEADER(AsmJSInterruptCheck);
+
+    LAsmJSInterruptCheck(Label* interruptExit, const CallSiteDesc& funcDesc)
+      : interruptExit_(interruptExit), funcDesc_(funcDesc)
+    {
+    }
+
+    bool isCall() const {
+        return true;
+    }
+
+    Label* interruptExit() const {
+        return interruptExit_;
+    }
+    const CallSiteDesc& funcDesc() const {
+        return funcDesc_;
+    }
+};
+
+class LInterruptCheck : public LInstructionHelper<0, 0, 0>
+{
+  public:
+    LIR_HEADER(InterruptCheck)
+};
+
+// Alternative to LInterruptCheck which does not emit an explicit check of the
+// interrupt flag but relies on the loop backedge being patched via a signal
+// handler.
+class LInterruptCheckImplicit : public LInstructionHelper<0, 0, 0>
+{
+    Label* oolEntry_;
+
+  public:
+    LIR_HEADER(InterruptCheckImplicit)
+
+    LInterruptCheckImplicit()
+      : oolEntry_(nullptr)
+    {}
+
+    Label* oolEntry() {
+        return oolEntry_;
+    }
+
+    void setOolEntry(Label* oolEntry) {
+        oolEntry_ = oolEntry;
+    }
+    MInterruptCheck* mir() const {
+        return mir_->toInterruptCheck();
+    }
+};
+
+class LDefVar : public LCallInstructionHelper<0, 1, 0>
+{
+  public:
+    LIR_HEADER(DefVar)
+
+    explicit LDefVar(const LAllocation& scopeChain)
+    {
+        setOperand(0, scopeChain);
+    }
+
+    const LAllocation* scopeChain() {
+        return getOperand(0);
+    }
+    MDefVar* mir() const {
+        return mir_->toDefVar();
+    }
+};
+
+class LDefFun : public LCallInstructionHelper<0, 1, 0>
+{
+  public:
+    LIR_HEADER(DefFun)
+
+    explicit LDefFun(const LAllocation& scopeChain)
+    {
+        setOperand(0, scopeChain);
+    }
+
+    const LAllocation* scopeChain() {
+        return getOperand(0);
+    }
+    MDefFun* mir() const {
+        return mir_->toDefFun();
+    }
+};
+
+class LTypeOfV : public LInstructionHelper<1, BOX_PIECES, 1>
+{
+  public:
+    LIR_HEADER(TypeOfV)
+
+    explicit LTypeOfV(const LDefinition& tempToUnbox) {
+        setTemp(0, tempToUnbox);
+    }
+
+    static const size_t Input = 0;
+
+    const LDefinition* tempToUnbox() {
+        return getTemp(0);
+    }
+
+    MTypeOf* mir() const {
+        return mir_->toTypeOf();
+    }
+};
+
+class LToIdV : public LInstructionHelper<BOX_PIECES, 2 * BOX_PIECES, 1>
+{
+  public:
+    LIR_HEADER(ToIdV)
+
+    explicit LToIdV(const LDefinition& temp)
+    {
+        setTemp(0, temp);
+    }
+
+    static const size_t Object = 0;
+    static const size_t Index = BOX_PIECES;
+
+    MToId* mir() const {
+        return mir_->toToId();
+    }
+
+    const LDefinition* tempFloat() {
+        return getTemp(0);
+    }
+};
+
+// Allocate an object for |new| on the caller-side,
+// when there is no templateObject or prototype known
+class LCreateThis : public LCallInstructionHelper<BOX_PIECES, 1, 0>
+{
+  public:
+    LIR_HEADER(CreateThis)
+
+    explicit LCreateThis(const LAllocation& callee)
+    {
+        setOperand(0, callee);
+    }
+
+    const LAllocation* getCallee() {
+        return getOperand(0);
+    }
+
+    MCreateThis* mir() const {
+        return mir_->toCreateThis();
+    }
+};
+
+// Allocate an object for |new| on the caller-side,
+// when the prototype is known.
+class LCreateThisWithProto : public LCallInstructionHelper<1, 2, 0>
+{
+  public:
+    LIR_HEADER(CreateThisWithProto)
+
+    LCreateThisWithProto(const LAllocation& callee, const LAllocation& prototype)
+    {
+        setOperand(0, callee);
+        setOperand(1, prototype);
+    }
+
+    const LAllocation* getCallee() {
+        return getOperand(0);
+    }
+    const LAllocation* getPrototype() {
+        return getOperand(1);
+    }
+
+    MCreateThis* mir() const {
+        return mir_->toCreateThis();
+    }
+};
+
+// Allocate an object for |new| on the caller-side.
+// Always performs object initialization with a fast path.
+class LCreateThisWithTemplate : public LInstructionHelper<1, 0, 1>
+{
+  public:
+    LIR_HEADER(CreateThisWithTemplate)
+
+    explicit LCreateThisWithTemplate(const LDefinition& temp) {
+        setTemp(0, temp);
+    }
+
+    MCreateThisWithTemplate* mir() const {
+        return mir_->toCreateThisWithTemplate();
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+};
+
+// Allocate a new arguments object for the frame.
+class LCreateArgumentsObject : public LCallInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(CreateArgumentsObject)
+
+    LCreateArgumentsObject(const LAllocation& callObj, const LDefinition& temp)
+    {
+        setOperand(0, callObj);
+        setTemp(0, temp);
+    }
+
+    const LAllocation* getCallObject() {
+        return getOperand(0);
+    }
+
+    MCreateArgumentsObject* mir() const {
+        return mir_->toCreateArgumentsObject();
+    }
+};
+
+// Get argument from arguments object.
+class LGetArgumentsObjectArg : public LInstructionHelper<BOX_PIECES, 1, 1>
+{
+  public:
+    LIR_HEADER(GetArgumentsObjectArg)
+
+    LGetArgumentsObjectArg(const LAllocation& argsObj, const LDefinition& temp)
+    {
+        setOperand(0, argsObj);
+        setTemp(0, temp);
+    }
+
+    const LAllocation* getArgsObject() {
+        return getOperand(0);
+    }
+
+    MGetArgumentsObjectArg* mir() const {
+        return mir_->toGetArgumentsObjectArg();
+    }
+};
+
+// Set argument on arguments object.
+class LSetArgumentsObjectArg : public LInstructionHelper<0, 1 + BOX_PIECES, 1>
+{
+  public:
+    LIR_HEADER(SetArgumentsObjectArg)
+
+    LSetArgumentsObjectArg(const LAllocation& argsObj, const LDefinition& temp)
+    {
+        setOperand(0, argsObj);
+        setTemp(0, temp);
+    }
+
+    const LAllocation* getArgsObject() {
+        return getOperand(0);
+    }
+
+    MSetArgumentsObjectArg* mir() const {
+        return mir_->toSetArgumentsObjectArg();
+    }
+
+    static const size_t ValueIndex = 1;
+};
+
+// If the Value is an Object, return unbox(Value).
+// Otherwise, return the other Object.
+class LReturnFromCtor : public LInstructionHelper<1, BOX_PIECES + 1, 0>
+{
+  public:
+    LIR_HEADER(ReturnFromCtor)
+
+    explicit LReturnFromCtor(const LAllocation& object)
+    {
+        // Value set by useBox() during lowering.
+        setOperand(LReturnFromCtor::ObjectIndex, object);
+    }
+
+    const LAllocation* getObject() {
+        return getOperand(LReturnFromCtor::ObjectIndex);
+    }
+
+    static const size_t ValueIndex = 0;
+    static const size_t ObjectIndex = BOX_PIECES;
+};
+
+class LComputeThis : public LInstructionHelper<1, BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(ComputeThis)
+
+    static const size_t ValueIndex = 0;
+
+    const LDefinition* output() {
+        return getDef(0);
+    }
+
+    MComputeThis* mir() const {
+        return mir_->toComputeThis();
+    }
+};
+
+class LLoadArrowThis : public LInstructionHelper<BOX_PIECES, 1, 0>
+{
+  public:
+    explicit LLoadArrowThis(const LAllocation& callee) {
+        setOperand(0, callee);
+    }
+
+    LIR_HEADER(LoadArrowThis)
+
+    const LAllocation* callee() {
+        return getOperand(0);
+    }
+};
+
+// Writes a typed argument for a function call to the frame's argument vector.
+class LStackArgT : public LInstructionHelper<0, 1, 0>
+{
+    uint32_t argslot_; // Index into frame-scope argument vector.
+    MIRType type_;
+
+  public:
+    LIR_HEADER(StackArgT)
+
+    LStackArgT(uint32_t argslot, MIRType type, const LAllocation& arg)
+      : argslot_(argslot),
+        type_(type)
+    {
+        setOperand(0, arg);
+    }
+    uint32_t argslot() const {
+        return argslot_;
+    }
+    MIRType type() const {
+        return type_;
+    }
+    const LAllocation* getArgument() {
+        return getOperand(0);
+    }
+};
+
+// Writes an untyped argument for a function call to the frame's argument vector.
+class LStackArgV : public LInstructionHelper<0, BOX_PIECES, 0>
+{
+    uint32_t argslot_; // Index into frame-scope argument vector.
+
+  public:
+    LIR_HEADER(StackArgV)
+
+    explicit LStackArgV(uint32_t argslot)
+      : argslot_(argslot)
+    { }
+
+    uint32_t argslot() const {
+        return argslot_;
+    }
+};
+
+// Common code for LIR descended from MCall.
+template <size_t Defs, size_t Operands, size_t Temps>
+class LJSCallInstructionHelper : public LCallInstructionHelper<Defs, Operands, Temps>
+{
+  public:
+    uint32_t argslot() const {
+        if (JitStackValueAlignment > 1)
+            return AlignBytes(mir()->numStackArgs(), JitStackValueAlignment);
+        return mir()->numStackArgs();
+    }
+    MCall* mir() const {
+        return this->mir_->toCall();
+    }
+
+    bool hasSingleTarget() const {
+        return getSingleTarget() != nullptr;
+    }
+    JSFunction* getSingleTarget() const {
+        return mir()->getSingleTarget();
+    }
+
+    // Does not include |this|.
+    uint32_t numActualArgs() const {
+        return mir()->numActualArgs();
+    }
+
+    bool isConstructing() const {
+        return mir()->isConstructing();
+    }
+};
+
+// Generates a polymorphic callsite, wherein the function being called is
+// unknown and anticipated to vary.
+class LCallGeneric : public LJSCallInstructionHelper<BOX_PIECES, 1, 2>
+{
+  public:
+    LIR_HEADER(CallGeneric)
+
+    LCallGeneric(const LAllocation& func, const LDefinition& nargsreg,
+                 const LDefinition& tmpobjreg)
+    {
+        setOperand(0, func);
+        setTemp(0, nargsreg);
+        setTemp(1, tmpobjreg);
+    }
+
+    const LAllocation* getFunction() {
+        return getOperand(0);
+    }
+    const LDefinition* getNargsReg() {
+        return getTemp(0);
+    }
+    const LDefinition* getTempObject() {
+        return getTemp(1);
+    }
+};
+
+// Generates a hardcoded callsite for a known, non-native target.
+class LCallKnown : public LJSCallInstructionHelper<BOX_PIECES, 1, 1>
+{
+  public:
+    LIR_HEADER(CallKnown)
+
+    LCallKnown(const LAllocation& func, const LDefinition& tmpobjreg)
+    {
+        setOperand(0, func);
+        setTemp(0, tmpobjreg);
+    }
+
+    const LAllocation* getFunction() {
+        return getOperand(0);
+    }
+    const LDefinition* getTempObject() {
+        return getTemp(0);
+    }
+};
+
+// Generates a hardcoded callsite for a known, native target.
+class LCallNative : public LJSCallInstructionHelper<BOX_PIECES, 0, 4>
+{
+  public:
+    LIR_HEADER(CallNative)
+
+    LCallNative(const LDefinition& argContext, const LDefinition& argUintN,
+                const LDefinition& argVp, const LDefinition& tmpreg)
+    {
+        // Registers used for callWithABI().
+        setTemp(0, argContext);
+        setTemp(1, argUintN);
+        setTemp(2, argVp);
+
+        // Temporary registers.
+        setTemp(3, tmpreg);
+    }
+
+    const LDefinition* getArgContextReg() {
+        return getTemp(0);
+    }
+    const LDefinition* getArgUintNReg() {
+        return getTemp(1);
+    }
+    const LDefinition* getArgVpReg() {
+        return getTemp(2);
+    }
+    const LDefinition* getTempReg() {
+        return getTemp(3);
+    }
+};
+
+// Generates a hardcoded callsite for a known, DOM-native target.
+class LCallDOMNative : public LJSCallInstructionHelper<BOX_PIECES, 0, 4>
+{
+  public:
+    LIR_HEADER(CallDOMNative)
+
+    LCallDOMNative(const LDefinition& argJSContext, const LDefinition& argObj,
+                   const LDefinition& argPrivate, const LDefinition& argArgs)
+    {
+        setTemp(0, argJSContext);
+        setTemp(1, argObj);
+        setTemp(2, argPrivate);
+        setTemp(3, argArgs);
+    }
+
+    const LDefinition* getArgJSContext() {
+        return getTemp(0);
+    }
+    const LDefinition* getArgObj() {
+        return getTemp(1);
+    }
+    const LDefinition* getArgPrivate() {
+        return getTemp(2);
+    }
+    const LDefinition* getArgArgs() {
+        return getTemp(3);
+    }
+};
+
+class LBail : public LInstructionHelper<0, 0, 0>
+{
+  public:
+    LIR_HEADER(Bail)
+};
+
+class LUnreachable : public LControlInstructionHelper<0, 0, 0>
+{
+  public:
+    LIR_HEADER(Unreachable)
+};
+
+class LEncodeSnapshot : public LInstructionHelper<0, 0, 0>
+{
+  public:
+    LIR_HEADER(EncodeSnapshot)
+};
+
+template <size_t defs, size_t ops>
+class LDOMPropertyInstructionHelper : public LCallInstructionHelper<defs, 1 + ops, 3>
+{
+  protected:
+    LDOMPropertyInstructionHelper(const LDefinition& JSContextReg, const LAllocation& ObjectReg,
+                                  const LDefinition& PrivReg, const LDefinition& ValueReg)
+    {
+        this->setOperand(0, ObjectReg);
+        this->setTemp(0, JSContextReg);
+        this->setTemp(1, PrivReg);
+        this->setTemp(2, ValueReg);
+    }
+
+  public:
+    const LDefinition* getJSContextReg() {
+        return this->getTemp(0);
+    }
+    const LAllocation* getObjectReg() {
+        return this->getOperand(0);
+    }
+    const LDefinition* getPrivReg() {
+        return this->getTemp(1);
+    }
+    const LDefinition* getValueReg() {
+        return this->getTemp(2);
+    }
+};
+
+
+class LGetDOMProperty : public LDOMPropertyInstructionHelper<BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(GetDOMProperty)
+
+    LGetDOMProperty(const LDefinition& JSContextReg, const LAllocation& ObjectReg,
+                    const LDefinition& PrivReg, const LDefinition& ValueReg)
+      : LDOMPropertyInstructionHelper<BOX_PIECES, 0>(JSContextReg, ObjectReg,
+                                                     PrivReg, ValueReg)
+    { }
+
+    MGetDOMProperty* mir() const {
+        return mir_->toGetDOMProperty();
+    }
+};
+
+class LGetDOMMemberV : public LInstructionHelper<BOX_PIECES, 1, 0>
+{
+  public:
+    LIR_HEADER(GetDOMMemberV);
+    explicit LGetDOMMemberV(const LAllocation& object) {
+        setOperand(0, object);
+    }
+
+    const LAllocation* object() {
+        return getOperand(0);
+    }
+
+    MGetDOMMember* mir() const {
+        return mir_->toGetDOMMember();
+    }
+};
+
+class LGetDOMMemberT : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(GetDOMMemberT);
+    explicit LGetDOMMemberT(const LAllocation& object) {
+        setOperand(0, object);
+    }
+
+    const LAllocation* object() {
+        return getOperand(0);
+    }
+
+    MGetDOMMember* mir() const {
+        return mir_->toGetDOMMember();
+    }
+};
+
+class LSetDOMProperty : public LDOMPropertyInstructionHelper<0, BOX_PIECES>
+{
+  public:
+    LIR_HEADER(SetDOMProperty)
+
+    LSetDOMProperty(const LDefinition& JSContextReg, const LAllocation& ObjectReg,
+                    const LDefinition& PrivReg, const LDefinition& ValueReg)
+      : LDOMPropertyInstructionHelper<0, BOX_PIECES>(JSContextReg, ObjectReg,
+                                                     PrivReg, ValueReg)
+    { }
+
+    static const size_t Value = 1;
+
+    MSetDOMProperty* mir() const {
+        return mir_->toSetDOMProperty();
+    }
+};
+
+// Generates a polymorphic callsite, wherein the function being called is
+// unknown and anticipated to vary.
+class LApplyArgsGeneric : public LCallInstructionHelper<BOX_PIECES, BOX_PIECES + 2, 2>
+{
+  public:
+    LIR_HEADER(ApplyArgsGeneric)
+
+    LApplyArgsGeneric(const LAllocation& func, const LAllocation& argc,
+                      const LDefinition& tmpobjreg, const LDefinition& tmpcopy)
+    {
+        setOperand(0, func);
+        setOperand(1, argc);
+        setTemp(0, tmpobjreg);
+        setTemp(1, tmpcopy);
+    }
+
+    MApplyArgs* mir() const {
+        return mir_->toApplyArgs();
+    }
+
+    bool hasSingleTarget() const {
+        return getSingleTarget() != nullptr;
+    }
+    JSFunction* getSingleTarget() const {
+        return mir()->getSingleTarget();
+    }
+
+    const LAllocation* getFunction() {
+        return getOperand(0);
+    }
+    const LAllocation* getArgc() {
+        return getOperand(1);
+    }
+    static const size_t ThisIndex = 2;
+
+    const LDefinition* getTempObject() {
+        return getTemp(0);
+    }
+    const LDefinition* getTempStackCounter() {
+        return getTemp(1);
+    }
+};
+
+class LArraySplice : public LCallInstructionHelper<0, 3, 0>
+{
+  public:
+    LIR_HEADER(ArraySplice)
+
+    LArraySplice(const LAllocation& object, const LAllocation& start,
+                 const LAllocation& deleteCount)
+    {
+        setOperand(0, object);
+        setOperand(1, start);
+        setOperand(2, deleteCount);
+    }
+
+    MArraySplice* mir() const {
+        return mir_->toArraySplice();
+    }
+
+    const LAllocation* getObject() {
+        return getOperand(0);
+    }
+    const LAllocation* getStart() {
+        return getOperand(1);
+    }
+    const LAllocation* getDeleteCount() {
+        return getOperand(2);
+    }
+};
+
+class LGetDynamicName : public LCallInstructionHelper<BOX_PIECES, 2, 3>
+{
+  public:
+    LIR_HEADER(GetDynamicName)
+
+    LGetDynamicName(const LAllocation& scopeChain, const LAllocation& name,
+                    const LDefinition& temp1, const LDefinition& temp2, const LDefinition& temp3)
+    {
+        setOperand(0, scopeChain);
+        setOperand(1, name);
+        setTemp(0, temp1);
+        setTemp(1, temp2);
+        setTemp(2, temp3);
+    }
+
+    MGetDynamicName* mir() const {
+        return mir_->toGetDynamicName();
+    }
+
+    const LAllocation* getScopeChain() {
+        return getOperand(0);
+    }
+    const LAllocation* getName() {
+        return getOperand(1);
+    }
+
+    const LDefinition* temp1() {
+        return getTemp(0);
+    }
+    const LDefinition* temp2() {
+        return getTemp(1);
+    }
+    const LDefinition* temp3() {
+        return getTemp(2);
+    }
+};
+
+class LFilterArgumentsOrEvalS : public LCallInstructionHelper<0, 1, 2>
+{
+  public:
+    LIR_HEADER(FilterArgumentsOrEvalS)
+
+    LFilterArgumentsOrEvalS(const LAllocation& string, const LDefinition& temp1,
+                            const LDefinition& temp2)
+    {
+        setOperand(0, string);
+        setTemp(0, temp1);
+        setTemp(1, temp2);
+    }
+
+    MFilterArgumentsOrEval* mir() const {
+        return mir_->toFilterArgumentsOrEval();
+    }
+
+    const LAllocation* getString() {
+        return getOperand(0);
+    }
+    const LDefinition* temp1() {
+        return getTemp(0);
+    }
+    const LDefinition* temp2() {
+        return getTemp(1);
+    }
+};
+
+class LFilterArgumentsOrEvalV : public LCallInstructionHelper<0, BOX_PIECES, 3>
+{
+  public:
+    LIR_HEADER(FilterArgumentsOrEvalV)
+
+    LFilterArgumentsOrEvalV(const LDefinition& temp1, const LDefinition& temp2,
+                            const LDefinition& temp3)
+    {
+        setTemp(0, temp1);
+        setTemp(1, temp2);
+        setTemp(2, temp3);
+    }
+
+    static const size_t Input = 0;
+
+    MFilterArgumentsOrEval* mir() const {
+        return mir_->toFilterArgumentsOrEval();
+    }
+
+    const LDefinition* temp1() {
+        return getTemp(0);
+    }
+    const LDefinition* temp2() {
+        return getTemp(1);
+    }
+    const LDefinition* temp3() {
+        return getTemp(2);
+    }
+};
+
+class LCallDirectEval : public LCallInstructionHelper<BOX_PIECES, 2 + (2 * BOX_PIECES), 0>
+{
+  public:
+    LIR_HEADER(CallDirectEval)
+
+    LCallDirectEval(const LAllocation& scopeChain, const LAllocation& string)
+    {
+        setOperand(0, scopeChain);
+        setOperand(1, string);
+    }
+
+    static const size_t ThisValue = 2;
+    static const size_t NewTarget = 2 + BOX_PIECES;
+
+    MCallDirectEval* mir() const {
+        return mir_->toCallDirectEval();
+    }
+
+    const LAllocation* getScopeChain() {
+        return getOperand(0);
+    }
+    const LAllocation* getString() {
+        return getOperand(1);
+    }
+};
+
+// Takes in either an integer or boolean input and tests it for truthiness.
+class LTestIAndBranch : public LControlInstructionHelper<2, 1, 0>
+{
+  public:
+    LIR_HEADER(TestIAndBranch)
+
+    LTestIAndBranch(const LAllocation& in, MBasicBlock* ifTrue, MBasicBlock* ifFalse)
+    {
+        setOperand(0, in);
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+    }
+
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+};
+
+// Takes in either an integer or boolean input and tests it for truthiness.
+class LTestDAndBranch : public LControlInstructionHelper<2, 1, 0>
+{
+  public:
+    LIR_HEADER(TestDAndBranch)
+
+    LTestDAndBranch(const LAllocation& in, MBasicBlock* ifTrue, MBasicBlock* ifFalse)
+    {
+        setOperand(0, in);
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+    }
+
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+};
+
+// Takes in either an integer or boolean input and tests it for truthiness.
+class LTestFAndBranch : public LControlInstructionHelper<2, 1, 0>
+{
+  public:
+    LIR_HEADER(TestFAndBranch)
+
+    LTestFAndBranch(const LAllocation& in, MBasicBlock* ifTrue, MBasicBlock* ifFalse)
+    {
+        setOperand(0, in);
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+    }
+
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+};
+
+// Takes an object and tests it for truthiness.  An object is falsy iff it
+// emulates |undefined|; see js::EmulatesUndefined.
+class LTestOAndBranch : public LControlInstructionHelper<2, 1, 1>
+{
+  public:
+    LIR_HEADER(TestOAndBranch)
+
+    LTestOAndBranch(const LAllocation& input, MBasicBlock* ifTruthy, MBasicBlock* ifFalsy,
+                    const LDefinition& temp)
+    {
+        setOperand(0, input);
+        setSuccessor(0, ifTruthy);
+        setSuccessor(1, ifFalsy);
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MBasicBlock* ifTruthy() {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalsy() {
+        return getSuccessor(1);
+    }
+
+    MTest* mir() {
+        return mir_->toTest();
+    }
+};
+
+// Takes in a boxed value and tests it for truthiness.
+class LTestVAndBranch : public LControlInstructionHelper<2, BOX_PIECES, 3>
+{
+  public:
+    LIR_HEADER(TestVAndBranch)
+
+    LTestVAndBranch(MBasicBlock* ifTruthy, MBasicBlock* ifFalsy, const LDefinition& temp0,
+                    const LDefinition& temp1, const LDefinition& temp2)
+    {
+        setSuccessor(0, ifTruthy);
+        setSuccessor(1, ifFalsy);
+        setTemp(0, temp0);
+        setTemp(1, temp1);
+        setTemp(2, temp2);
+    }
+
+    const char* extraName() const {
+        return mir()->operandMightEmulateUndefined() ? "MightEmulateUndefined" : nullptr;
+    }
+
+    static const size_t Input = 0;
+
+    const LDefinition* tempFloat() {
+        return getTemp(0);
+    }
+
+    const LDefinition* temp1() {
+        return getTemp(1);
+    }
+
+    const LDefinition* temp2() {
+        return getTemp(2);
+    }
+
+    MBasicBlock* ifTruthy() {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalsy() {
+        return getSuccessor(1);
+    }
+
+    MTest* mir() const {
+        return mir_->toTest();
+    }
+};
+
+// Dispatches control flow to a successor based on incoming JSFunction*.
+// Used to implemenent polymorphic inlining.
+class LFunctionDispatch : public LInstructionHelper<0, 1, 0>
+{
+    // Dispatch is performed based on a function -> block map
+    // stored in the MIR.
+
+  public:
+    LIR_HEADER(FunctionDispatch);
+
+    explicit LFunctionDispatch(const LAllocation& in) {
+        setOperand(0, in);
+    }
+
+    MFunctionDispatch* mir() const {
+        return mir_->toFunctionDispatch();
+    }
+};
+
+class LObjectGroupDispatch : public LInstructionHelper<0, 1, 1>
+{
+    // Dispatch is performed based on an ObjectGroup -> block
+    // map inferred by the MIR.
+
+  public:
+    LIR_HEADER(ObjectGroupDispatch);
+
+    const char* extraName() const {
+        return mir()->hasFallback() ? "HasFallback" : "NoFallback";
+    }
+
+    LObjectGroupDispatch(const LAllocation& in, const LDefinition& temp) {
+        setOperand(0, in);
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    MObjectGroupDispatch* mir() const {
+        return mir_->toObjectGroupDispatch();
+    }
+};
+
+// Compares two integral values of the same JS type, either integer or object.
+// For objects, both operands are in registers.
+class LCompare : public LInstructionHelper<1, 2, 0>
+{
+    JSOp jsop_;
+
+  public:
+    LIR_HEADER(Compare)
+    LCompare(JSOp jsop, const LAllocation& left, const LAllocation& right)
+      : jsop_(jsop)
+    {
+        setOperand(0, left);
+        setOperand(1, right);
+    }
+
+    JSOp jsop() const {
+        return jsop_;
+    }
+    const LAllocation* left() {
+        return getOperand(0);
+    }
+    const LAllocation* right() {
+        return getOperand(1);
+    }
+    MCompare* mir() {
+        return mir_->toCompare();
+    }
+    const char* extraName() const {
+        return js_CodeName[jsop_];
+    }
+};
+
+// Compares two integral values of the same JS type, either integer or object.
+// For objects, both operands are in registers.
+class LCompareAndBranch : public LControlInstructionHelper<2, 2, 0>
+{
+    MCompare* cmpMir_;
+    JSOp jsop_;
+
+  public:
+    LIR_HEADER(CompareAndBranch)
+    LCompareAndBranch(MCompare* cmpMir, JSOp jsop,
+                      const LAllocation& left, const LAllocation& right,
+                      MBasicBlock* ifTrue, MBasicBlock* ifFalse)
+      : cmpMir_(cmpMir), jsop_(jsop)
+    {
+        setOperand(0, left);
+        setOperand(1, right);
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+    }
+
+    JSOp jsop() const {
+        return jsop_;
+    }
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+    const LAllocation* left() {
+        return getOperand(0);
+    }
+    const LAllocation* right() {
+        return getOperand(1);
+    }
+    MTest* mir() const {
+        return mir_->toTest();
+    }
+    MCompare* cmpMir() const {
+        return cmpMir_;
+    }
+    const char* extraName() const {
+        return js_CodeName[jsop_];
+    }
+};
+
+class LCompareD : public LInstructionHelper<1, 2, 0>
+{
+  public:
+    LIR_HEADER(CompareD)
+    LCompareD(const LAllocation& left, const LAllocation& right) {
+        setOperand(0, left);
+        setOperand(1, right);
+    }
+
+    const LAllocation* left() {
+        return getOperand(0);
+    }
+    const LAllocation* right() {
+        return getOperand(1);
+    }
+    MCompare* mir() {
+        return mir_->toCompare();
+    }
+};
+
+class LCompareF : public LInstructionHelper<1, 2, 0>
+{
+  public:
+    LIR_HEADER(CompareF)
+    LCompareF(const LAllocation& left, const LAllocation& right) {
+        setOperand(0, left);
+        setOperand(1, right);
+    }
+
+    const LAllocation* left() {
+        return getOperand(0);
+    }
+    const LAllocation* right() {
+        return getOperand(1);
+    }
+    MCompare* mir() {
+        return mir_->toCompare();
+    }
+};
+
+class LCompareDAndBranch : public LControlInstructionHelper<2, 2, 0>
+{
+    MCompare* cmpMir_;
+
+  public:
+    LIR_HEADER(CompareDAndBranch)
+    LCompareDAndBranch(MCompare* cmpMir, const LAllocation& left, const LAllocation& right,
+                       MBasicBlock* ifTrue, MBasicBlock* ifFalse)
+      : cmpMir_(cmpMir)
+    {
+        setOperand(0, left);
+        setOperand(1, right);
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+    }
+
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+    const LAllocation* left() {
+        return getOperand(0);
+    }
+    const LAllocation* right() {
+        return getOperand(1);
+    }
+    MTest* mir() const {
+        return mir_->toTest();
+    }
+    MCompare* cmpMir() const {
+        return cmpMir_;
+    }
+};
+
+class LCompareFAndBranch : public LControlInstructionHelper<2, 2, 0>
+{
+    MCompare* cmpMir_;
+
+  public:
+    LIR_HEADER(CompareFAndBranch)
+    LCompareFAndBranch(MCompare* cmpMir, const LAllocation& left, const LAllocation& right,
+                       MBasicBlock* ifTrue, MBasicBlock* ifFalse)
+      : cmpMir_(cmpMir)
+    {
+        setOperand(0, left);
+        setOperand(1, right);
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+    }
+
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+    const LAllocation* left() {
+        return getOperand(0);
+    }
+    const LAllocation* right() {
+        return getOperand(1);
+    }
+    MTest* mir() const {
+        return mir_->toTest();
+    }
+    MCompare* cmpMir() const {
+        return cmpMir_;
+    }
+};
+
+class LCompareS : public LInstructionHelper<1, 2, 0>
+{
+  public:
+    LIR_HEADER(CompareS)
+    LCompareS(const LAllocation& left, const LAllocation& right) {
+        setOperand(0, left);
+        setOperand(1, right);
+    }
+
+    const LAllocation* left() {
+        return getOperand(0);
+    }
+    const LAllocation* right() {
+        return getOperand(1);
+    }
+    MCompare* mir() {
+        return mir_->toCompare();
+    }
+};
+
+// strict-equality between value and string.
+class LCompareStrictS : public LInstructionHelper<1, BOX_PIECES + 1, 1>
+{
+  public:
+    LIR_HEADER(CompareStrictS)
+    LCompareStrictS(const LAllocation& rhs, const LDefinition& temp) {
+        setOperand(BOX_PIECES, rhs);
+        setTemp(0, temp);
+    }
+
+    static const size_t Lhs = 0;
+
+    const LAllocation* right() {
+        return getOperand(BOX_PIECES);
+    }
+    const LDefinition* tempToUnbox() {
+        return getTemp(0);
+    }
+    MCompare* mir() {
+        return mir_->toCompare();
+    }
+};
+
+// Used for strict-equality comparisons where one side is a boolean
+// and the other is a value. Note that CompareI is used to compare
+// two booleans.
+class LCompareB : public LInstructionHelper<1, BOX_PIECES + 1, 0>
+{
+  public:
+    LIR_HEADER(CompareB)
+
+    explicit LCompareB(const LAllocation& rhs) {
+        setOperand(BOX_PIECES, rhs);
+    }
+
+    static const size_t Lhs = 0;
+
+    const LAllocation* rhs() {
+        return getOperand(BOX_PIECES);
+    }
+
+    MCompare* mir() {
+        return mir_->toCompare();
+    }
+};
+
+class LCompareBAndBranch : public LControlInstructionHelper<2, BOX_PIECES + 1, 0>
+{
+    MCompare* cmpMir_;
+
+  public:
+    LIR_HEADER(CompareBAndBranch)
+
+    LCompareBAndBranch(MCompare* cmpMir, const LAllocation& rhs,
+                       MBasicBlock* ifTrue, MBasicBlock* ifFalse)
+      : cmpMir_(cmpMir)
+    {
+        setOperand(BOX_PIECES, rhs);
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+    }
+
+    static const size_t Lhs = 0;
+
+    const LAllocation* rhs() {
+        return getOperand(BOX_PIECES);
+    }
+
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+    MTest* mir() const {
+        return mir_->toTest();
+    }
+    MCompare* cmpMir() const {
+        return cmpMir_;
+    }
+};
+
+class LCompareV : public LInstructionHelper<1, 2 * BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(CompareV)
+
+    static const size_t LhsInput = 0;
+    static const size_t RhsInput = BOX_PIECES;
+
+    MCompare* mir() const {
+        return mir_->toCompare();
+    }
+};
+
+class LCompareVAndBranch : public LControlInstructionHelper<2, 2 * BOX_PIECES, 0>
+{
+    MCompare* cmpMir_;
+
+  public:
+    LIR_HEADER(CompareVAndBranch)
+
+    static const size_t LhsInput = 0;
+    static const size_t RhsInput = BOX_PIECES;
+
+    LCompareVAndBranch(MCompare* cmpMir, MBasicBlock* ifTrue, MBasicBlock* ifFalse)
+      : cmpMir_(cmpMir)
+    {
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+    }
+
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+    MTest* mir() const {
+        return mir_->toTest();
+    }
+    MCompare* cmpMir() const {
+        return cmpMir_;
+    }
+};
+
+class LCompareVM : public LCallInstructionHelper<1, 2 * BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(CompareVM)
+
+    static const size_t LhsInput = 0;
+    static const size_t RhsInput = BOX_PIECES;
+
+    MCompare* mir() const {
+        return mir_->toCompare();
+    }
+};
+
+class LBitAndAndBranch : public LControlInstructionHelper<2, 2, 0>
+{
+  public:
+    LIR_HEADER(BitAndAndBranch)
+    LBitAndAndBranch(MBasicBlock* ifTrue, MBasicBlock* ifFalse)
+    {
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+    }
+
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+    const LAllocation* left() {
+        return getOperand(0);
+    }
+    const LAllocation* right() {
+        return getOperand(1);
+    }
+};
+
+// Takes a value and tests whether it is null, undefined, or is an object that
+// emulates |undefined|, as determined by the JSCLASS_EMULATES_UNDEFINED class
+// flag on unwrapped objects.  See also js::EmulatesUndefined.
+class LIsNullOrLikeUndefinedV : public LInstructionHelper<1, BOX_PIECES, 2>
+{
+  public:
+    LIR_HEADER(IsNullOrLikeUndefinedV)
+
+    LIsNullOrLikeUndefinedV(const LDefinition& temp, const LDefinition& tempToUnbox)
+    {
+        setTemp(0, temp);
+        setTemp(1, tempToUnbox);
+    }
+
+    static const size_t Value = 0;
+
+    MCompare* mir() {
+        return mir_->toCompare();
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    const LDefinition* tempToUnbox() {
+        return getTemp(1);
+    }
+};
+
+// Takes an object or object-or-null pointer and tests whether it is null or is
+// an object that emulates |undefined|, as above.
+class LIsNullOrLikeUndefinedT : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(IsNullOrLikeUndefinedT)
+
+    explicit LIsNullOrLikeUndefinedT(const LAllocation& input)
+    {
+        setOperand(0, input);
+    }
+
+    MCompare* mir() {
+        return mir_->toCompare();
+    }
+};
+
+class LIsNullOrLikeUndefinedAndBranchV : public LControlInstructionHelper<2, BOX_PIECES, 2>
+{
+    MCompare* cmpMir_;
+
+  public:
+    LIR_HEADER(IsNullOrLikeUndefinedAndBranchV)
+
+    LIsNullOrLikeUndefinedAndBranchV(MCompare* cmpMir, MBasicBlock* ifTrue, MBasicBlock* ifFalse,
+                                     const LDefinition& temp, const LDefinition& tempToUnbox)
+      : cmpMir_(cmpMir)
+    {
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+        setTemp(0, temp);
+        setTemp(1, tempToUnbox);
+    }
+
+    static const size_t Value = 0;
+
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+    MTest* mir() const {
+        return mir_->toTest();
+    }
+    MCompare* cmpMir() const {
+        return cmpMir_;
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+    const LDefinition* tempToUnbox() {
+        return getTemp(1);
+    }
+};
+
+class LIsNullOrLikeUndefinedAndBranchT : public LControlInstructionHelper<2, 1, 1>
+{
+    MCompare* cmpMir_;
+
+  public:
+    LIR_HEADER(IsNullOrLikeUndefinedAndBranchT)
+
+    LIsNullOrLikeUndefinedAndBranchT(MCompare* cmpMir, const LAllocation& input,
+                                     MBasicBlock* ifTrue, MBasicBlock* ifFalse,
+                                     const LDefinition& temp)
+      : cmpMir_(cmpMir)
+    {
+        setOperand(0, input);
+        setSuccessor(0, ifTrue);
+        setSuccessor(1, ifFalse);
+        setTemp(0, temp);
+    }
+
+    MBasicBlock* ifTrue() const {
+        return getSuccessor(0);
+    }
+    MBasicBlock* ifFalse() const {
+        return getSuccessor(1);
+    }
+    MTest* mir() const {
+        return mir_->toTest();
+    }
+    MCompare* cmpMir() const {
+        return cmpMir_;
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+};
+
+// Not operation on an integer.
+class LNotI : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(NotI)
+
+    explicit LNotI(const LAllocation& input) {
+        setOperand(0, input);
+    }
+};
+
+// Not operation on a double.
+class LNotD : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(NotD)
+
+    explicit LNotD(const LAllocation& input) {
+        setOperand(0, input);
+    }
+
+    MNot* mir() {
+        return mir_->toNot();
+    }
+};
+
+// Not operation on a float32.
+class LNotF : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(NotF)
+
+    explicit LNotF(const LAllocation& input) {
+        setOperand(0, input);
+    }
+
+    MNot* mir() {
+        return mir_->toNot();
+    }
+};
+
+// Boolean complement operation on an object.
+class LNotO : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(NotO)
+
+    explicit LNotO(const LAllocation& input)
+    {
+        setOperand(0, input);
+    }
+
+    MNot* mir() {
+        return mir_->toNot();
+    }
+};
+
+// Boolean complement operation on a value.
+class LNotV : public LInstructionHelper<1, BOX_PIECES, 3>
+{
+  public:
+    LIR_HEADER(NotV)
+
+    static const size_t Input = 0;
+    LNotV(const LDefinition& temp0, const LDefinition& temp1, const LDefinition& temp2)
+    {
+        setTemp(0, temp0);
+        setTemp(1, temp1);
+        setTemp(2, temp2);
+    }
+
+    const LDefinition* tempFloat() {
+        return getTemp(0);
+    }
+
+    const LDefinition* temp1() {
+        return getTemp(1);
+    }
+
+    const LDefinition* temp2() {
+        return getTemp(2);
+    }
+
+    MNot* mir() {
+        return mir_->toNot();
+    }
+};
+
+// Bitwise not operation, takes a 32-bit integer as input and returning
+// a 32-bit integer result as an output.
+class LBitNotI : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(BitNotI)
+};
+
+// Call a VM function to perform a BITNOT operation.
+class LBitNotV : public LCallInstructionHelper<1, BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(BitNotV)
+
+    static const size_t Input = 0;
+};
+
+// Binary bitwise operation, taking two 32-bit integers as inputs and returning
+// a 32-bit integer result as an output.
+class LBitOpI : public LInstructionHelper<1, 2, 0>
+{
+    JSOp op_;
+
+  public:
+    LIR_HEADER(BitOpI)
+
+    explicit LBitOpI(JSOp op)
+      : op_(op)
+    { }
+
+    const char* extraName() const {
+        if (bitop() == JSOP_URSH && mir_->toUrsh()->bailoutsDisabled())
+            return "ursh:BailoutsDisabled";
+        return js_CodeName[op_];
+    }
+
+    JSOp bitop() const {
+        return op_;
+    }
+};
+
+// Call a VM function to perform a bitwise operation.
+class LBitOpV : public LCallInstructionHelper<1, 2 * BOX_PIECES, 0>
+{
+    JSOp jsop_;
+
+  public:
+    LIR_HEADER(BitOpV)
+
+    explicit LBitOpV(JSOp jsop)
+      : jsop_(jsop)
+    { }
+
+    JSOp jsop() const {
+        return jsop_;
+    }
+
+    const char* extraName() const {
+        return js_CodeName[jsop_];
+    }
+
+    static const size_t LhsInput = 0;
+    static const size_t RhsInput = BOX_PIECES;
+};
+
+// Shift operation, taking two 32-bit integers as inputs and returning
+// a 32-bit integer result as an output.
+class LShiftI : public LBinaryMath<0>
+{
+    JSOp op_;
+
+  public:
+    LIR_HEADER(ShiftI)
+
+    explicit LShiftI(JSOp op)
+      : op_(op)
+    { }
+
+    JSOp bitop() {
+        return op_;
+    }
+
+    MInstruction* mir() {
+        return mir_->toInstruction();
+    }
+
+    const char* extraName() const {
+        return js_CodeName[op_];
+    }
+};
+
+class LUrshD : public LBinaryMath<1>
+{
+  public:
+    LIR_HEADER(UrshD)
+
+    LUrshD(const LAllocation& lhs, const LAllocation& rhs, const LDefinition& temp) {
+        setOperand(0, lhs);
+        setOperand(1, rhs);
+        setTemp(0, temp);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+};
+
+// Returns from the function being compiled (not used in inlined frames). The
+// input must be a box.
+class LReturn : public LInstructionHelper<0, BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(Return)
+};
+
+class LThrow : public LCallInstructionHelper<0, BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(Throw)
+
+    static const size_t Value = 0;
+};
+
+class LMinMaxBase : public LInstructionHelper<1, 2, 0>
+{
+  protected:
+    LMinMaxBase(const LAllocation& first, const LAllocation& second)
+    {
+        setOperand(0, first);
+        setOperand(1, second);
+    }
+
+  public:
+    const LAllocation* first() {
+        return this->getOperand(0);
+    }
+    const LAllocation* second() {
+        return this->getOperand(1);
+    }
+    const LDefinition* output() {
+        return this->getDef(0);
+    }
+    MMinMax* mir() const {
+        return mir_->toMinMax();
+    }
+    const char* extraName() const {
+        return mir()->isMax() ? "Max" : "Min";
+    }
+};
+
+class LMinMaxI : public LMinMaxBase
+{
+  public:
+    LIR_HEADER(MinMaxI)
+    LMinMaxI(const LAllocation& first, const LAllocation& second) : LMinMaxBase(first, second)
+    {}
+};
+
+class LMinMaxD : public LMinMaxBase
+{
+  public:
+    LIR_HEADER(MinMaxD)
+    LMinMaxD(const LAllocation& first, const LAllocation& second) : LMinMaxBase(first, second)
+    {}
+};
+
+class LMinMaxF : public LMinMaxBase
+{
+  public:
+    LIR_HEADER(MinMaxF)
+    LMinMaxF(const LAllocation& first, const LAllocation& second) : LMinMaxBase(first, second)
+    {}
+};
+
+// Negative of an integer
+class LNegI : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(NegI);
+    explicit LNegI(const LAllocation& num) {
+        setOperand(0, num);
+    }
+};
+
+// Negative of a double.
+class LNegD : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(NegD)
+    explicit LNegD(const LAllocation& num) {
+        setOperand(0, num);
+    }
+};
+
+// Negative of a float32.
+class LNegF : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(NegF)
+    explicit LNegF(const LAllocation& num) {
+        setOperand(0, num);
+    }
+};
+
+// Absolute value of an integer.
+class LAbsI : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(AbsI)
+    explicit LAbsI(const LAllocation& num) {
+        setOperand(0, num);
+    }
+};
+
+// Absolute value of a double.
+class LAbsD : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(AbsD)
+    explicit LAbsD(const LAllocation& num) {
+        setOperand(0, num);
+    }
+};
+
+// Absolute value of a float32.
+class LAbsF : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(AbsF)
+    explicit LAbsF(const LAllocation& num) {
+        setOperand(0, num);
+    }
+};
+
+// Count leading zeroes
+class LClzI : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(ClzI)
+    explicit LClzI(const LAllocation& num) {
+        setOperand(0, num);
+    }
+
+    MClz* mir() const {
+        return mir_->toClz();
+    }
+};
+
+// Square root of a double.
+class LSqrtD : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(SqrtD)
+    explicit LSqrtD(const LAllocation& num) {
+        setOperand(0, num);
+    }
+};
+
+// Square root of a float32.
+class LSqrtF : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(SqrtF)
+    explicit LSqrtF(const LAllocation& num) {
+        setOperand(0, num);
+    }
+};
+
+class LAtan2D : public LCallInstructionHelper<1, 2, 1>
+{
+  public:
+    LIR_HEADER(Atan2D)
+    LAtan2D(const LAllocation& y, const LAllocation& x, const LDefinition& temp) {
+        setOperand(0, y);
+        setOperand(1, x);
+        setTemp(0, temp);
+    }
+
+    const LAllocation* y() {
+        return getOperand(0);
+    }
+
+    const LAllocation* x() {
+        return getOperand(1);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    const LDefinition* output() {
+        return getDef(0);
+    }
+};
+
+class LHypot : public LCallInstructionHelper<1, 4, 1>
+{
+    uint32_t numOperands_;
+  public:
+    LIR_HEADER(Hypot)
+    LHypot(const LAllocation& x, const LAllocation& y, const LDefinition& temp)
+      : numOperands_(2)
+    {
+        setOperand(0, x);
+        setOperand(1, y);
+        setTemp(0, temp);
+    }
+
+    LHypot(const LAllocation& x, const LAllocation& y, const LAllocation& z, const LDefinition& temp)
+      : numOperands_(3)
+    {
+        setOperand(0, x);
+        setOperand(1, y);
+        setOperand(2, z);
+        setTemp(0, temp);
+    }
+
+    LHypot(const LAllocation& x, const LAllocation& y, const LAllocation& z, const LAllocation& w, const LDefinition& temp)
+      : numOperands_(4)
+    {
+        setOperand(0, x);
+        setOperand(1, y);
+        setOperand(2, z);
+        setOperand(3, w);
+        setTemp(0, temp);
+    }
+
+    uint32_t numArgs() const { return numOperands_; }
+
+    const LAllocation* x() {
+        return getOperand(0);
+    }
+
+    const LAllocation* y() {
+        return getOperand(1);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+
+    const LDefinition* output() {
+        return getDef(0);
+    }
+};
+
+// Double raised to an integer power.
+class LPowI : public LCallInstructionHelper<1, 2, 1>
+{
+  public:
+    LIR_HEADER(PowI)
+    LPowI(const LAllocation& value, const LAllocation& power, const LDefinition& temp) {
+        setOperand(0, value);
+        setOperand(1, power);
+        setTemp(0, temp);
+    }
+
+    const LAllocation* value() {
+        return getOperand(0);
+    }
+    const LAllocation* power() {
+        return getOperand(1);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+};
+
+// Double raised to a double power.
+class LPowD : public LCallInstructionHelper<1, 2, 1>
+{
+  public:
+    LIR_HEADER(PowD)
+    LPowD(const LAllocation& value, const LAllocation& power, const LDefinition& temp) {
+        setOperand(0, value);
+        setOperand(1, power);
+        setTemp(0, temp);
+    }
+
+    const LAllocation* value() {
+        return getOperand(0);
+    }
+    const LAllocation* power() {
+        return getOperand(1);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+};
+
+class LMathFunctionD : public LCallInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(MathFunctionD)
+    LMathFunctionD(const LAllocation& input, const LDefinition& temp) {
+        setOperand(0, input);
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+    MMathFunction* mir() const {
+        return mir_->toMathFunction();
+    }
+    const char* extraName() const {
+        return MMathFunction::FunctionName(mir()->function());
+    }
+};
+
+class LMathFunctionF : public LCallInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(MathFunctionF)
+    LMathFunctionF(const LAllocation& input, const LDefinition& temp) {
+        setOperand(0, input);
+        setTemp(0, temp);
+    }
+
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+    MMathFunction* mir() const {
+        return mir_->toMathFunction();
+    }
+    const char* extraName() const {
+        return MMathFunction::FunctionName(mir()->function());
+    }
+};
+
+// Adds two integers, returning an integer value.
+class LAddI : public LBinaryMath<0>
+{
+    bool recoversInput_;
+
+  public:
+    LIR_HEADER(AddI)
+
+    LAddI()
+      : recoversInput_(false)
+    { }
+
+    const char* extraName() const {
+        return snapshot() ? "OverflowCheck" : nullptr;
+    }
+
+    virtual bool recoversInput() const {
+        return recoversInput_;
+    }
+    void setRecoversInput() {
+        recoversInput_ = true;
+    }
+
+    MAdd* mir() const {
+        return mir_->toAdd();
+    }
+};
+
+// Subtracts two integers, returning an integer value.
+class LSubI : public LBinaryMath<0>
+{
+    bool recoversInput_;
+
+  public:
+    LIR_HEADER(SubI)
+
+    LSubI()
+      : recoversInput_(false)
+    { }
+
+    const char* extraName() const {
+        return snapshot() ? "OverflowCheck" : nullptr;
+    }
+
+    virtual bool recoversInput() const {
+        return recoversInput_;
+    }
+    void setRecoversInput() {
+        recoversInput_ = true;
+    }
+    MSub* mir() const {
+        return mir_->toSub();
+    }
+};
+
+// Performs an add, sub, mul, or div on two double values.
+class LMathD : public LBinaryMath<0>
+{
+    JSOp jsop_;
+
+  public:
+    LIR_HEADER(MathD)
+
+    explicit LMathD(JSOp jsop)
+      : jsop_(jsop)
+    { }
+
+    JSOp jsop() const {
+        return jsop_;
+    }
+
+    const char* extraName() const {
+        return js_CodeName[jsop_];
+    }
+};
+
+// Performs an add, sub, mul, or div on two double values.
+class LMathF: public LBinaryMath<0>
+{
+    JSOp jsop_;
+
+  public:
+    LIR_HEADER(MathF)
+
+    explicit LMathF(JSOp jsop)
+      : jsop_(jsop)
+    { }
+
+    JSOp jsop() const {
+        return jsop_;
+    }
+
+    const char* extraName() const {
+        return js_CodeName[jsop_];
+    }
+};
+
+class LModD : public LBinaryMath<1>
+{
+  public:
+    LIR_HEADER(ModD)
+
+    LModD(const LAllocation& lhs, const LAllocation& rhs, const LDefinition& temp) {
+        setOperand(0, lhs);
+        setOperand(1, rhs);
+        setTemp(0, temp);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+    bool isCall() const {
+        return true;
+    }
+};
+
+// Call a VM function to perform a binary operation.
+class LBinaryV : public LCallInstructionHelper<BOX_PIECES, 2 * BOX_PIECES, 0>
+{
+    JSOp jsop_;
+
+  public:
+    LIR_HEADER(BinaryV)
+
+    explicit LBinaryV(JSOp jsop)
+      : jsop_(jsop)
+    { }
+
+    JSOp jsop() const {
+        return jsop_;
+    }
+
+    const char* extraName() const {
+        return js_CodeName[jsop_];
+    }
+
+    static const size_t LhsInput = 0;
+    static const size_t RhsInput = BOX_PIECES;
+};
+
+// Adds two string, returning a string.
+class LConcat : public LInstructionHelper<1, 2, 5>
+{
+  public:
+    LIR_HEADER(Concat)
+
+    LConcat(const LAllocation& lhs, const LAllocation& rhs, const LDefinition& temp1,
+            const LDefinition& temp2, const LDefinition& temp3, const LDefinition& temp4,
+            const LDefinition& temp5)
+    {
+        setOperand(0, lhs);
+        setOperand(1, rhs);
+        setTemp(0, temp1);
+        setTemp(1, temp2);
+        setTemp(2, temp3);
+        setTemp(3, temp4);
+        setTemp(4, temp5);
+    }
+
+    const LAllocation* lhs() {
+        return this->getOperand(0);
+    }
+    const LAllocation* rhs() {
+        return this->getOperand(1);
+    }
+    const LDefinition* temp1() {
+        return this->getTemp(0);
+    }
+    const LDefinition* temp2() {
+        return this->getTemp(1);
+    }
+    const LDefinition* temp3() {
+        return this->getTemp(2);
+    }
+    const LDefinition* temp4() {
+        return this->getTemp(3);
+    }
+    const LDefinition* temp5() {
+        return this->getTemp(4);
+    }
+};
+
+// Get uint16 character code from a string.
+class LCharCodeAt : public LInstructionHelper<1, 2, 0>
+{
+  public:
+    LIR_HEADER(CharCodeAt)
+
+    LCharCodeAt(const LAllocation& str, const LAllocation& index) {
+        setOperand(0, str);
+        setOperand(1, index);
+    }
+
+    const LAllocation* str() {
+        return this->getOperand(0);
+    }
+    const LAllocation* index() {
+        return this->getOperand(1);
+    }
+};
+
+// Convert uint16 character code to a string.
+class LFromCharCode : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(FromCharCode)
+
+    explicit LFromCharCode(const LAllocation& code) {
+        setOperand(0, code);
+    }
+
+    const LAllocation* code() {
+        return this->getOperand(0);
+    }
+};
+
+class LStringSplit : public LCallInstructionHelper<1, 2, 0>
+{
+  public:
+    LIR_HEADER(StringSplit)
+
+    LStringSplit(const LAllocation& string, const LAllocation& separator) {
+        setOperand(0, string);
+        setOperand(1, separator);
+    }
+    const LAllocation* string() {
+        return getOperand(0);
+    }
+    const LAllocation* separator() {
+        return getOperand(1);
+    }
+    const MStringSplit* mir() const {
+        return mir_->toStringSplit();
+    }
+};
+
+class LSubstr : public LInstructionHelper<1, 3, 3>
+{
+  public:
+    LIR_HEADER(Substr)
+
+    LSubstr(const LAllocation& string, const LAllocation& begin, const LAllocation& length,
+            const LDefinition& temp, const LDefinition& temp2, const LDefinition& temp3)
+    {
+        setOperand(0, string);
+        setOperand(1, begin);
+        setOperand(2, length);
+        setTemp(0, temp);
+        setTemp(1, temp2);
+        setTemp(2, temp3);
+    }
+    const LAllocation* string() {
+        return getOperand(0);
+    }
+    const LAllocation* begin() {
+        return getOperand(1);
+    }
+    const LAllocation* length() {
+        return getOperand(2);
+    }
+    const LDefinition* temp() {
+        return getTemp(0);
+    }
+    const LDefinition* temp2() {
+        return getTemp(1);
+    }
+    const LDefinition* temp3() {
+        return getTemp(2);
+    }
+    const MStringSplit* mir() const {
+        return mir_->toStringSplit();
+    }
+};
+
+// Convert a 32-bit integer to a double.
+class LInt32ToDouble : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(Int32ToDouble)
+
+    explicit LInt32ToDouble(const LAllocation& input) {
+        setOperand(0, input);
+    }
+};
+
+// Convert a 32-bit float to a double.
+class LFloat32ToDouble : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(Float32ToDouble)
+
+    explicit LFloat32ToDouble(const LAllocation& input) {
+        setOperand(0, input);
+    }
+};
+
+// Convert a double to a 32-bit float.
+class LDoubleToFloat32 : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(DoubleToFloat32)
+
+    explicit LDoubleToFloat32(const LAllocation& input) {
+        setOperand(0, input);
+    }
+};
+
+// Convert a 32-bit integer to a float32.
+class LInt32ToFloat32 : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(Int32ToFloat32)
+
+    explicit LInt32ToFloat32(const LAllocation& input) {
+        setOperand(0, input);
+    }
+};
+
+// Convert a value to a double.
+class LValueToDouble : public LInstructionHelper<1, BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(ValueToDouble)
+    static const size_t Input = 0;
+
+    MToDouble* mir() {
+        return mir_->toToDouble();
+    }
+};
+
+// Convert a value to a float32.
+class LValueToFloat32 : public LInstructionHelper<1, BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(ValueToFloat32)
+    static const size_t Input = 0;
+
+    MToFloat32* mir() {
+        return mir_->toToFloat32();
+    }
+};
+
+// Convert a value to an int32.
+//   Input: components of a Value
+//   Output: 32-bit integer
+//   Bailout: undefined, string, object, or non-int32 double
+//   Temps: one float register, one GP register
+//
+// This instruction requires a temporary float register.
+class LValueToInt32 : public LInstructionHelper<1, BOX_PIECES, 2>
+{
+  public:
+    enum Mode {
+        NORMAL,
+        TRUNCATE
+    };
+
+  private:
+    Mode mode_;
+
+  public:
+    LIR_HEADER(ValueToInt32)
+
+    LValueToInt32(const LDefinition& temp0, const LDefinition& temp1, Mode mode)
+      : mode_(mode)
+    {
+        setTemp(0, temp0);
+        setTemp(1, temp1);
+    }
+
+    const char* extraName() const {
+        return mode() == NORMAL ? "Normal" : "Truncate";
+    }
+
+    static const size_t Input = 0;
+
+    Mode mode() const {
+        return mode_;
+    }
+    const LDefinition* tempFloat() {
+        return getTemp(0);
+    }
+    const LDefinition* temp() {
+        return getTemp(1);
+    }
+    MToInt32* mirNormal() const {
+        MOZ_ASSERT(mode_ == NORMAL);
+        return mir_->toToInt32();
+    }
+    MTruncateToInt32* mirTruncate() const {
+        MOZ_ASSERT(mode_ == TRUNCATE);
+        return mir_->toTruncateToInt32();
+    }
+    MInstruction* mir() const {
+        return mir_->toInstruction();
+    }
+};
+
+// Convert a double to an int32.
+//   Input: floating-point register
+//   Output: 32-bit integer
+//   Bailout: if the double cannot be converted to an integer.
+class LDoubleToInt32 : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(DoubleToInt32)
+
+    explicit LDoubleToInt32(const LAllocation& in) {
+        setOperand(0, in);
+    }
+
+    MToInt32* mir() const {
+        return mir_->toToInt32();
+    }
+};
+
+// Convert a float32 to an int32.
+//   Input: floating-point register
+//   Output: 32-bit integer
+//   Bailout: if the float32 cannot be converted to an integer.
+class LFloat32ToInt32 : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(Float32ToInt32)
+
+    explicit LFloat32ToInt32(const LAllocation& in) {
+        setOperand(0, in);
+    }
+
+    MToInt32* mir() const {
+        return mir_->toToInt32();
+    }
+};
+
+// Convert a double to a truncated int32.
+//   Input: floating-point register
+//   Output: 32-bit integer
+class LTruncateDToInt32 : public LInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(TruncateDToInt32)
+
+    LTruncateDToInt32(const LAllocation& in, const LDefinition& temp) {
+        setOperand(0, in);
+        setTemp(0, temp);
+    }
+
+    const LDefinition* tempFloat() {
+        return getTemp(0);
+    }
+
+    MTruncateToInt32* mir() const {
+        return mir_->toTruncateToInt32();
+    }
+};
+
+// Convert a float32 to a truncated int32.
+//   Input: floating-point register
+//   Output: 32-bit integer
+class LTruncateFToInt32 : public LInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(TruncateFToInt32)
+
+    LTruncateFToInt32(const LAllocation& in, const LDefinition& temp) {
+        setOperand(0, in);
+        setTemp(0, temp);
+    }
+
+    const LDefinition* tempFloat() {
+        return getTemp(0);
+    }
+
+    MTruncateToInt32* mir() const {
+        return mir_->toTruncateToInt32();
+    }
+};
+
+// Convert a boolean value to a string.
+class LBooleanToString : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(BooleanToString)
+
+    explicit LBooleanToString(const LAllocation& input) {
+        setOperand(0, input);
+    }
+
+    const MToString* mir() {
+        return mir_->toToString();
+    }
+};
+
+// Convert an integer hosted on one definition to a string with a function call.
+class LIntToString : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(IntToString)
+
+    explicit LIntToString(const LAllocation& input) {
+        setOperand(0, input);
+    }
+
+    const MToString* mir() {
+        return mir_->toToString();
+    }
+};
+
+// Convert a double hosted on one definition to a string with a function call.
+class LDoubleToString : public LInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(DoubleToString)
+
+    LDoubleToString(const LAllocation& input, const LDefinition& temp) {
+        setOperand(0, input);
+        setTemp(0, temp);
+    }
+
+    const LDefinition* tempInt() {
+        return getTemp(0);
+    }
+    const MToString* mir() {
+        return mir_->toToString();
+    }
+};
+
+// Convert a primitive to a string with a function call.
+class LValueToString : public LInstructionHelper<1, BOX_PIECES, 1>
+{
+  public:
+    LIR_HEADER(ValueToString)
+
+    explicit LValueToString(const LDefinition& tempToUnbox)
+    {
+        setTemp(0, tempToUnbox);
+    }
+
+    static const size_t Input = 0;
+
+    const MToString* mir() {
+        return mir_->toToString();
+    }
+
+    const LDefinition* tempToUnbox() {
+        return getTemp(0);
+    }
+};
+
+// Convert a value to an object or null pointer.
+class LValueToObjectOrNull : public LInstructionHelper<1, BOX_PIECES, 0>
+{
+  public:
+    LIR_HEADER(ValueToObjectOrNull)
+
+    explicit LValueToObjectOrNull()
+    {}
+
+    static const size_t Input = 0;
+
+    const MToObjectOrNull* mir() {
+        return mir_->toToObjectOrNull();
+    }
+};
+
+class LInt32x4ToFloat32x4 : public LInstructionHelper<1, 1, 0>
+{
+  public:
+    LIR_HEADER(Int32x4ToFloat32x4);
+    explicit LInt32x4ToFloat32x4(const LAllocation& input) {
+        setOperand(0, input);
+    }
+};
+
+class LFloat32x4ToInt32x4 : public LInstructionHelper<1, 1, 1>
+{
+  public:
+    LIR_HEADER(Float32x4ToInt32x4);
+    explicit LFloat32x4ToInt32x4(const LAllocation& input, const LDefinition& temp