Skip to content

Commit

Permalink
[AIE2P] Optimize regbankselect for fifo/acc
Browse files Browse the repository at this point in the history
For G_IMPLICIT_DEF.
Looking through PHI nodes.
  • Loading branch information
andcarminati committed Feb 4, 2025
1 parent 07fe638 commit 64294b7
Show file tree
Hide file tree
Showing 4 changed files with 390 additions and 117 deletions.
97 changes: 56 additions & 41 deletions llvm/lib/Target/AIE/aie2p/AIE2PRegisterBankInfo.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,10 @@
#include "AIE2PGenRegisterBank.inc"
using namespace llvm;

static llvm::cl::opt<unsigned>
MaxDepthBankSearch("aie-max-depth-bank-search", cl::Hidden, cl::init(4),
cl::desc("Max depth search during RegBankSelect"));

RegisterBankInfo::PartialMapping AIE2PGenRegisterBankInfo::PartMappings[]{
// StartIdx, Length, RegBank
// 0: GPR 32-bit value
Expand Down Expand Up @@ -729,56 +733,62 @@ bool AIE2PRegisterBankInfo::hasFifoInput(const MachineInstr &MI,

bool AIE2PRegisterBankInfo::isUseAccInsn(const MachineRegisterInfo &MRI,
const TargetRegisterInfo &TRI,
const Register &RegOp) const {
// Helper function to trace through COPY and G_BITCAST
auto traceToActualReg = [&](Register &Reg) {
for (auto &UseMI : MRI.use_nodbg_instructions(Reg)) {
MachineInstr *ConvUseMI = &UseMI;
unsigned ConvUseOpc = ConvUseMI->getOpcode();
// skip copies
while (ConvUseOpc == TargetOpcode::G_BITCAST ||
ConvUseOpc == TargetOpcode::COPY) {
Register DefReg = ConvUseMI->getOperand(0).getReg();
if (DefReg.isPhysical())
break;
Reg = DefReg;
if (MRI.use_empty(DefReg))
break;
ConvUseMI = &*MRI.use_instr_nodbg_begin(DefReg);
ConvUseOpc = ConvUseMI->getOpcode();
}
}
};
const Register &RegOp,
unsigned Depth) const {

// Create a non-const copy of RegOp for tracing
Register TracedRegOp = RegOp;
auto IsCopyToVReg = [](const MachineInstr &MI) {
return (MI.isCopy() && MI.getOperand(0).getReg().isVirtual());
};

// Trace RegOp to its actual register, updating it if necessary
traceToActualReg(TracedRegOp);
for (auto &UseMI : MRI.use_nodbg_instructions(RegOp)) {
const unsigned UseOpcode = UseMI.getOpcode();

// Now check for accumulator-usage using the updated TracedRegOp
return any_of(MRI.use_nodbg_instructions(TracedRegOp),
[&](const MachineInstr &UseMI) {
// Check if this instruction uses the accumulator register
return (MRI.getType(TracedRegOp).getSizeInBits() == 2048) ||
usesAccReg(UseMI, MRI, TRI, TracedRegOp);
});
if (Depth > MaxDepthBankSearch)
return false;
// skip copies
if (UseOpcode == TargetOpcode::G_BITCAST || IsCopyToVReg(UseMI) ||
UseMI.isPHI()) {
Register DefReg = UseMI.getOperand(0).getReg();
if (DefReg.isPhysical())
continue;
if (isUseAccInsn(MRI, TRI, DefReg, Depth + 1))
return true;
} else if (MRI.getType(RegOp).getSizeInBits() == 2048 ||
usesAccReg(UseMI, MRI, TRI, RegOp)) {
return true;
}
}
return false;
}

// Check if RegOp is used as a fifo register.
bool AIE2PRegisterBankInfo::isUseFifoInsn(const MachineRegisterInfo &MRI,
const TargetRegisterInfo &TRI,
const Register RegOp) const {
// TODO: Trace RegOp to its actual definition ignoring COPY and G_BITCAST as
// we do for accumulator bank.
// Use getDefIgnoringCopiesAndBitcasts and refactor the code between
// accumulator and fifo handling.
const Register RegOp,
unsigned Depth) const {

auto IsCopyToVReg = [](const MachineInstr &MI) {
return (MI.isCopy() && MI.getOperand(0).getReg().isVirtual());
};

for (auto &UseMI : MRI.use_nodbg_instructions(RegOp)) {
const unsigned UseOpcode = UseMI.getOpcode();

return any_of(MRI.use_nodbg_instructions(RegOp),
[&](const MachineInstr &UseMI) {
// Check if this instruction uses the accumulator register
return hasFifoInput(UseMI, MRI, TRI, RegOp);
});
if (Depth > MaxDepthBankSearch)
return false;
// skip copies
if (UseOpcode == TargetOpcode::G_BITCAST || IsCopyToVReg(UseMI) ||
UseMI.isPHI()) {
Register DefReg = UseMI.getOperand(0).getReg();
if (DefReg.isPhysical())
continue;
if (isUseFifoInsn(MRI, TRI, DefReg, Depth + 1))
return true;
} else if (hasFifoInput(UseMI, MRI, TRI, RegOp)) {
return true;
}
}
return false;
}

const RegisterBankInfo::InstructionMapping &
Expand Down Expand Up @@ -853,6 +863,10 @@ AIE2PRegisterBankInfo::getInstrMapping(const MachineInstr &MI) const {
OpRegBankIdx[0] = getAccPartialMappingIdx(Type);
return AIEBaseRegisterBankInfo::getInstrMappingFinal(MI, Cost, OpSize,
OpRegBankIdx);
} else if (isUseFifoInsn(MRI, TRI, DstReg)) {
OpRegBankIdx[0] = getFifoPartialMappingIdx(Type);
return AIEBaseRegisterBankInfo::getInstrMappingFinal(MI, Cost, OpSize,
OpRegBankIdx);
}
return AIEBaseRegisterBankInfo::getInstrMapping(MI);
}
Expand Down Expand Up @@ -1001,6 +1015,7 @@ AIE2PRegisterBankInfo::getInstrMapping(const MachineInstr &MI) const {
}
return AIEBaseRegisterBankInfo::getInstrMapping(MI);
}

default:
// Base class implementation for others
return AIEBaseRegisterBankInfo::getInstrMapping(MI);
Expand Down
8 changes: 4 additions & 4 deletions llvm/lib/Target/AIE/aie2p/AIE2PRegisterBankInfo.h
Original file line number Diff line number Diff line change
Expand Up @@ -80,14 +80,14 @@ class AIE2PRegisterBankInfo final : public AIE2PGenRegisterBankInfo {
bool usesAccReg(const MachineInstr &MI, const MachineRegisterInfo &MRI,
const TargetRegisterInfo &TRI, const Register &AccReg) const;
bool isUseAccInsn(const MachineRegisterInfo &MRI,
const TargetRegisterInfo &TRI,
const Register &AccReg) const;
const TargetRegisterInfo &TRI, const Register &AccReg,
unsigned Depth = 0) const;
bool hasFifoInput(const MachineInstr &MI, const MachineRegisterInfo &MRI,
const TargetRegisterInfo &TRI,
const Register FifoReg) const;
bool isUseFifoInsn(const MachineRegisterInfo &MRI,
const TargetRegisterInfo &TRI,
const Register FifoReg) const;
const TargetRegisterInfo &TRI, const Register FifoReg,
unsigned Depth = 0) const;
};
} // end namespace llvm
#endif
Loading

0 comments on commit 64294b7

Please sign in to comment.