Skip to content

Commit e9e7ff3

Browse files
committed
Try to use foldMemoryOperand from optimizeLoadInstr
1 parent 1466e68 commit e9e7ff3

File tree

5 files changed

+86
-79
lines changed

5 files changed

+86
-79
lines changed

llvm/include/llvm/CodeGen/TargetInstrInfo.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1700,7 +1700,7 @@ class TargetInstrInfo : public MCInstrInfo {
17001700
/// instruction that defines FoldAsLoadDefReg, and the function returns
17011701
/// the machine instruction generated due to folding.
17021702
virtual MachineInstr *optimizeLoadInstr(MachineInstr &MI,
1703-
MachineRegisterInfo *MRI,
1703+
const MachineRegisterInfo *MRI,
17041704
Register &FoldAsLoadDefReg,
17051705
MachineInstr *&DefMI) const {
17061706
return nullptr;

llvm/lib/Target/SystemZ/SystemZInstrInfo.cpp

Lines changed: 82 additions & 75 deletions
Original file line numberDiff line numberDiff line change
@@ -625,12 +625,9 @@ static void transferMIFlag(MachineInstr *OldMI, MachineInstr *NewMI,
625625
}
626626

627627
MachineInstr *SystemZInstrInfo::optimizeLoadInstr(MachineInstr &MI,
628-
MachineRegisterInfo *MRI,
628+
const MachineRegisterInfo *MRI,
629629
Register &FoldAsLoadDefReg,
630630
MachineInstr *&DefMI) const {
631-
const TargetRegisterInfo *TRI = MRI->getTargetRegisterInfo();
632-
MachineBasicBlock *MBB = MI.getParent();
633-
634631
// Check whether we can move the DefMI load, and that it only has one use.
635632
DefMI = MRI->getVRegDef(FoldAsLoadDefReg);
636633
assert(DefMI);
@@ -639,76 +636,9 @@ MachineInstr *SystemZInstrInfo::optimizeLoadInstr(MachineInstr &MI,
639636
!MRI->hasOneNonDBGUse(FoldAsLoadDefReg))
640637
return nullptr;
641638

642-
// For reassociable FP operations, any loads have been purposefully left
643-
// unfolded so that MachineCombiner can do its work on reg/reg
644-
// opcodes. After that, as many loads as possible are now folded.
645-
// TODO: This may be beneficial with other opcodes as well as machine-sink
646-
// can move loads close to their user in a different MBB.
647-
unsigned LoadOpc = 0;
648-
unsigned RegMemOpcode = 0;
649-
const TargetRegisterClass *FPRC = nullptr;
650-
RegMemOpcode = MI.getOpcode() == SystemZ::WFADB ? SystemZ::ADB
651-
: MI.getOpcode() == SystemZ::WFSDB ? SystemZ::SDB
652-
: MI.getOpcode() == SystemZ::WFMDB ? SystemZ::MDB
653-
: 0;
654-
if (RegMemOpcode) {
655-
LoadOpc = SystemZ::VL64;
656-
FPRC = &SystemZ::FP64BitRegClass;
657-
} else {
658-
RegMemOpcode = MI.getOpcode() == SystemZ::WFASB ? SystemZ::AEB
659-
: MI.getOpcode() == SystemZ::WFSSB ? SystemZ::SEB
660-
: MI.getOpcode() == SystemZ::WFMSB ? SystemZ::MEEB
661-
: 0;
662-
if (RegMemOpcode) {
663-
LoadOpc = SystemZ::VL32;
664-
FPRC = &SystemZ::FP32BitRegClass;
665-
}
666-
}
667-
if (!RegMemOpcode || DefMI->getOpcode() != LoadOpc)
668-
return nullptr;
669-
670-
// If RegMemOpcode clobbers CC, first make sure CC is not live at this point.
671-
if (get(RegMemOpcode).hasImplicitDefOfPhysReg(SystemZ::CC)) {
672-
assert(DefMI->getParent() == MI.getParent() && "Assuming a local fold.");
673-
for (MachineBasicBlock::iterator MII = std::prev(MI.getIterator());;
674-
--MII) {
675-
if (MII->definesRegister(SystemZ::CC)) {
676-
if (!MII->registerDefIsDead(SystemZ::CC))
677-
return nullptr;
678-
break;
679-
}
680-
if (MII == MBB->begin()) {
681-
if (MBB->isLiveIn(SystemZ::CC))
682-
return nullptr;
683-
break;
684-
}
685-
}
686-
}
687-
688-
Register DstReg = MI.getOperand(0).getReg();
689-
MachineOperand LHS = MI.getOperand(1);
690-
MachineOperand RHS = MI.getOperand(2);
691-
MachineOperand &RegMO = RHS.getReg() == FoldAsLoadDefReg ? LHS : RHS;
692-
if ((RegMemOpcode == SystemZ::SDB || RegMemOpcode == SystemZ::SEB) &&
693-
FoldAsLoadDefReg != RHS.getReg())
694-
return nullptr;
695-
696-
MachineOperand &Base = DefMI->getOperand(1);
697-
MachineOperand &Disp = DefMI->getOperand(2);
698-
MachineOperand &Indx = DefMI->getOperand(3);
699-
MachineInstrBuilder MIB =
700-
BuildMI(*MI.getParent(), MI, MI.getDebugLoc(), get(RegMemOpcode), DstReg)
701-
.add(RegMO)
702-
.add(Base)
703-
.add(Disp)
704-
.add(Indx)
705-
.addMemOperand(*DefMI->memoperands_begin());
706-
MIB->addRegisterDead(SystemZ::CC, TRI);
707-
MRI->setRegClass(DstReg, FPRC);
708-
MRI->setRegClass(RegMO.getReg(), FPRC);
709-
transferMIFlag(&MI, MIB, MachineInstr::NoFPExcept);
710-
711-
return MIB;
639+
int UseOpIdx = MI.findRegisterUseOperandIdx(FoldAsLoadDefReg);
640+
assert(UseOpIdx != -1 && "Expected FoldAsLoadDefReg to be used by MI.");
641+
return foldMemoryOperand(MI, {((unsigned) UseOpIdx)}, *DefMI);
712642
}
713643

714644
bool SystemZInstrInfo::foldImmediate(MachineInstr &UseMI, MachineInstr &DefMI,
@@ -1484,7 +1414,84 @@ MachineInstr *SystemZInstrInfo::foldMemoryOperandImpl(
14841414
MachineFunction &MF, MachineInstr &MI, ArrayRef<unsigned> Ops,
14851415
MachineBasicBlock::iterator InsertPt, MachineInstr &LoadMI,
14861416
LiveIntervals *LIS) const {
1487-
return nullptr;
1417+
MachineRegisterInfo *MRI = &MF.getRegInfo();
1418+
MachineBasicBlock *MBB = MI.getParent();
1419+
1420+
// For reassociable FP operations, any loads have been purposefully left
1421+
// unfolded so that MachineCombiner can do its work on reg/reg
1422+
// opcodes. After that, as many loads as possible are now folded.
1423+
// TODO: This may be beneficial with other opcodes as well as machine-sink
1424+
// can move loads close to their user in a different MBB, which the isel
1425+
// matcher did not see.
1426+
unsigned LoadOpc = 0;
1427+
unsigned RegMemOpcode = 0;
1428+
const TargetRegisterClass *FPRC = nullptr;
1429+
RegMemOpcode = MI.getOpcode() == SystemZ::WFADB ? SystemZ::ADB
1430+
: MI.getOpcode() == SystemZ::WFSDB ? SystemZ::SDB
1431+
: MI.getOpcode() == SystemZ::WFMDB ? SystemZ::MDB
1432+
: 0;
1433+
if (RegMemOpcode) {
1434+
LoadOpc = SystemZ::VL64;
1435+
FPRC = &SystemZ::FP64BitRegClass;
1436+
} else {
1437+
RegMemOpcode = MI.getOpcode() == SystemZ::WFASB ? SystemZ::AEB
1438+
: MI.getOpcode() == SystemZ::WFSSB ? SystemZ::SEB
1439+
: MI.getOpcode() == SystemZ::WFMSB ? SystemZ::MEEB
1440+
: 0;
1441+
if (RegMemOpcode) {
1442+
LoadOpc = SystemZ::VL32;
1443+
FPRC = &SystemZ::FP32BitRegClass;
1444+
}
1445+
}
1446+
if (!RegMemOpcode || LoadMI.getOpcode() != LoadOpc)
1447+
return nullptr;
1448+
1449+
// If RegMemOpcode clobbers CC, first make sure CC is not live at this point.
1450+
if (get(RegMemOpcode).hasImplicitDefOfPhysReg(SystemZ::CC)) {
1451+
assert(LoadMI.getParent() == MI.getParent() && "Assuming a local fold.");
1452+
assert(LoadMI != InsertPt && "Assuming InsertPt not to be first in MBB.");
1453+
for (MachineBasicBlock::iterator MII = std::prev(InsertPt);;
1454+
--MII) {
1455+
if (MII->definesRegister(SystemZ::CC)) {
1456+
if (!MII->registerDefIsDead(SystemZ::CC))
1457+
return nullptr;
1458+
break;
1459+
}
1460+
if (MII == MBB->begin()) {
1461+
if (MBB->isLiveIn(SystemZ::CC))
1462+
return nullptr;
1463+
break;
1464+
}
1465+
}
1466+
}
1467+
1468+
Register FoldAsLoadDefReg = LoadMI.getOperand(0).getReg();
1469+
// We don't really need Ops, but do a sanity check:
1470+
assert(Ops.size() == 1 && FoldAsLoadDefReg == MI.getOperand(Ops[0]).getReg() &&
1471+
"Expected MI to be the only user of the load.");
1472+
Register DstReg = MI.getOperand(0).getReg();
1473+
MachineOperand LHS = MI.getOperand(1);
1474+
MachineOperand RHS = MI.getOperand(2);
1475+
MachineOperand &RegMO = RHS.getReg() == FoldAsLoadDefReg ? LHS : RHS;
1476+
if ((RegMemOpcode == SystemZ::SDB || RegMemOpcode == SystemZ::SEB) &&
1477+
FoldAsLoadDefReg != RHS.getReg())
1478+
return nullptr;
1479+
1480+
MachineOperand &Base = LoadMI.getOperand(1);
1481+
MachineOperand &Disp = LoadMI.getOperand(2);
1482+
MachineOperand &Indx = LoadMI.getOperand(3);
1483+
MachineInstrBuilder MIB =
1484+
BuildMI(*MI.getParent(), InsertPt, MI.getDebugLoc(), get(RegMemOpcode), DstReg)
1485+
.add(RegMO)
1486+
.add(Base)
1487+
.add(Disp)
1488+
.add(Indx);
1489+
MIB->addRegisterDead(SystemZ::CC, &RI);
1490+
MRI->setRegClass(DstReg, FPRC);
1491+
MRI->setRegClass(RegMO.getReg(), FPRC);
1492+
transferMIFlag(&MI, MIB, MachineInstr::NoFPExcept);
1493+
1494+
return MIB;
14881495
}
14891496

14901497
bool SystemZInstrInfo::expandPostRAPseudo(MachineInstr &MI) const {

llvm/lib/Target/SystemZ/SystemZInstrInfo.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -255,7 +255,7 @@ class SystemZInstrInfo : public SystemZGenInstrInfo {
255255
ArrayRef<MachineOperand> Cond, Register TrueReg,
256256
Register FalseReg) const override;
257257
MachineInstr *optimizeLoadInstr(MachineInstr &MI,
258-
MachineRegisterInfo *MRI,
258+
const MachineRegisterInfo *MRI,
259259
Register &FoldAsLoadDefReg,
260260
MachineInstr *&DefMI) const override;
261261
bool foldImmediate(MachineInstr &UseMI, MachineInstr &DefMI, Register Reg,

llvm/lib/Target/X86/X86InstrInfo.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5498,7 +5498,7 @@ bool X86InstrInfo::optimizeCompareInstr(MachineInstr &CmpInstr, Register SrcReg,
54985498
/// register, the virtual register is used once in the same BB, and the
54995499
/// instructions in-between do not load or store, and have no side effects.
55005500
MachineInstr *X86InstrInfo::optimizeLoadInstr(MachineInstr &MI,
5501-
MachineRegisterInfo *MRI,
5501+
const MachineRegisterInfo *MRI,
55025502
Register &FoldAsLoadDefReg,
55035503
MachineInstr *&DefMI) const {
55045504
// Check whether we can move DefMI here.

llvm/lib/Target/X86/X86InstrInfo.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -559,7 +559,7 @@ class X86InstrInfo final : public X86GenInstrInfo {
559559
const MachineRegisterInfo *MRI) const override;
560560

561561
MachineInstr *optimizeLoadInstr(MachineInstr &MI,
562-
MachineRegisterInfo *MRI,
562+
const MachineRegisterInfo *MRI,
563563
Register &FoldAsLoadDefReg,
564564
MachineInstr *&DefMI) const override;
565565

0 commit comments

Comments
 (0)