26#define RISCV_EXPAND_PSEUDO_NAME "RISC-V pseudo instruction expansion pass"
27#define RISCV_PRERA_EXPAND_PSEUDO_NAME "RISC-V Pre-RA pseudo instruction expansion pass"
72char RISCVExpandPseudo::ID = 0;
76 TII = STI->getInstrInfo();
88 assert(OldSize >= NewSize);
112 switch (
MBBI->getOpcode()) {
113 case RISCV::PseudoMV_FPR16INX:
114 return expandMV_FPR16INX(
MBB,
MBBI);
115 case RISCV::PseudoMV_FPR32INX:
116 return expandMV_FPR32INX(
MBB,
MBBI);
117 case RISCV::PseudoRV32ZdinxSD:
118 return expandRV32ZdinxStore(
MBB,
MBBI);
119 case RISCV::PseudoRV32ZdinxLD:
120 return expandRV32ZdinxLoad(
MBB,
MBBI);
121 case RISCV::PseudoCCMOVGPRNoX0:
122 case RISCV::PseudoCCMOVGPR:
123 case RISCV::PseudoCCADD:
124 case RISCV::PseudoCCSUB:
125 case RISCV::PseudoCCAND:
126 case RISCV::PseudoCCOR:
127 case RISCV::PseudoCCXOR:
128 case RISCV::PseudoCCADDW:
129 case RISCV::PseudoCCSUBW:
130 case RISCV::PseudoCCSLL:
131 case RISCV::PseudoCCSRL:
132 case RISCV::PseudoCCSRA:
133 case RISCV::PseudoCCADDI:
134 case RISCV::PseudoCCSLLI:
135 case RISCV::PseudoCCSRLI:
136 case RISCV::PseudoCCSRAI:
137 case RISCV::PseudoCCANDI:
138 case RISCV::PseudoCCORI:
139 case RISCV::PseudoCCXORI:
140 case RISCV::PseudoCCSLLW:
141 case RISCV::PseudoCCSRLW:
142 case RISCV::PseudoCCSRAW:
143 case RISCV::PseudoCCADDIW:
144 case RISCV::PseudoCCSLLIW:
145 case RISCV::PseudoCCSRLIW:
146 case RISCV::PseudoCCSRAIW:
147 case RISCV::PseudoCCANDN:
148 case RISCV::PseudoCCORN:
149 case RISCV::PseudoCCXNOR:
150 case RISCV::PseudoCCNDS_BFOS:
151 case RISCV::PseudoCCNDS_BFOZ:
152 return expandCCOp(
MBB,
MBBI, NextMBBI);
153 case RISCV::PseudoVMCLR_M_B1:
154 case RISCV::PseudoVMCLR_M_B2:
155 case RISCV::PseudoVMCLR_M_B4:
156 case RISCV::PseudoVMCLR_M_B8:
157 case RISCV::PseudoVMCLR_M_B16:
158 case RISCV::PseudoVMCLR_M_B32:
159 case RISCV::PseudoVMCLR_M_B64:
161 return expandVMSET_VMCLR(
MBB,
MBBI, RISCV::VMXOR_MM);
162 case RISCV::PseudoVMSET_M_B1:
163 case RISCV::PseudoVMSET_M_B2:
164 case RISCV::PseudoVMSET_M_B4:
165 case RISCV::PseudoVMSET_M_B8:
166 case RISCV::PseudoVMSET_M_B16:
167 case RISCV::PseudoVMSET_M_B32:
168 case RISCV::PseudoVMSET_M_B64:
170 return expandVMSET_VMCLR(
MBB,
MBBI, RISCV::VMXNOR_MM);
171 case RISCV::PseudoReadVLENBViaVSETVLIX0:
172 return expandPseudoReadVLENBViaVSETVLIX0(
MBB,
MBBI);
205 assert(
MI.getOperand(4).getReg() == DestReg);
207 if (
MI.getOpcode() == RISCV::PseudoCCMOVGPR ||
208 MI.getOpcode() == RISCV::PseudoCCMOVGPRNoX0) {
211 .
add(
MI.getOperand(5))
215 switch (
MI.getOpcode()) {
218 case RISCV::PseudoCCADD: NewOpc = RISCV::ADD;
break;
219 case RISCV::PseudoCCSUB: NewOpc = RISCV::SUB;
break;
220 case RISCV::PseudoCCSLL: NewOpc = RISCV::SLL;
break;
221 case RISCV::PseudoCCSRL: NewOpc = RISCV::SRL;
break;
222 case RISCV::PseudoCCSRA: NewOpc = RISCV::SRA;
break;
223 case RISCV::PseudoCCAND: NewOpc = RISCV::AND;
break;
224 case RISCV::PseudoCCOR: NewOpc = RISCV::OR;
break;
225 case RISCV::PseudoCCXOR: NewOpc = RISCV::XOR;
break;
226 case RISCV::PseudoCCADDI: NewOpc = RISCV::ADDI;
break;
227 case RISCV::PseudoCCSLLI: NewOpc = RISCV::SLLI;
break;
228 case RISCV::PseudoCCSRLI: NewOpc = RISCV::SRLI;
break;
229 case RISCV::PseudoCCSRAI: NewOpc = RISCV::SRAI;
break;
230 case RISCV::PseudoCCANDI: NewOpc = RISCV::ANDI;
break;
231 case RISCV::PseudoCCORI: NewOpc = RISCV::ORI;
break;
232 case RISCV::PseudoCCXORI: NewOpc = RISCV::XORI;
break;
233 case RISCV::PseudoCCADDW: NewOpc = RISCV::ADDW;
break;
234 case RISCV::PseudoCCSUBW: NewOpc = RISCV::SUBW;
break;
235 case RISCV::PseudoCCSLLW: NewOpc = RISCV::SLLW;
break;
236 case RISCV::PseudoCCSRLW: NewOpc = RISCV::SRLW;
break;
237 case RISCV::PseudoCCSRAW: NewOpc = RISCV::SRAW;
break;
238 case RISCV::PseudoCCADDIW: NewOpc = RISCV::ADDIW;
break;
239 case RISCV::PseudoCCSLLIW: NewOpc = RISCV::SLLIW;
break;
240 case RISCV::PseudoCCSRLIW: NewOpc = RISCV::SRLIW;
break;
241 case RISCV::PseudoCCSRAIW: NewOpc = RISCV::SRAIW;
break;
242 case RISCV::PseudoCCANDN: NewOpc = RISCV::ANDN;
break;
243 case RISCV::PseudoCCORN: NewOpc = RISCV::ORN;
break;
244 case RISCV::PseudoCCXNOR: NewOpc = RISCV::XNOR;
break;
245 case RISCV::PseudoCCNDS_BFOS: NewOpc = RISCV::NDS_BFOS;
break;
246 case RISCV::PseudoCCNDS_BFOZ: NewOpc = RISCV::NDS_BFOZ;
break;
249 if (NewOpc == RISCV::NDS_BFOZ || NewOpc == RISCV::NDS_BFOS) {
251 .
add(
MI.getOperand(5))
252 .
add(
MI.getOperand(6))
253 .
add(
MI.getOperand(7));
256 .
add(
MI.getOperand(5))
257 .
add(
MI.getOperand(6));
270 MI.eraseFromParent();
298 MBBI->getOperand(0).getReg(), RISCV::sub_16, &RISCV::GPRRegClass);
300 MBBI->getOperand(1).getReg(), RISCV::sub_16, &RISCV::GPRRegClass);
315 MBBI->getOperand(0).getReg(), RISCV::sub_32, &RISCV::GPRRegClass);
317 MBBI->getOperand(1).getReg(), RISCV::sub_32, &RISCV::GPRRegClass);
335 TRI->getSubReg(
MBBI->getOperand(0).getReg(), RISCV::sub_gpr_even);
337 TRI->getSubReg(
MBBI->getOperand(0).getReg(), RISCV::sub_gpr_odd);
338 if (
Hi == RISCV::DUMMY_REG_PAIR_WITH_X0)
347 if (
MBBI->getOperand(2).isGlobal() ||
MBBI->getOperand(2).isCPI()) {
348 assert(
MBBI->getOperand(2).getOffset() % 8 == 0);
349 MBBI->getOperand(2).setOffset(
MBBI->getOperand(2).getOffset() + 4);
355 assert(isInt<12>(
MBBI->getOperand(2).getImm() + 4));
369 MIBLo.setMemRefs(NewLoMMOs);
384 TRI->getSubReg(
MBBI->getOperand(0).getReg(), RISCV::sub_gpr_even);
386 TRI->getSubReg(
MBBI->getOperand(0).getReg(), RISCV::sub_gpr_odd);
387 assert(
Hi != RISCV::DUMMY_REG_PAIR_WITH_X0 &&
"Cannot write to X0_Pair");
393 bool IsOp1EqualToLo =
Lo ==
MBBI->getOperand(1).getReg();
395 if (!IsOp1EqualToLo) {
401 if (
MBBI->getOperand(2).isGlobal() ||
MBBI->getOperand(2).isCPI()) {
402 auto Offset =
MBBI->getOperand(2).getOffset();
410 assert(isInt<12>(
MBBI->getOperand(2).getImm() + 4));
417 if (IsOp1EqualToLo) {
437bool RISCVExpandPseudo::expandPseudoReadVLENBViaVSETVLIX0(
441 unsigned Mul =
MBBI->getOperand(1).getImm();
444 VLMUL, 8,
true,
true);
480 unsigned FlagsHi,
unsigned SecondOpcode);
508char RISCVPreRAExpandPseudo::ID = 0;
510bool RISCVPreRAExpandPseudo::runOnMachineFunction(
MachineFunction &MF) {
512 TII = STI->getInstrInfo();
524 assert(OldSize >= NewSize);
546 switch (
MBBI->getOpcode()) {
547 case RISCV::PseudoLLA:
548 return expandLoadLocalAddress(
MBB,
MBBI, NextMBBI);
549 case RISCV::PseudoLGA:
550 return expandLoadGlobalAddress(
MBB,
MBBI, NextMBBI);
551 case RISCV::PseudoLA_TLS_IE:
552 return expandLoadTLSIEAddress(
MBB,
MBBI, NextMBBI);
553 case RISCV::PseudoLA_TLS_GD:
554 return expandLoadTLSGDAddress(
MBB,
MBBI, NextMBBI);
555 case RISCV::PseudoLA_TLSDESC:
556 return expandLoadTLSDescAddress(
MBB,
MBBI, NextMBBI);
561bool RISCVPreRAExpandPseudo::expandAuipcInstPair(
564 unsigned SecondOpcode) {
574 Symbol.setTargetFlags(FlagsHi);
586 if (
MI.hasOneMemOperand())
589 MI.eraseFromParent();
593bool RISCVPreRAExpandPseudo::expandLoadLocalAddress(
600bool RISCVPreRAExpandPseudo::expandLoadGlobalAddress(
603 unsigned SecondOpcode = STI->is64Bit() ? RISCV::LD : RISCV::LW;
608bool RISCVPreRAExpandPseudo::expandLoadTLSIEAddress(
611 unsigned SecondOpcode = STI->is64Bit() ? RISCV::LD : RISCV::LW;
616bool RISCVPreRAExpandPseudo::expandLoadTLSGDAddress(
623bool RISCVPreRAExpandPseudo::expandLoadTLSDescAddress(
631 unsigned SecondOpcode = STI.is64Bit() ? RISCV::LD : RISCV::LW;
633 Register FinalReg =
MI.getOperand(0).getReg();
664 MI.eraseFromParent();
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
MachineBasicBlock MachineBasicBlock::iterator MBBI
static Expected< BitVector > expand(StringRef S, StringRef Original)
const HexagonInstrInfo * TII
This file implements the LivePhysRegs utility for tracking liveness of physical registers.
Register const TargetRegisterInfo * TRI
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
#define RISCV_PRERA_EXPAND_PSEUDO_NAME
#define RISCV_EXPAND_PSEUDO_NAME
riscv prera expand pseudo
static unsigned getInstSizeInBytes(const MachineInstr &MI, const SystemZInstrInfo *TII)
support::ulittle16_t & Lo
support::ulittle16_t & Hi
Represent the analysis usage information of a pass.
LLVM_ABI void setPreservesCFG()
This function should be called by the pass, iff they do not:
FunctionPass class - This class is used to implement most global optimizations.
A set of physical registers with utility functions to track liveness when walking backward/forward th...
LLVM_ABI MCSymbol * createNamedTempSymbol()
Create a temporary symbol with a unique name whose name cannot be omitted in the symbol table.
Describe properties that are true of each instruction in the target description file.
MCSymbol - Instances of this class represent a symbol name in the MC file, and MCSymbols are created ...
LLVM_ABI void transferSuccessors(MachineBasicBlock *FromMBB)
Transfers all the successors from MBB to this machine basic block (i.e., copies all the successors Fr...
const BasicBlock * getBasicBlock() const
Return the LLVM basic block that this instance corresponded to originally.
LLVM_ABI void addSuccessor(MachineBasicBlock *Succ, BranchProbability Prob=BranchProbability::getUnknown())
Add Succ as a successor of this MachineBasicBlock.
LLVM_ABI void eraseFromParent()
This method unlinks 'this' from the containing function and deletes it.
const MachineFunction * getParent() const
Return the MachineFunction containing this basic block.
void splice(iterator Where, MachineBasicBlock *Other, iterator From)
Take an instruction from MBB 'Other' at the position From, and insert it into this MBB right before '...
MachineFunctionPass - This class adapts the FunctionPass interface to allow convenient creation of pa...
void getAnalysisUsage(AnalysisUsage &AU) const override
getAnalysisUsage - Subclasses that override getAnalysisUsage must call this.
virtual bool runOnMachineFunction(MachineFunction &MF)=0
runOnMachineFunction - This method must be overloaded to perform the desired machine code transformat...
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
MachineMemOperand * getMachineMemOperand(MachinePointerInfo PtrInfo, MachineMemOperand::Flags f, LLT MemTy, Align base_alignment, const AAMDNodes &AAInfo=AAMDNodes(), const MDNode *Ranges=nullptr, SyncScope::ID SSID=SyncScope::System, AtomicOrdering Ordering=AtomicOrdering::NotAtomic, AtomicOrdering FailureOrdering=AtomicOrdering::NotAtomic)
getMachineMemOperand - Allocate a new MachineMemOperand.
MCContext & getContext() const
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
MachineBasicBlock * CreateMachineBasicBlock(const BasicBlock *BB=nullptr, std::optional< UniqueBBID > BBID=std::nullopt)
CreateMachineBasicBlock - Allocate a new MachineBasicBlock.
void insert(iterator MBBI, MachineBasicBlock *MBB)
const MachineInstrBuilder & setMemRefs(ArrayRef< MachineMemOperand * > MMOs) const
const MachineInstrBuilder & addImm(int64_t Val) const
Add a new immediate operand.
const MachineInstrBuilder & add(const MachineOperand &MO) const
const MachineInstrBuilder & addSym(MCSymbol *Sym, unsigned char TargetFlags=0) const
const MachineInstrBuilder & addReg(Register RegNo, unsigned flags=0, unsigned SubReg=0) const
Add a new virtual register operand.
const MachineInstrBuilder & addMBB(MachineBasicBlock *MBB, unsigned TargetFlags=0) const
Representation of each machine instruction.
LLVM_ABI void setPreInstrSymbol(MachineFunction &MF, MCSymbol *Symbol)
Set a symbol that will be emitted just prior to the instruction itself.
LLVM_ABI void addMemOperand(MachineFunction &MF, MachineMemOperand *MO)
Add a MachineMemOperand to the machine instruction.
A description of a memory reference used in the backend.
MachineOperand class - Representation of each machine instruction operand.
LLVM_ABI Register createVirtualRegister(const TargetRegisterClass *RegClass, StringRef Name="")
createVirtualRegister - Create and return a new virtual register in the function with the specified r...
virtual StringRef getPassName() const
getPassName - Return a nice clean name for a pass.
Wrapper class representing virtual and physical registers.
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
StringRef - Represent a constant reference to a string, i.e.
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
self_iterator getIterator()
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
CondCode getOppositeBranchCondition(CondCode)
unsigned getBrCond(CondCode CC, unsigned SelectOpc=0)
static VLMUL encodeLMUL(unsigned LMUL, bool Fractional)
LLVM_ABI unsigned encodeVTYPE(VLMUL VLMUL, unsigned SEW, bool TailAgnostic, bool MaskAgnostic, bool AltFmt=false)
@ Define
Register definition.
@ Kill
The last use of a register.
@ Undef
Value of the register doesn't matter.
This is an optimization pass for GlobalISel generic memory operations.
MachineInstrBuilder BuildMI(MachineFunction &MF, const MIMetadata &MIMD, const MCInstrDesc &MCID)
Builder interface. Specify how to create the initial instruction itself.
unsigned getKillRegState(bool B)
void computeAndAddLiveIns(LivePhysRegs &LiveRegs, MachineBasicBlock &MBB)
Convenience function combining computeLiveIns() and addLiveIns().
FunctionPass * createRISCVExpandPseudoPass()
FunctionPass * createRISCVPreRAExpandPseudoPass()
Description of the encoding of one expression Op.