Skip to content

Commit fdc4ea3

Browse files
committed
[SystemZ, RegAlloc] Favor 3-address instructions during instruction selection.
This patch aims to reduce spilling and register moves by using the 3-address versions of instructions per default instead of the 2-address equivalent ones. It seems that both spilling and register moves are improved noticeably generally. Regalloc hints are passed to increase conversions to 2-address instructions which are done in SystemZShortenInst.cpp (after regalloc). Since the SystemZ reg/mem instructions are 2-address (dst and lhs regs are the same), foldMemoryOperandImpl() can no longer trivially fold a spilled source register since the reg/reg instruction is now 3-address. In order to remedy this, new 3-address pseudo memory instructions are used to perform the folding only when the dst and lhs virtual registers are known to be allocated to the same physreg. In order to not let MachineCopyPropagation run and change registers on these transformed instructions (making it 3-address), a new target pass called SystemZPostRewrite.cpp is run just after VirtRegRewriter, that immediately lowers the pseudo to a target instruction. If it would have been possibe to insert a COPY instruction and change a register operand (convert to 2-address) in foldMemoryOperandImpl() while trusting that the caller (e.g. InlineSpiller) would update/repair the involved LiveIntervals, the solution involving pseudo instructions would not have been needed. This is perhaps a potential improvement (see Phabricator post). Common code changes: * A new hook TargetPassConfig::addPostRewrite() is utilized to be able to run a target pass immediately before MachineCopyPropagation. * VirtRegMap is passed as an argument to foldMemoryOperand(). Review: Ulrich Weigand, Quentin Colombet https://reviews.llvm.org/D60888 llvm-svn: 362868
1 parent 27de3d3 commit fdc4ea3

26 files changed

+515
-217
lines changed

llvm/include/llvm/CodeGen/TargetInstrInfo.h

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
#include "llvm/CodeGen/MachineOperand.h"
2727
#include "llvm/CodeGen/MachineOutliner.h"
2828
#include "llvm/CodeGen/PseudoSourceValue.h"
29+
#include "llvm/CodeGen/VirtRegMap.h"
2930
#include "llvm/MC/MCInstrInfo.h"
3031
#include "llvm/Support/BranchProbability.h"
3132
#include "llvm/Support/ErrorHandling.h"
@@ -932,9 +933,12 @@ class TargetInstrInfo : public MCInstrInfo {
932933
/// operand folded, otherwise NULL is returned.
933934
/// The new instruction is inserted before MI, and the client is responsible
934935
/// for removing the old instruction.
936+
/// If VRM is passed, the assigned physregs can be inspected by target to
937+
/// decide on using an opcode (note that those assignments can still change).
935938
MachineInstr *foldMemoryOperand(MachineInstr &MI, ArrayRef<unsigned> Ops,
936939
int FI,
937-
LiveIntervals *LIS = nullptr) const;
940+
LiveIntervals *LIS = nullptr,
941+
VirtRegMap *VRM = nullptr) const;
938942

939943
/// Same as the previous version except it allows folding of any load and
940944
/// store from / to any address, not just from a specific stack slot.
@@ -1024,7 +1028,8 @@ class TargetInstrInfo : public MCInstrInfo {
10241028
foldMemoryOperandImpl(MachineFunction &MF, MachineInstr &MI,
10251029
ArrayRef<unsigned> Ops,
10261030
MachineBasicBlock::iterator InsertPt, int FrameIndex,
1027-
LiveIntervals *LIS = nullptr) const {
1031+
LiveIntervals *LIS = nullptr,
1032+
VirtRegMap *VRM = nullptr) const {
10281033
return nullptr;
10291034
}
10301035

llvm/include/llvm/CodeGen/TargetPassConfig.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -386,6 +386,10 @@ class TargetPassConfig : public ImmutablePass {
386386
return false;
387387
}
388388

389+
/// Add passes to be run immediately after virtual registers are rewritten
390+
/// to physical registers.
391+
virtual void addPostRewrite() { }
392+
389393
/// This method may be implemented by targets that want to run passes after
390394
/// register allocation pass pipeline but before prolog-epilog insertion.
391395
virtual void addPostRegAlloc() { }

llvm/lib/CodeGen/InlineSpiller.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -837,7 +837,7 @@ foldMemoryOperand(ArrayRef<std::pair<MachineInstr *, unsigned>> Ops,
837837

838838
MachineInstr *FoldMI =
839839
LoadMI ? TII.foldMemoryOperand(*MI, FoldOps, *LoadMI, &LIS)
840-
: TII.foldMemoryOperand(*MI, FoldOps, StackSlot, &LIS);
840+
: TII.foldMemoryOperand(*MI, FoldOps, StackSlot, &LIS, &VRM);
841841
if (!FoldMI)
842842
return false;
843843

llvm/lib/CodeGen/TargetInstrInfo.cpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -524,7 +524,8 @@ static MachineInstr *foldPatchpoint(MachineFunction &MF, MachineInstr &MI,
524524

525525
MachineInstr *TargetInstrInfo::foldMemoryOperand(MachineInstr &MI,
526526
ArrayRef<unsigned> Ops, int FI,
527-
LiveIntervals *LIS) const {
527+
LiveIntervals *LIS,
528+
VirtRegMap *VRM) const {
528529
auto Flags = MachineMemOperand::MONone;
529530
for (unsigned OpIdx : Ops)
530531
Flags |= MI.getOperand(OpIdx).isDef() ? MachineMemOperand::MOStore
@@ -570,7 +571,7 @@ MachineInstr *TargetInstrInfo::foldMemoryOperand(MachineInstr &MI,
570571
MBB->insert(MI, NewMI);
571572
} else {
572573
// Ask the target to do the actual folding.
573-
NewMI = foldMemoryOperandImpl(MF, MI, Ops, MI, FI, LIS);
574+
NewMI = foldMemoryOperandImpl(MF, MI, Ops, MI, FI, LIS, VRM);
574575
}
575576

576577
if (NewMI) {

llvm/lib/CodeGen/TargetPassConfig.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1168,6 +1168,10 @@ void TargetPassConfig::addOptimizedRegAlloc() {
11681168
addPass(&MachineSchedulerID);
11691169

11701170
if (addRegAssignmentOptimized()) {
1171+
// Allow targets to expand pseudo instructions depending on the choice of
1172+
// registers before MachineCopyPropagation.
1173+
addPostRewrite();
1174+
11711175
// Copy propagate to forward register uses and try to eliminate COPYs that
11721176
// were not coalesced.
11731177
addPass(&MachineCopyPropagationID);

llvm/lib/Target/AArch64/AArch64InstrInfo.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3049,7 +3049,7 @@ void llvm::emitFrameOffset(MachineBasicBlock &MBB,
30493049
MachineInstr *AArch64InstrInfo::foldMemoryOperandImpl(
30503050
MachineFunction &MF, MachineInstr &MI, ArrayRef<unsigned> Ops,
30513051
MachineBasicBlock::iterator InsertPt, int FrameIndex,
3052-
LiveIntervals *LIS) const {
3052+
LiveIntervals *LIS, VirtRegMap *VRM) const {
30533053
// This is a bit of a hack. Consider this instruction:
30543054
//
30553055
// %0 = COPY %sp; GPR64all:%0

llvm/lib/Target/AArch64/AArch64InstrInfo.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -162,7 +162,8 @@ class AArch64InstrInfo final : public AArch64GenInstrInfo {
162162
foldMemoryOperandImpl(MachineFunction &MF, MachineInstr &MI,
163163
ArrayRef<unsigned> Ops,
164164
MachineBasicBlock::iterator InsertPt, int FrameIndex,
165-
LiveIntervals *LIS = nullptr) const override;
165+
LiveIntervals *LIS = nullptr,
166+
VirtRegMap *VRM = nullptr) const override;
166167

167168
/// \returns true if a branch from an instruction with opcode \p BranchOpc
168169
/// bytes is capable of jumping to a position \p BrOffset bytes away.

llvm/lib/Target/SystemZ/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ add_llvm_target(SystemZCodeGen
3030
SystemZMCInstLower.cpp
3131
SystemZRegisterInfo.cpp
3232
SystemZSelectionDAGInfo.cpp
33+
SystemZPostRewrite.cpp
3334
SystemZShortenInst.cpp
3435
SystemZSubtarget.cpp
3536
SystemZTargetMachine.cpp

llvm/lib/Target/SystemZ/SystemZ.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -194,6 +194,7 @@ FunctionPass *createSystemZExpandPseudoPass(SystemZTargetMachine &TM);
194194
FunctionPass *createSystemZShortenInstPass(SystemZTargetMachine &TM);
195195
FunctionPass *createSystemZLongBranchPass(SystemZTargetMachine &TM);
196196
FunctionPass *createSystemZLDCleanupPass(SystemZTargetMachine &TM);
197+
FunctionPass *createSystemZPostRewritePass(SystemZTargetMachine &TM);
197198
FunctionPass *createSystemZTDCPass();
198199
} // end namespace llvm
199200

0 commit comments

Comments
 (0)