Skip to content

Commit 260a641

Browse files
committed
[RISCV] Pre-RA expand pseudos pass
Expand load address pseudo-instructions earlier (pre-ra) to allow follow-up patches to fold the addi of PseudoLLA instructions into the immediate operand of load/store instructions. Differential Revision: https://reviews.llvm.org/D123264
1 parent 883fccc commit 260a641

15 files changed

+340
-324
lines changed

llvm/include/llvm/CodeGen/MachineInstr.h

+2
Original file line numberDiff line numberDiff line change
@@ -923,6 +923,8 @@ class MachineInstr
923923
/// For example, if the instruction has a unique labels attached
924924
/// to it, duplicating it would cause multiple definition errors.
925925
bool isNotDuplicable(QueryType Type = AnyInBundle) const {
926+
if (getPreInstrSymbol() || getPostInstrSymbol())
927+
return true;
926928
return hasProperty(MCID::NotDuplicable, Type);
927929
}
928930

llvm/lib/CodeGen/MachineInstr.cpp

+5
Original file line numberDiff line numberDiff line change
@@ -630,6 +630,11 @@ bool MachineInstr::isIdenticalTo(const MachineInstr &Other,
630630
if (getDebugLoc() && Other.getDebugLoc() &&
631631
getDebugLoc() != Other.getDebugLoc())
632632
return false;
633+
// If pre- or post-instruction symbols do not match then the two instructions
634+
// are not identical.
635+
if (getPreInstrSymbol() != Other.getPreInstrSymbol() ||
636+
getPostInstrSymbol() != Other.getPostInstrSymbol())
637+
return false;
633638
return true;
634639
}
635640

llvm/lib/Target/RISCV/RISCV.h

+3
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,9 @@ void initializeRISCVMergeBaseOffsetOptPass(PassRegistry &);
5656
FunctionPass *createRISCVExpandPseudoPass();
5757
void initializeRISCVExpandPseudoPass(PassRegistry &);
5858

59+
FunctionPass *createRISCVPreRAExpandPseudoPass();
60+
void initializeRISCVPreRAExpandPseudoPass(PassRegistry &);
61+
5962
FunctionPass *createRISCVExpandAtomicPseudoPass();
6063
void initializeRISCVExpandAtomicPseudoPass(PassRegistry &);
6164

llvm/lib/Target/RISCV/RISCVExpandPseudoInsts.cpp

+157-108
Original file line numberDiff line numberDiff line change
@@ -19,10 +19,12 @@
1919
#include "llvm/CodeGen/LivePhysRegs.h"
2020
#include "llvm/CodeGen/MachineFunctionPass.h"
2121
#include "llvm/CodeGen/MachineInstrBuilder.h"
22+
#include "llvm/MC/MCContext.h"
2223

2324
using namespace llvm;
2425

2526
#define RISCV_EXPAND_PSEUDO_NAME "RISCV pseudo instruction expansion pass"
27+
#define RISCV_PRERA_EXPAND_PSEUDO_NAME "RISCV Pre-RA pseudo instruction expansion pass"
2628

2729
namespace {
2830

@@ -43,22 +45,6 @@ class RISCVExpandPseudo : public MachineFunctionPass {
4345
bool expandMBB(MachineBasicBlock &MBB);
4446
bool expandMI(MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
4547
MachineBasicBlock::iterator &NextMBBI);
46-
bool expandAuipcInstPair(MachineBasicBlock &MBB,
47-
MachineBasicBlock::iterator MBBI,
48-
MachineBasicBlock::iterator &NextMBBI,
49-
unsigned FlagsHi, unsigned SecondOpcode);
50-
bool expandLoadLocalAddress(MachineBasicBlock &MBB,
51-
MachineBasicBlock::iterator MBBI,
52-
MachineBasicBlock::iterator &NextMBBI);
53-
bool expandLoadAddress(MachineBasicBlock &MBB,
54-
MachineBasicBlock::iterator MBBI,
55-
MachineBasicBlock::iterator &NextMBBI);
56-
bool expandLoadTLSIEAddress(MachineBasicBlock &MBB,
57-
MachineBasicBlock::iterator MBBI,
58-
MachineBasicBlock::iterator &NextMBBI);
59-
bool expandLoadTLSGDAddress(MachineBasicBlock &MBB,
60-
MachineBasicBlock::iterator MBBI,
61-
MachineBasicBlock::iterator &NextMBBI);
6248
bool expandVSetVL(MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI);
6349
bool expandVMSET_VMCLR(MachineBasicBlock &MBB,
6450
MachineBasicBlock::iterator MBBI, unsigned Opcode);
@@ -96,14 +82,6 @@ bool RISCVExpandPseudo::expandMI(MachineBasicBlock &MBB,
9682
// expanded instructions for each pseudo is correct in the Size field of the
9783
// tablegen definition for the pseudo.
9884
switch (MBBI->getOpcode()) {
99-
case RISCV::PseudoLLA:
100-
return expandLoadLocalAddress(MBB, MBBI, NextMBBI);
101-
case RISCV::PseudoLA:
102-
return expandLoadAddress(MBB, MBBI, NextMBBI);
103-
case RISCV::PseudoLA_TLS_IE:
104-
return expandLoadTLSIEAddress(MBB, MBBI, NextMBBI);
105-
case RISCV::PseudoLA_TLS_GD:
106-
return expandLoadTLSGDAddress(MBB, MBBI, NextMBBI);
10785
case RISCV::PseudoVSETVLI:
10886
case RISCV::PseudoVSETVLIX0:
10987
case RISCV::PseudoVSETIVLI:
@@ -155,90 +133,6 @@ bool RISCVExpandPseudo::expandMI(MachineBasicBlock &MBB,
155133
return false;
156134
}
157135

158-
bool RISCVExpandPseudo::expandAuipcInstPair(
159-
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
160-
MachineBasicBlock::iterator &NextMBBI, unsigned FlagsHi,
161-
unsigned SecondOpcode) {
162-
MachineFunction *MF = MBB.getParent();
163-
MachineInstr &MI = *MBBI;
164-
DebugLoc DL = MI.getDebugLoc();
165-
166-
Register DestReg = MI.getOperand(0).getReg();
167-
const MachineOperand &Symbol = MI.getOperand(1);
168-
169-
MachineBasicBlock *NewMBB = MF->CreateMachineBasicBlock(MBB.getBasicBlock());
170-
171-
// Tell AsmPrinter that we unconditionally want the symbol of this label to be
172-
// emitted.
173-
NewMBB->setLabelMustBeEmitted();
174-
175-
MF->insert(++MBB.getIterator(), NewMBB);
176-
177-
BuildMI(NewMBB, DL, TII->get(RISCV::AUIPC), DestReg)
178-
.addDisp(Symbol, 0, FlagsHi);
179-
BuildMI(NewMBB, DL, TII->get(SecondOpcode), DestReg)
180-
.addReg(DestReg)
181-
.addMBB(NewMBB, RISCVII::MO_PCREL_LO);
182-
183-
// Move all the rest of the instructions to NewMBB.
184-
NewMBB->splice(NewMBB->end(), &MBB, std::next(MBBI), MBB.end());
185-
// Update machine-CFG edges.
186-
NewMBB->transferSuccessorsAndUpdatePHIs(&MBB);
187-
// Make the original basic block fall-through to the new.
188-
MBB.addSuccessor(NewMBB);
189-
190-
// Make sure live-ins are correctly attached to this new basic block.
191-
LivePhysRegs LiveRegs;
192-
computeAndAddLiveIns(LiveRegs, *NewMBB);
193-
194-
NextMBBI = MBB.end();
195-
MI.eraseFromParent();
196-
return true;
197-
}
198-
199-
bool RISCVExpandPseudo::expandLoadLocalAddress(
200-
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
201-
MachineBasicBlock::iterator &NextMBBI) {
202-
return expandAuipcInstPair(MBB, MBBI, NextMBBI, RISCVII::MO_PCREL_HI,
203-
RISCV::ADDI);
204-
}
205-
206-
bool RISCVExpandPseudo::expandLoadAddress(
207-
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
208-
MachineBasicBlock::iterator &NextMBBI) {
209-
MachineFunction *MF = MBB.getParent();
210-
211-
unsigned SecondOpcode;
212-
unsigned FlagsHi;
213-
if (MF->getTarget().isPositionIndependent()) {
214-
const auto &STI = MF->getSubtarget<RISCVSubtarget>();
215-
SecondOpcode = STI.is64Bit() ? RISCV::LD : RISCV::LW;
216-
FlagsHi = RISCVII::MO_GOT_HI;
217-
} else {
218-
SecondOpcode = RISCV::ADDI;
219-
FlagsHi = RISCVII::MO_PCREL_HI;
220-
}
221-
return expandAuipcInstPair(MBB, MBBI, NextMBBI, FlagsHi, SecondOpcode);
222-
}
223-
224-
bool RISCVExpandPseudo::expandLoadTLSIEAddress(
225-
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
226-
MachineBasicBlock::iterator &NextMBBI) {
227-
MachineFunction *MF = MBB.getParent();
228-
229-
const auto &STI = MF->getSubtarget<RISCVSubtarget>();
230-
unsigned SecondOpcode = STI.is64Bit() ? RISCV::LD : RISCV::LW;
231-
return expandAuipcInstPair(MBB, MBBI, NextMBBI, RISCVII::MO_TLS_GOT_HI,
232-
SecondOpcode);
233-
}
234-
235-
bool RISCVExpandPseudo::expandLoadTLSGDAddress(
236-
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
237-
MachineBasicBlock::iterator &NextMBBI) {
238-
return expandAuipcInstPair(MBB, MBBI, NextMBBI, RISCVII::MO_TLS_GD_HI,
239-
RISCV::ADDI);
240-
}
241-
242136
bool RISCVExpandPseudo::expandVSetVL(MachineBasicBlock &MBB,
243137
MachineBasicBlock::iterator MBBI) {
244138
assert(MBBI->getNumExplicitOperands() == 3 && MBBI->getNumOperands() >= 5 &&
@@ -377,12 +271,167 @@ bool RISCVExpandPseudo::expandVRELOAD(MachineBasicBlock &MBB,
377271
return true;
378272
}
379273

274+
class RISCVPreRAExpandPseudo : public MachineFunctionPass {
275+
public:
276+
const RISCVInstrInfo *TII;
277+
static char ID;
278+
279+
RISCVPreRAExpandPseudo() : MachineFunctionPass(ID) {
280+
initializeRISCVPreRAExpandPseudoPass(*PassRegistry::getPassRegistry());
281+
}
282+
283+
bool runOnMachineFunction(MachineFunction &MF) override;
284+
285+
void getAnalysisUsage(AnalysisUsage &AU) const override {
286+
AU.setPreservesCFG();
287+
MachineFunctionPass::getAnalysisUsage(AU);
288+
}
289+
StringRef getPassName() const override {
290+
return RISCV_PRERA_EXPAND_PSEUDO_NAME;
291+
}
292+
293+
private:
294+
bool expandMBB(MachineBasicBlock &MBB);
295+
bool expandMI(MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
296+
MachineBasicBlock::iterator &NextMBBI);
297+
bool expandAuipcInstPair(MachineBasicBlock &MBB,
298+
MachineBasicBlock::iterator MBBI,
299+
MachineBasicBlock::iterator &NextMBBI,
300+
unsigned FlagsHi, unsigned SecondOpcode);
301+
bool expandLoadLocalAddress(MachineBasicBlock &MBB,
302+
MachineBasicBlock::iterator MBBI,
303+
MachineBasicBlock::iterator &NextMBBI);
304+
bool expandLoadAddress(MachineBasicBlock &MBB,
305+
MachineBasicBlock::iterator MBBI,
306+
MachineBasicBlock::iterator &NextMBBI);
307+
bool expandLoadTLSIEAddress(MachineBasicBlock &MBB,
308+
MachineBasicBlock::iterator MBBI,
309+
MachineBasicBlock::iterator &NextMBBI);
310+
bool expandLoadTLSGDAddress(MachineBasicBlock &MBB,
311+
MachineBasicBlock::iterator MBBI,
312+
MachineBasicBlock::iterator &NextMBBI);
313+
};
314+
315+
char RISCVPreRAExpandPseudo::ID = 0;
316+
317+
bool RISCVPreRAExpandPseudo::runOnMachineFunction(MachineFunction &MF) {
318+
TII = static_cast<const RISCVInstrInfo *>(MF.getSubtarget().getInstrInfo());
319+
bool Modified = false;
320+
for (auto &MBB : MF)
321+
Modified |= expandMBB(MBB);
322+
return Modified;
323+
}
324+
325+
bool RISCVPreRAExpandPseudo::expandMBB(MachineBasicBlock &MBB) {
326+
bool Modified = false;
327+
328+
MachineBasicBlock::iterator MBBI = MBB.begin(), E = MBB.end();
329+
while (MBBI != E) {
330+
MachineBasicBlock::iterator NMBBI = std::next(MBBI);
331+
Modified |= expandMI(MBB, MBBI, NMBBI);
332+
MBBI = NMBBI;
333+
}
334+
335+
return Modified;
336+
}
337+
338+
bool RISCVPreRAExpandPseudo::expandMI(MachineBasicBlock &MBB,
339+
MachineBasicBlock::iterator MBBI,
340+
MachineBasicBlock::iterator &NextMBBI) {
341+
342+
switch (MBBI->getOpcode()) {
343+
case RISCV::PseudoLLA:
344+
return expandLoadLocalAddress(MBB, MBBI, NextMBBI);
345+
case RISCV::PseudoLA:
346+
return expandLoadAddress(MBB, MBBI, NextMBBI);
347+
case RISCV::PseudoLA_TLS_IE:
348+
return expandLoadTLSIEAddress(MBB, MBBI, NextMBBI);
349+
case RISCV::PseudoLA_TLS_GD:
350+
return expandLoadTLSGDAddress(MBB, MBBI, NextMBBI);
351+
}
352+
return false;
353+
}
354+
355+
bool RISCVPreRAExpandPseudo::expandAuipcInstPair(
356+
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
357+
MachineBasicBlock::iterator &NextMBBI, unsigned FlagsHi,
358+
unsigned SecondOpcode) {
359+
MachineFunction *MF = MBB.getParent();
360+
MachineInstr &MI = *MBBI;
361+
DebugLoc DL = MI.getDebugLoc();
362+
363+
Register DestReg = MI.getOperand(0).getReg();
364+
Register ScratchReg =
365+
MF->getRegInfo().createVirtualRegister(&RISCV::GPRRegClass);
366+
367+
MachineOperand &Symbol = MI.getOperand(1);
368+
Symbol.setTargetFlags(FlagsHi);
369+
MCSymbol *AUIPCSymbol = MF->getContext().createNamedTempSymbol("pcrel_hi");
370+
371+
MachineInstr *MIAUIPC =
372+
BuildMI(MBB, MBBI, DL, TII->get(RISCV::AUIPC), ScratchReg).add(Symbol);
373+
MIAUIPC->setPreInstrSymbol(*MF, AUIPCSymbol);
374+
375+
MachineInstr *SecondMI =
376+
BuildMI(MBB, MBBI, DL, TII->get(SecondOpcode), DestReg)
377+
.addReg(ScratchReg)
378+
.addSym(AUIPCSymbol, RISCVII::MO_PCREL_LO);
379+
380+
if (MI.hasOneMemOperand())
381+
SecondMI->addMemOperand(*MF, *MI.memoperands_begin());
382+
383+
MI.eraseFromParent();
384+
return true;
385+
}
386+
387+
bool RISCVPreRAExpandPseudo::expandLoadLocalAddress(
388+
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
389+
MachineBasicBlock::iterator &NextMBBI) {
390+
return expandAuipcInstPair(MBB, MBBI, NextMBBI, RISCVII::MO_PCREL_HI,
391+
RISCV::ADDI);
392+
}
393+
394+
bool RISCVPreRAExpandPseudo::expandLoadAddress(
395+
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
396+
MachineBasicBlock::iterator &NextMBBI) {
397+
MachineFunction *MF = MBB.getParent();
398+
399+
assert(MF->getTarget().isPositionIndependent());
400+
const auto &STI = MF->getSubtarget<RISCVSubtarget>();
401+
unsigned SecondOpcode = STI.is64Bit() ? RISCV::LD : RISCV::LW;
402+
return expandAuipcInstPair(MBB, MBBI, NextMBBI, RISCVII::MO_GOT_HI,
403+
SecondOpcode);
404+
}
405+
406+
bool RISCVPreRAExpandPseudo::expandLoadTLSIEAddress(
407+
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
408+
MachineBasicBlock::iterator &NextMBBI) {
409+
MachineFunction *MF = MBB.getParent();
410+
411+
const auto &STI = MF->getSubtarget<RISCVSubtarget>();
412+
unsigned SecondOpcode = STI.is64Bit() ? RISCV::LD : RISCV::LW;
413+
return expandAuipcInstPair(MBB, MBBI, NextMBBI, RISCVII::MO_TLS_GOT_HI,
414+
SecondOpcode);
415+
}
416+
417+
bool RISCVPreRAExpandPseudo::expandLoadTLSGDAddress(
418+
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
419+
MachineBasicBlock::iterator &NextMBBI) {
420+
return expandAuipcInstPair(MBB, MBBI, NextMBBI, RISCVII::MO_TLS_GD_HI,
421+
RISCV::ADDI);
422+
}
423+
380424
} // end of anonymous namespace
381425

382426
INITIALIZE_PASS(RISCVExpandPseudo, "riscv-expand-pseudo",
383427
RISCV_EXPAND_PSEUDO_NAME, false, false)
428+
429+
INITIALIZE_PASS(RISCVPreRAExpandPseudo, "riscv-prera-expand-pseudo",
430+
RISCV_PRERA_EXPAND_PSEUDO_NAME, false, false)
431+
384432
namespace llvm {
385433

386434
FunctionPass *createRISCVExpandPseudoPass() { return new RISCVExpandPseudo(); }
435+
FunctionPass *createRISCVPreRAExpandPseudoPass() { return new RISCVPreRAExpandPseudo(); }
387436

388437
} // end of namespace llvm

llvm/lib/Target/RISCV/RISCVMCInstLower.cpp

+3
Original file line numberDiff line numberDiff line change
@@ -125,6 +125,9 @@ bool llvm::lowerRISCVMachineOperandToMCOperand(const MachineOperand &MO,
125125
case MachineOperand::MO_JumpTableIndex:
126126
MCOp = lowerSymbolOperand(MO, AP.GetJTISymbol(MO.getIndex()), AP);
127127
break;
128+
case MachineOperand::MO_MCSymbol:
129+
MCOp = lowerSymbolOperand(MO, MO.getMCSymbol(), AP);
130+
break;
128131
}
129132
return true;
130133
}

llvm/lib/Target/RISCV/RISCVTargetMachine.cpp

+2
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@ extern "C" LLVM_EXTERNAL_VISIBILITY void LLVMInitializeRISCVTarget() {
5252
initializeRISCVCodeGenPreparePass(*PR);
5353
initializeRISCVMergeBaseOffsetOptPass(*PR);
5454
initializeRISCVSExtWRemovalPass(*PR);
55+
initializeRISCVPreRAExpandPseudoPass(*PR);
5556
initializeRISCVExpandPseudoPass(*PR);
5657
initializeRISCVInsertVSETVLIPass(*PR);
5758
}
@@ -253,6 +254,7 @@ void RISCVPassConfig::addMachineSSAOptimization() {
253254

254255
if (TM->getTargetTriple().getArch() == Triple::riscv64)
255256
addPass(createRISCVSExtWRemovalPass());
257+
addPass(createRISCVPreRAExpandPseudoPass());
256258
}
257259

258260
void RISCVPassConfig::addPreRegAlloc() {

llvm/test/CodeGen/RISCV/O3-pipeline.ll

+1
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,7 @@
9696
; CHECK-NEXT: Peephole Optimizations
9797
; CHECK-NEXT: Remove dead machine instructions
9898
; RV64-NEXT: RISCV sext.w Removal
99+
; CHECK-NEXT: RISCV Pre-RA pseudo instruction expansion pass
99100
; CHECK-NEXT: RISCV Merge Base Offset
100101
; CHECK-NEXT: RISCV Insert VSETVLI pass
101102
; CHECK-NEXT: Detect Dead Lanes

0 commit comments

Comments
 (0)