/* -*- 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_Lowering_shared_h
#define jit_shared_Lowering_shared_h

// This file declares the structures that are used for attaching LIR to a
// MIRGraph.

#include "jit/IonAllocPolicy.h"
#include "jit/LIR.h"

namespace js {
namespace jit {

class MBasicBlock;
class MTableSwitch;
class MIRGenerator;
class MIRGraph;
class MDefinition;
class MInstruction;
class LOsiPoint;

class LIRGeneratorShared : public MInstructionVisitorWithDefaults
{
  protected:
    MIRGenerator *gen;
    MIRGraph &graph;
    LIRGraph &lirGraph_;
    LBlock *current;
    MResumePoint *lastResumePoint_;
    LOsiPoint *osiPoint_;

  public:
    LIRGeneratorShared(MIRGenerator *gen, MIRGraph &graph, LIRGraph &lirGraph)
      : gen(gen),
        graph(graph),
        lirGraph_(lirGraph),
        lastResumePoint_(NULL),
        osiPoint_(NULL)
    { }

    MIRGenerator *mir() {
        return gen;
    }

  protected:
    // A backend can decide that an instruction should be emitted at its uses,
    // rather than at its definition. To communicate this, set the
    // instruction's virtual register set to 0. When using the instruction,
    // its virtual register is temporarily reassigned. To know to clear it
    // after constructing the use information, the worklist bit is temporarily
    // unset.
    //
    // The backend can use the worklist bit to determine whether or not a
    // definition should be created.
    inline bool emitAtUses(MInstruction *mir);

    // The lowest-level calls to use, those that do not wrap another call to
    // use(), must prefix grabbing virtual register IDs by these calls.
    inline bool ensureDefined(MDefinition *mir);

    // These all create a use of a virtual register, with an optional
    // allocation policy.
    inline LUse use(MDefinition *mir, LUse policy);
    inline LUse use(MDefinition *mir);
    inline LUse useAtStart(MDefinition *mir);
    inline LUse useRegister(MDefinition *mir);
    inline LUse useRegisterAtStart(MDefinition *mir);
    inline LUse useFixed(MDefinition *mir, Register reg);
    inline LUse useFixed(MDefinition *mir, FloatRegister reg);
    inline LUse useFixed(MDefinition *mir, AnyRegister reg);
    inline LAllocation useOrConstant(MDefinition *mir);
    // "Any" is architecture dependent, and will include registers and stack slots on X86,
    // and only registers on ARM.
    inline LAllocation useAny(MDefinition *mir);
    inline LAllocation useAnyOrConstant(MDefinition *mir);
    // "Storable" is architecture dependend, and will include registers and constants on X86
    // and only registers on ARM.
    // this is a generic "things we can expect to write into memory in 1 instruction"
    inline LAllocation useStorable(MDefinition *mir);
    inline LAllocation useStorableAtStart(MDefinition *mir);
    inline LAllocation useKeepaliveOrConstant(MDefinition *mir);
    inline LAllocation useRegisterOrConstant(MDefinition *mir);
    inline LAllocation useRegisterOrConstantAtStart(MDefinition *mir);
    inline LAllocation useRegisterOrNonDoubleConstant(MDefinition *mir);

#ifdef JS_NUNBOX32
    inline LUse useType(MDefinition *mir, LUse::Policy policy);
    inline LUse usePayload(MDefinition *mir, LUse::Policy policy);
    inline LUse usePayloadAtStart(MDefinition *mir, LUse::Policy policy);
    inline LUse usePayloadInRegisterAtStart(MDefinition *mir);

    // Adds a box input to an instruction, setting operand |n| to the type and
    // |n+1| to the payload. Does not modify the operands, instead expecting a
    // policy to already be set.
    inline bool fillBoxUses(LInstruction *lir, size_t n, MDefinition *mir);
#endif

    // These create temporary register requests.
    inline LDefinition temp(LDefinition::Type type = LDefinition::GENERAL,
                            LDefinition::Policy policy = LDefinition::DEFAULT);
    inline LDefinition tempFloat();
    inline LDefinition tempCopy(MDefinition *input, uint32_t reusedInput);

    // Note that the fixed register has a GENERAL type.
    inline LDefinition tempFixed(Register reg);

    template <size_t Ops, size_t Temps>
    inline bool defineFixed(LInstructionHelper<1, Ops, Temps> *lir, MDefinition *mir,
                            const LAllocation &output);

    template <size_t Ops, size_t Temps>
    inline bool defineBox(LInstructionHelper<BOX_PIECES, Ops, Temps> *lir, MDefinition *mir,
                          LDefinition::Policy policy = LDefinition::DEFAULT);

    inline bool defineReturn(LInstruction *lir, MDefinition *mir);

    template <size_t Ops, size_t Temps>
    inline bool define(LInstructionHelper<1, Ops, Temps> *lir, MDefinition *mir,
                        const LDefinition &def);

    template <size_t Ops, size_t Temps>
    inline bool define(LInstructionHelper<1, Ops, Temps> *lir, MDefinition *mir,
                       LDefinition::Policy policy = LDefinition::DEFAULT);

    template <size_t Ops, size_t Temps>
    inline bool defineReuseInput(LInstructionHelper<1, Ops, Temps> *lir, MDefinition *mir, uint32_t operand);

    // Rather than defining a new virtual register, sets |ins| to have the same
    // virtual register as |as|.
    inline bool redefine(MDefinition *ins, MDefinition *as);

    // Defines an IR's output as the same as another IR. This is similar to
    // redefine(), but used when creating new LIR.
    inline bool defineAs(LInstruction *outLir, MDefinition *outMir, MDefinition *inMir);

    uint32_t getVirtualRegister() {
        return lirGraph_.getVirtualRegister();
    }

    template <typename T> void annotate(T *ins);
    template <typename T> bool add(T *ins, MInstruction *mir = NULL);

    void lowerTypedPhiInput(MPhi *phi, uint32_t inputPosition, LBlock *block, size_t lirIndex);
    bool defineTypedPhi(MPhi *phi, size_t lirIndex);

    LOsiPoint *popOsiPoint() {
        LOsiPoint *tmp = osiPoint_;
        osiPoint_ = NULL;
        return tmp;
    }

    LSnapshot *buildSnapshot(LInstruction *ins, MResumePoint *rp, BailoutKind kind);
    bool assignPostSnapshot(MInstruction *mir, LInstruction *ins);

    // Marks this instruction as fallible, meaning that before it performs
    // effects (if any), it may check pre-conditions and bailout if they do not
    // hold. This function informs the register allocator that it will need to
    // capture appropriate state.
    bool assignSnapshot(LInstruction *ins, BailoutKind kind = Bailout_Normal);

    // Marks this instruction as needing to call into either the VM or GC. This
    // function may build a snapshot that captures the result of its own
    // instruction, and as such, should generally be called after define*().
    bool assignSafepoint(LInstruction *ins, MInstruction *mir);

  public:
    bool visitConstant(MConstant *ins);

    // Whether to generate typed reads for element accesses with hole checks.
    static bool allowTypedElementHoleCheck() {
        return false;
    }

    // Whether to generate typed array accesses on statically known objects.
    static bool allowStaticTypedArrayAccesses() {
        return false;
    }
};

} // namespace jit
} // namespace js

#endif /* jit_shared_Lowering_shared_h */
