1 //===- LanaiInstrInfo.h - Lanai Instruction Information ---------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file contains the Lanai implementation of the TargetInstrInfo class. 10 // 11 //===----------------------------------------------------------------------===// 12 13 #ifndef LLVM_LIB_TARGET_LANAI_LANAIINSTRINFO_H 14 #define LLVM_LIB_TARGET_LANAI_LANAIINSTRINFO_H 15 16 #include "LanaiRegisterInfo.h" 17 #include "MCTargetDesc/LanaiMCTargetDesc.h" 18 #include "llvm/CodeGen/TargetInstrInfo.h" 19 20 #define GET_INSTRINFO_HEADER 21 #include "LanaiGenInstrInfo.inc" 22 23 namespace llvm { 24 25 class LanaiInstrInfo : public LanaiGenInstrInfo { 26 const LanaiRegisterInfo RegisterInfo; 27 28 public: 29 LanaiInstrInfo(); 30 31 // getRegisterInfo - TargetInstrInfo is a superset of MRegister info. As 32 // such, whenever a client has an instance of instruction info, it should 33 // always be able to get register info as well (through this method). 34 virtual const LanaiRegisterInfo &getRegisterInfo() const { 35 return RegisterInfo; 36 } 37 38 bool areMemAccessesTriviallyDisjoint(const MachineInstr &MIa, 39 const MachineInstr &MIb) const override; 40 41 unsigned isLoadFromStackSlot(const MachineInstr &MI, 42 int &FrameIndex) const override; 43 44 unsigned isLoadFromStackSlotPostFE(const MachineInstr &MI, 45 int &FrameIndex) const override; 46 47 unsigned isStoreToStackSlot(const MachineInstr &MI, 48 int &FrameIndex) const override; 49 50 void copyPhysReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator Position, 51 const DebugLoc &DL, MCRegister DestinationRegister, 52 MCRegister SourceRegister, bool KillSource) const override; 53 54 void storeRegToStackSlot(MachineBasicBlock &MBB, 55 MachineBasicBlock::iterator Position, 56 Register SourceRegister, bool IsKill, int FrameIndex, 57 const TargetRegisterClass *RegisterClass, 58 const TargetRegisterInfo *RegisterInfo, 59 Register VReg) const override; 60 61 void loadRegFromStackSlot(MachineBasicBlock &MBB, 62 MachineBasicBlock::iterator Position, 63 Register DestinationRegister, int FrameIndex, 64 const TargetRegisterClass *RegisterClass, 65 const TargetRegisterInfo *RegisterInfo, 66 Register VReg) const override; 67 68 bool expandPostRAPseudo(MachineInstr &MI) const override; 69 70 bool getMemOperandsWithOffsetWidth( 71 const MachineInstr &LdSt, 72 SmallVectorImpl<const MachineOperand *> &BaseOps, int64_t &Offset, 73 bool &OffsetIsScalable, unsigned &Width, 74 const TargetRegisterInfo *TRI) const override; 75 76 bool getMemOperandWithOffsetWidth(const MachineInstr &LdSt, 77 const MachineOperand *&BaseOp, 78 int64_t &Offset, unsigned &Width, 79 const TargetRegisterInfo *TRI) const; 80 81 std::pair<unsigned, unsigned> 82 decomposeMachineOperandsTargetFlags(unsigned TF) const override; 83 84 ArrayRef<std::pair<unsigned, const char *>> 85 getSerializableDirectMachineOperandTargetFlags() const override; 86 87 bool analyzeBranch(MachineBasicBlock &MBB, MachineBasicBlock *&TrueBlock, 88 MachineBasicBlock *&FalseBlock, 89 SmallVectorImpl<MachineOperand> &Condition, 90 bool AllowModify) const override; 91 92 unsigned removeBranch(MachineBasicBlock &MBB, 93 int *BytesRemoved = nullptr) const override; 94 95 // For a comparison instruction, return the source registers in SrcReg and 96 // SrcReg2 if having two register operands, and the value it compares against 97 // in CmpValue. Return true if the comparison instruction can be analyzed. 98 bool analyzeCompare(const MachineInstr &MI, Register &SrcReg, 99 Register &SrcReg2, int64_t &CmpMask, 100 int64_t &CmpValue) const override; 101 102 // See if the comparison instruction can be converted into something more 103 // efficient. E.g., on Lanai register-register instructions can set the flag 104 // register, obviating the need for a separate compare. 105 bool optimizeCompareInstr(MachineInstr &CmpInstr, Register SrcReg, 106 Register SrcReg2, int64_t CmpMask, int64_t CmpValue, 107 const MachineRegisterInfo *MRI) const override; 108 109 // Analyze the given select instruction, returning true if it cannot be 110 // understood. It is assumed that MI->isSelect() is true. 111 // 112 // When successful, return the controlling condition and the operands that 113 // determine the true and false result values. 114 // 115 // Result = SELECT Cond, TrueOp, FalseOp 116 // 117 // Lanai can optimize certain select instructions, for example by predicating 118 // the instruction defining one of the operands and sets Optimizable to true. 119 bool analyzeSelect(const MachineInstr &MI, 120 SmallVectorImpl<MachineOperand> &Cond, unsigned &TrueOp, 121 unsigned &FalseOp, bool &Optimizable) const override; 122 123 // Given a select instruction that was understood by analyzeSelect and 124 // returned Optimizable = true, attempt to optimize MI by merging it with one 125 // of its operands. Returns NULL on failure. 126 // 127 // When successful, returns the new select instruction. The client is 128 // responsible for deleting MI. 129 // 130 // If both sides of the select can be optimized, the TrueOp is modifed. 131 // PreferFalse is not used. 132 MachineInstr *optimizeSelect(MachineInstr &MI, 133 SmallPtrSetImpl<MachineInstr *> &SeenMIs, 134 bool PreferFalse) const override; 135 136 bool reverseBranchCondition( 137 SmallVectorImpl<MachineOperand> &Condition) const override; 138 139 unsigned insertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TrueBlock, 140 MachineBasicBlock *FalseBlock, 141 ArrayRef<MachineOperand> Condition, 142 const DebugLoc &DL, 143 int *BytesAdded = nullptr) const override; 144 }; 145 146 static inline bool isSPLSOpcode(unsigned Opcode) { 147 switch (Opcode) { 148 case Lanai::LDBs_RI: 149 case Lanai::LDBz_RI: 150 case Lanai::LDHs_RI: 151 case Lanai::LDHz_RI: 152 case Lanai::STB_RI: 153 case Lanai::STH_RI: 154 return true; 155 default: 156 return false; 157 } 158 } 159 160 static inline bool isRMOpcode(unsigned Opcode) { 161 switch (Opcode) { 162 case Lanai::LDW_RI: 163 case Lanai::SW_RI: 164 return true; 165 default: 166 return false; 167 } 168 } 169 170 static inline bool isRRMOpcode(unsigned Opcode) { 171 switch (Opcode) { 172 case Lanai::LDBs_RR: 173 case Lanai::LDBz_RR: 174 case Lanai::LDHs_RR: 175 case Lanai::LDHz_RR: 176 case Lanai::LDWz_RR: 177 case Lanai::LDW_RR: 178 case Lanai::STB_RR: 179 case Lanai::STH_RR: 180 case Lanai::SW_RR: 181 return true; 182 default: 183 return false; 184 } 185 } 186 187 } // namespace llvm 188 189 #endif // LLVM_LIB_TARGET_LANAI_LANAIINSTRINFO_H 190