Home | History | Annotate | Download | only in R600
      1 //===-- AMDGPUInstrInfo.h - AMDGPU Instruction Information ------*- C++ -*-===//
      2 //
      3 //                     The LLVM Compiler Infrastructure
      4 //
      5 // This file is distributed under the University of Illinois Open Source
      6 // License. See LICENSE.TXT for details.
      7 //
      8 //===----------------------------------------------------------------------===//
      9 //
     10 /// \file
     11 /// \brief Contains the definition of a TargetInstrInfo class that is common
     12 /// to all AMD GPUs.
     13 //
     14 //===----------------------------------------------------------------------===//
     15 
     16 #ifndef AMDGPUINSTRUCTIONINFO_H
     17 #define AMDGPUINSTRUCTIONINFO_H
     18 
     19 #include "AMDGPUInstrInfo.h"
     20 #include "AMDGPURegisterInfo.h"
     21 #include "llvm/Target/TargetInstrInfo.h"
     22 #include <map>
     23 
     24 #define GET_INSTRINFO_HEADER
     25 #define GET_INSTRINFO_ENUM
     26 #define GET_INSTRINFO_OPERAND_ENUM
     27 #include "AMDGPUGenInstrInfo.inc"
     28 
     29 #define OPCODE_IS_ZERO_INT AMDGPU::PRED_SETE_INT
     30 #define OPCODE_IS_NOT_ZERO_INT AMDGPU::PRED_SETNE_INT
     31 #define OPCODE_IS_ZERO AMDGPU::PRED_SETE
     32 #define OPCODE_IS_NOT_ZERO AMDGPU::PRED_SETNE
     33 
     34 namespace llvm {
     35 
     36 class AMDGPUSubtarget;
     37 class MachineFunction;
     38 class MachineInstr;
     39 class MachineInstrBuilder;
     40 
     41 class AMDGPUInstrInfo : public AMDGPUGenInstrInfo {
     42 private:
     43   const AMDGPURegisterInfo RI;
     44   bool getNextBranchInstr(MachineBasicBlock::iterator &iter,
     45                           MachineBasicBlock &MBB) const;
     46   virtual void anchor();
     47 protected:
     48   const AMDGPUSubtarget &ST;
     49 public:
     50   explicit AMDGPUInstrInfo(const AMDGPUSubtarget &st);
     51 
     52   virtual const AMDGPURegisterInfo &getRegisterInfo() const = 0;
     53 
     54   bool isCoalescableExtInstr(const MachineInstr &MI, unsigned &SrcReg,
     55                              unsigned &DstReg, unsigned &SubIdx) const override;
     56 
     57   unsigned isLoadFromStackSlot(const MachineInstr *MI,
     58                                int &FrameIndex) const override;
     59   unsigned isLoadFromStackSlotPostFE(const MachineInstr *MI,
     60                                      int &FrameIndex) const override;
     61   bool hasLoadFromStackSlot(const MachineInstr *MI,
     62                             const MachineMemOperand *&MMO,
     63                             int &FrameIndex) const override;
     64   unsigned isStoreFromStackSlot(const MachineInstr *MI, int &FrameIndex) const;
     65   unsigned isStoreFromStackSlotPostFE(const MachineInstr *MI,
     66                                       int &FrameIndex) const;
     67   bool hasStoreFromStackSlot(const MachineInstr *MI,
     68                              const MachineMemOperand *&MMO,
     69                              int &FrameIndex) const;
     70 
     71   MachineInstr *
     72   convertToThreeAddress(MachineFunction::iterator &MFI,
     73                         MachineBasicBlock::iterator &MBBI,
     74                         LiveVariables *LV) const override;
     75 
     76 
     77   virtual void copyPhysReg(MachineBasicBlock &MBB,
     78                            MachineBasicBlock::iterator MI, DebugLoc DL,
     79                            unsigned DestReg, unsigned SrcReg,
     80                            bool KillSrc) const = 0;
     81 
     82   bool expandPostRAPseudo(MachineBasicBlock::iterator MI) const override;
     83 
     84   void storeRegToStackSlot(MachineBasicBlock &MBB,
     85                            MachineBasicBlock::iterator MI,
     86                            unsigned SrcReg, bool isKill, int FrameIndex,
     87                            const TargetRegisterClass *RC,
     88                            const TargetRegisterInfo *TRI) const override;
     89   void loadRegFromStackSlot(MachineBasicBlock &MBB,
     90                             MachineBasicBlock::iterator MI,
     91                             unsigned DestReg, int FrameIndex,
     92                             const TargetRegisterClass *RC,
     93                             const TargetRegisterInfo *TRI) const override;
     94 
     95 protected:
     96   MachineInstr *foldMemoryOperandImpl(MachineFunction &MF,
     97                                       MachineInstr *MI,
     98                                       const SmallVectorImpl<unsigned> &Ops,
     99                                       int FrameIndex) const override;
    100   MachineInstr *foldMemoryOperandImpl(MachineFunction &MF,
    101                                       MachineInstr *MI,
    102                                       const SmallVectorImpl<unsigned> &Ops,
    103                                       MachineInstr *LoadMI) const override;
    104   /// \returns the smallest register index that will be accessed by an indirect
    105   /// read or write or -1 if indirect addressing is not used by this program.
    106   int getIndirectIndexBegin(const MachineFunction &MF) const;
    107 
    108   /// \returns the largest register index that will be accessed by an indirect
    109   /// read or write or -1 if indirect addressing is not used by this program.
    110   int getIndirectIndexEnd(const MachineFunction &MF) const;
    111 
    112 public:
    113   bool canFoldMemoryOperand(const MachineInstr *MI,
    114                            const SmallVectorImpl<unsigned> &Ops) const override;
    115   bool unfoldMemoryOperand(MachineFunction &MF, MachineInstr *MI,
    116                         unsigned Reg, bool UnfoldLoad, bool UnfoldStore,
    117                         SmallVectorImpl<MachineInstr *> &NewMIs) const override;
    118   bool unfoldMemoryOperand(SelectionDAG &DAG, SDNode *N,
    119                            SmallVectorImpl<SDNode *> &NewNodes) const override;
    120   unsigned getOpcodeAfterMemoryUnfold(unsigned Opc,
    121                                bool UnfoldLoad, bool UnfoldStore,
    122                                unsigned *LoadRegIndex = nullptr) const override;
    123   bool shouldScheduleLoadsNear(SDNode *Load1, SDNode *Load2,
    124                                int64_t Offset1, int64_t Offset2,
    125                                unsigned NumLoads) const override;
    126 
    127   bool
    128   ReverseBranchCondition(SmallVectorImpl<MachineOperand> &Cond) const override;
    129   void insertNoop(MachineBasicBlock &MBB,
    130                   MachineBasicBlock::iterator MI) const override;
    131   bool isPredicated(const MachineInstr *MI) const override;
    132   bool SubsumesPredicate(const SmallVectorImpl<MachineOperand> &Pred1,
    133                    const SmallVectorImpl<MachineOperand> &Pred2) const override;
    134   bool DefinesPredicate(MachineInstr *MI,
    135                         std::vector<MachineOperand> &Pred) const override;
    136   bool isPredicable(MachineInstr *MI) const override;
    137   bool isSafeToMoveRegClassDefs(const TargetRegisterClass *RC) const override;
    138 
    139   // Helper functions that check the opcode for status information
    140   bool isRegisterStore(const MachineInstr &MI) const;
    141   bool isRegisterLoad(const MachineInstr &MI) const;
    142 
    143 //===---------------------------------------------------------------------===//
    144 // Pure virtual funtions to be implemented by sub-classes.
    145 //===---------------------------------------------------------------------===//
    146 
    147   virtual unsigned getIEQOpcode() const = 0;
    148   virtual bool isMov(unsigned opcode) const = 0;
    149 
    150   /// \brief Calculate the "Indirect Address" for the given \p RegIndex and
    151   ///        \p Channel
    152   ///
    153   /// We model indirect addressing using a virtual address space that can be
    154   /// accesed with loads and stores.  The "Indirect Address" is the memory
    155   /// address in this virtual address space that maps to the given \p RegIndex
    156   /// and \p Channel.
    157   virtual unsigned calculateIndirectAddress(unsigned RegIndex,
    158                                             unsigned Channel) const = 0;
    159 
    160   /// \returns The register class to be used for loading and storing values
    161   /// from an "Indirect Address" .
    162   virtual const TargetRegisterClass *getIndirectAddrRegClass() const = 0;
    163 
    164   /// \brief Build instruction(s) for an indirect register write.
    165   ///
    166   /// \returns The instruction that performs the indirect register write
    167   virtual MachineInstrBuilder buildIndirectWrite(MachineBasicBlock *MBB,
    168                                     MachineBasicBlock::iterator I,
    169                                     unsigned ValueReg, unsigned Address,
    170                                     unsigned OffsetReg) const = 0;
    171 
    172   /// \brief Build instruction(s) for an indirect register read.
    173   ///
    174   /// \returns The instruction that performs the indirect register read
    175   virtual MachineInstrBuilder buildIndirectRead(MachineBasicBlock *MBB,
    176                                     MachineBasicBlock::iterator I,
    177                                     unsigned ValueReg, unsigned Address,
    178                                     unsigned OffsetReg) const = 0;
    179 
    180   /// \brief Build a MOV instruction.
    181   virtual MachineInstr *buildMovInstr(MachineBasicBlock *MBB,
    182                                       MachineBasicBlock::iterator I,
    183                                       unsigned DstReg, unsigned SrcReg) const = 0;
    184 
    185   /// \brief Given a MIMG \p Opcode that writes all 4 channels, return the
    186   /// equivalent opcode that writes \p Channels Channels.
    187   int getMaskedMIMGOp(uint16_t Opcode, unsigned Channels) const;
    188 
    189 };
    190 
    191 namespace AMDGPU {
    192   int16_t getNamedOperandIdx(uint16_t Opcode, uint16_t NamedIndex);
    193 }  // End namespace AMDGPU
    194 
    195 } // End llvm namespace
    196 
    197 #define AMDGPU_FLAG_REGISTER_LOAD  (UINT64_C(1) << 63)
    198 #define AMDGPU_FLAG_REGISTER_STORE (UINT64_C(1) << 62)
    199 
    200 #endif // AMDGPUINSTRINFO_H
    201