Skip to content

Commit bf98899

Browse files
committed
FPInfo: RegBankSelect
1 parent dabbfd2 commit bf98899

File tree

2 files changed

+58
-21
lines changed

2 files changed

+58
-21
lines changed

llvm/lib/CodeGen/GlobalISel/RegBankSelect.cpp

Lines changed: 46 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@
3131
#include "llvm/CodeGen/TargetSubtargetInfo.h"
3232
#include "llvm/Config/llvm-config.h"
3333
#include "llvm/IR/Function.h"
34+
#include "llvm/IR/Instruction.h"
3435
#include "llvm/InitializePasses.h"
3536
#include "llvm/Pass.h"
3637
#include "llvm/Support/BlockFrequency.h"
@@ -158,26 +159,29 @@ bool RegBankSelect::repairReg(
158159

159160
// Build the instruction used to repair, then clone it at the right
160161
// places. Avoiding buildCopy bypasses the check that Src and Dst have the
161-
// same types because the type is a placeholder when this function is called.
162+
// same types because the type is a placeholder when this function is
163+
// called.
162164
MI = MIRBuilder.buildInstrNoInsert(TargetOpcode::COPY)
163-
.addDef(Dst)
164-
.addUse(Src);
165+
.addDef(Dst)
166+
.addUse(Src);
165167
LLVM_DEBUG(dbgs() << "Copy: " << printReg(Src) << ':'
166168
<< printRegClassOrBank(Src, *MRI, TRI)
167169
<< " to: " << printReg(Dst) << ':'
168170
<< printRegClassOrBank(Dst, *MRI, TRI) << '\n');
169171
} else {
170172
// TODO: Support with G_IMPLICIT_DEF + G_INSERT sequence or G_EXTRACT
171173
// sequence.
172-
assert(ValMapping.partsAllUniform() && "irregular breakdowns not supported");
174+
assert(ValMapping.partsAllUniform() &&
175+
"irregular breakdowns not supported");
173176

174-
LLT RegTy = MRI->getType(MO.getReg());
177+
Register MergeReg = MO.getReg();
178+
LLT RegTy = MRI->getType(MergeReg);
175179
if (MO.isDef()) {
176180
unsigned MergeOp;
177181
if (RegTy.isVector()) {
178-
if (ValMapping.NumBreakDowns == RegTy.getNumElements())
182+
if (ValMapping.NumBreakDowns == RegTy.getNumElements()) {
179183
MergeOp = TargetOpcode::G_BUILD_VECTOR;
180-
else {
184+
} else {
181185
assert(
182186
(ValMapping.BreakDown[0].Length * ValMapping.NumBreakDowns ==
183187
RegTy.getSizeInBits()) &&
@@ -187,24 +191,36 @@ bool RegBankSelect::repairReg(
187191

188192
MergeOp = TargetOpcode::G_CONCAT_VECTORS;
189193
}
190-
} else
194+
} else {
191195
MergeOp = TargetOpcode::G_MERGE_VALUES;
196+
if (RegTy.isFloat()) {
197+
const RegisterBank *Bank = ValMapping.BreakDown[0].RegBank;
198+
LLT Ty = RegTy.changeToInteger();
199+
MergeReg = MRI->createVirtualRegister({Bank, Ty});
200+
}
201+
}
192202

193203
auto MergeBuilder =
194-
MIRBuilder.buildInstrNoInsert(MergeOp)
195-
.addDef(MO.getReg());
204+
MIRBuilder.buildInstrNoInsert(MergeOp).addDef(MergeReg);
196205

197206
for (Register SrcReg : NewVRegs)
198207
MergeBuilder.addUse(SrcReg);
199208

200209
MI = MergeBuilder;
201210
} else {
202211
MachineInstrBuilder UnMergeBuilder =
203-
MIRBuilder.buildInstrNoInsert(TargetOpcode::G_UNMERGE_VALUES);
212+
MIRBuilder.buildInstrNoInsert(TargetOpcode::G_UNMERGE_VALUES);
204213
for (Register DefReg : NewVRegs)
205214
UnMergeBuilder.addDef(DefReg);
206215

207-
UnMergeBuilder.addUse(MO.getReg());
216+
if (RegTy.isFloat()) {
217+
const RegisterBank *Bank = ValMapping.BreakDown[0].RegBank;
218+
MergeReg =
219+
MIRBuilder.buildBitcast({Bank, RegTy.changeToInteger()}, MO.getReg())
220+
.getReg(0);
221+
}
222+
223+
UnMergeBuilder.addUse(MergeReg);
208224
MI = UnMergeBuilder;
209225
}
210226
}
@@ -215,20 +231,30 @@ bool RegBankSelect::repairReg(
215231
// TODO:
216232
// Check if MI is legal. if not, we need to legalize all the
217233
// instructions we are going to insert.
218-
std::unique_ptr<MachineInstr *[]> NewInstrs(
219-
new MachineInstr *[RepairPt.getNumInsertPoints()]);
220-
bool IsFirst = true;
221-
unsigned Idx = 0;
222-
for (const std::unique_ptr<InsertPoint> &InsertPt : RepairPt) {
234+
SmallVector<MachineInstr *> NewInstrs;
235+
NewInstrs.reserve(RepairPt.getNumInsertPoints());
236+
for (auto &&[Idx, InsertPt] : enumerate(RepairPt)) {
223237
MachineInstr *CurMI;
224-
if (IsFirst)
238+
if (Idx == 0)
225239
CurMI = MI;
226240
else
227241
CurMI = MIRBuilder.getMF().CloneMachineInstr(MI);
242+
228243
InsertPt->insert(*CurMI);
229-
NewInstrs[Idx++] = CurMI;
230-
IsFirst = false;
244+
NewInstrs.push_back(CurMI);
231245
}
246+
247+
LLT RegTy = MRI->getType(MO.getReg());
248+
if (MO.isDef() && RegTy.isFloat()) {
249+
for (auto *MI : NewInstrs) {
250+
auto Cast = MIRBuilder.buildInstrNoInsert(TargetOpcode::G_BITCAST)
251+
.addDef(MO.getReg())
252+
.addUse(MI->getOperand(0).getReg());
253+
254+
MI->getParent()->insertAfter(MI, Cast.getInstr());
255+
}
256+
}
257+
232258
// TODO:
233259
// Legalize NewInstrs if need be.
234260
return true;

llvm/lib/CodeGen/RegisterBankInfo.cpp

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -707,12 +707,22 @@ RegisterBankInfo::OperandsMapper::getNewVRegsEnd(unsigned StartIdx,
707707
: &NewVRegs[StartIdx + NumVal];
708708
}
709709

710+
static LLT inferType(LLT OrigType,
711+
const RegisterBankInfo::PartialMapping &PartMap) {
712+
if (PartMap.StartIdx == 0 && PartMap.Length == OrigType.getSizeInBits())
713+
return OrigType;
714+
// TODO: check if this is a full lane of a vector type and extract the
715+
// element type.
716+
return LLT::integer(PartMap.Length);
717+
}
718+
710719
void RegisterBankInfo::OperandsMapper::createVRegs(unsigned OpIdx) {
711720
assert(OpIdx < getInstrMapping().getNumOperands() && "Out-of-bound access");
712721
iterator_range<SmallVectorImpl<Register>::iterator> NewVRegsForOpIdx =
713722
getVRegsMem(OpIdx);
714723
const ValueMapping &ValMapping = getInstrMapping().getOperandMapping(OpIdx);
715724
const PartialMapping *PartMap = ValMapping.begin();
725+
LLT OrigType = getMRI().getType(getMI().getOperand(OpIdx).getReg());
716726
for (Register &NewVReg : NewVRegsForOpIdx) {
717727
assert(PartMap != ValMapping.end() && "Out-of-bound access");
718728
assert(NewVReg == 0 && "Register has already been created");
@@ -721,7 +731,8 @@ void RegisterBankInfo::OperandsMapper::createVRegs(unsigned OpIdx) {
721731
// of the instruction.
722732
// The rationale is that this generic code cannot guess how the
723733
// target plans to split the input type.
724-
NewVReg = MRI.createGenericVirtualRegister(LLT::scalar(PartMap->Length));
734+
LLT NewType = inferType(OrigType, *PartMap);
735+
NewVReg = MRI.createGenericVirtualRegister(NewType);
725736
MRI.setRegBank(NewVReg, *PartMap->RegBank);
726737
++PartMap;
727738
}

0 commit comments

Comments
 (0)