From 0f140c769a75779991d0bb31c2e34907621d2386 Mon Sep 17 00:00:00 2001 From: Tim Northover Date: Fri, 9 Sep 2016 11:46:34 +0000 Subject: GlobalISel: move type information to MachineRegisterInfo. We want each register to have a canonical type, which means the best place to store this is in MachineRegisterInfo rather than on every MachineInstr that happens to use or define that register. Most changes following from this are pretty simple (you need an MRI anyway if you're going to be doing any transformations, so just check the type there). But legalization doesn't really want to check redundant operands (when, for example, a G_ADD only ever has one type) so I've made use of MCInstrDesc's operand type field to encode these constraints and limit legalization's work. As an added bonus, more validation is possible, both in MachineVerifier and MachineIRBuilder (coming soon). llvm-svn: 281035 --- llvm/lib/CodeGen/GlobalISel/MachineIRBuilder.cpp | 167 +++++++++-------------- 1 file changed, 68 insertions(+), 99 deletions(-) (limited to 'llvm/lib/CodeGen/GlobalISel/MachineIRBuilder.cpp') diff --git a/llvm/lib/CodeGen/GlobalISel/MachineIRBuilder.cpp b/llvm/lib/CodeGen/GlobalISel/MachineIRBuilder.cpp index da18b036f0c..eb345811f67 100644 --- a/llvm/lib/CodeGen/GlobalISel/MachineIRBuilder.cpp +++ b/llvm/lib/CodeGen/GlobalISel/MachineIRBuilder.cpp @@ -14,6 +14,7 @@ #include "llvm/CodeGen/MachineFunction.h" #include "llvm/CodeGen/MachineInstr.h" #include "llvm/CodeGen/MachineInstrBuilder.h" +#include "llvm/CodeGen/MachineRegisterInfo.h" #include "llvm/Target/TargetInstrInfo.h" #include "llvm/Target/TargetOpcodes.h" #include "llvm/Target/TargetSubtargetInfo.h" @@ -23,6 +24,7 @@ using namespace llvm; void MachineIRBuilder::setMF(MachineFunction &MF) { this->MF = &MF; this->MBB = nullptr; + this->MRI = &MF.getRegInfo(); this->TII = MF.getSubtarget().getInstrInfo(); this->DL = DebugLoc(); this->MI = nullptr; @@ -67,100 +69,87 @@ void MachineIRBuilder::stopRecordingInsertions() { // Build instruction variants. //------------------------------------------------------------------------------ -MachineInstrBuilder MachineIRBuilder::buildInstr(unsigned Opcode, - ArrayRef Tys) { +MachineInstrBuilder MachineIRBuilder::buildInstr(unsigned Opcode) { MachineInstrBuilder MIB = BuildMI(getMF(), DL, getTII().get(Opcode)); - if (Tys.size() > 0) { - assert(isPreISelGenericOpcode(Opcode) && - "Only generic instruction can have a type"); - for (unsigned i = 0; i < Tys.size(); ++i) - MIB->setType(Tys[i], i); - } else - assert(!isPreISelGenericOpcode(Opcode) && - "Generic instruction must have a type"); getMBB().insert(getInsertPt(), MIB); if (InsertedInstr) InsertedInstr(MIB); return MIB; } -MachineInstrBuilder MachineIRBuilder::buildFrameIndex(LLT Ty, unsigned Res, - int Idx) { - return buildInstr(TargetOpcode::G_FRAME_INDEX, Ty) +MachineInstrBuilder MachineIRBuilder::buildFrameIndex(unsigned Res, int Idx) { + return buildInstr(TargetOpcode::G_FRAME_INDEX) .addDef(Res) .addFrameIndex(Idx); } -MachineInstrBuilder MachineIRBuilder::buildAdd(LLT Ty, unsigned Res, - unsigned Op0, unsigned Op1) { - return buildInstr(TargetOpcode::G_ADD, Ty) +MachineInstrBuilder MachineIRBuilder::buildAdd(unsigned Res, unsigned Op0, + unsigned Op1) { + return buildInstr(TargetOpcode::G_ADD) .addDef(Res) .addUse(Op0) .addUse(Op1); } -MachineInstrBuilder MachineIRBuilder::buildSub(LLT Ty, unsigned Res, - unsigned Op0, unsigned Op1) { - return buildInstr(TargetOpcode::G_SUB, Ty) +MachineInstrBuilder MachineIRBuilder::buildSub(unsigned Res, unsigned Op0, + unsigned Op1) { + return buildInstr(TargetOpcode::G_SUB) .addDef(Res) .addUse(Op0) .addUse(Op1); } -MachineInstrBuilder MachineIRBuilder::buildMul(LLT Ty, unsigned Res, - unsigned Op0, unsigned Op1) { - return buildInstr(TargetOpcode::G_MUL, Ty) +MachineInstrBuilder MachineIRBuilder::buildMul(unsigned Res, unsigned Op0, + unsigned Op1) { + return buildInstr(TargetOpcode::G_MUL) .addDef(Res) .addUse(Op0) .addUse(Op1); } MachineInstrBuilder MachineIRBuilder::buildBr(MachineBasicBlock &Dest) { - return buildInstr(TargetOpcode::G_BR, LLT::unsized()).addMBB(&Dest); + return buildInstr(TargetOpcode::G_BR).addMBB(&Dest); } MachineInstrBuilder MachineIRBuilder::buildCopy(unsigned Res, unsigned Op) { return buildInstr(TargetOpcode::COPY).addDef(Res).addUse(Op); } -MachineInstrBuilder MachineIRBuilder::buildConstant(LLT Ty, unsigned Res, - int64_t Val) { - return buildInstr(TargetOpcode::G_CONSTANT, Ty).addDef(Res).addImm(Val); +MachineInstrBuilder MachineIRBuilder::buildConstant(unsigned Res, int64_t Val) { + return buildInstr(TargetOpcode::G_CONSTANT).addDef(Res).addImm(Val); } -MachineInstrBuilder MachineIRBuilder::buildFConstant(LLT Ty, unsigned Res, - const ConstantFP &Val) { - return buildInstr(TargetOpcode::G_FCONSTANT, Ty).addDef(Res).addFPImm(&Val); +MachineInstrBuilder MachineIRBuilder::buildFConstant(unsigned Res, + const ConstantFP &Val) { + return buildInstr(TargetOpcode::G_FCONSTANT).addDef(Res).addFPImm(&Val); } -MachineInstrBuilder MachineIRBuilder::buildBrCond(LLT Ty, unsigned Tst, +MachineInstrBuilder MachineIRBuilder::buildBrCond(unsigned Tst, MachineBasicBlock &Dest) { - return buildInstr(TargetOpcode::G_BRCOND, Ty).addUse(Tst).addMBB(&Dest); + return buildInstr(TargetOpcode::G_BRCOND).addUse(Tst).addMBB(&Dest); } - - MachineInstrBuilder MachineIRBuilder::buildLoad(LLT VTy, LLT PTy, unsigned Res, - unsigned Addr, - MachineMemOperand &MMO) { - return buildInstr(TargetOpcode::G_LOAD, {VTy, PTy}) +MachineInstrBuilder MachineIRBuilder::buildLoad(unsigned Res, unsigned Addr, + MachineMemOperand &MMO) { + return buildInstr(TargetOpcode::G_LOAD) .addDef(Res) .addUse(Addr) .addMemOperand(&MMO); } -MachineInstrBuilder MachineIRBuilder::buildStore(LLT VTy, LLT PTy, - unsigned Val, unsigned Addr, - MachineMemOperand &MMO) { - return buildInstr(TargetOpcode::G_STORE, {VTy, PTy}) +MachineInstrBuilder MachineIRBuilder::buildStore(unsigned Val, unsigned Addr, + MachineMemOperand &MMO) { + return buildInstr(TargetOpcode::G_STORE) .addUse(Val) .addUse(Addr) .addMemOperand(&MMO); } -MachineInstrBuilder -MachineIRBuilder::buildUAdde(ArrayRef Tys, unsigned Res, unsigned CarryOut, - unsigned Op0, unsigned Op1, unsigned CarryIn) { - return buildInstr(TargetOpcode::G_UADDE, Tys) +MachineInstrBuilder MachineIRBuilder::buildUAdde(unsigned Res, + unsigned CarryOut, + unsigned Op0, unsigned Op1, + unsigned CarryIn) { + return buildInstr(TargetOpcode::G_UADDE) .addDef(Res) .addDef(CarryOut) .addUse(Op0) @@ -168,44 +157,34 @@ MachineIRBuilder::buildUAdde(ArrayRef Tys, unsigned Res, unsigned CarryOut, .addUse(CarryIn); } -MachineInstrBuilder MachineIRBuilder::buildType(LLT Ty, - unsigned Res, unsigned Op) { - return buildInstr(TargetOpcode::G_TYPE, Ty).addDef(Res).addUse(Op); +MachineInstrBuilder MachineIRBuilder::buildType(unsigned Res, unsigned Op) { + return buildInstr(TargetOpcode::G_TYPE).addDef(Res).addUse(Op); } -MachineInstrBuilder MachineIRBuilder::buildAnyExt(ArrayRef Tys, - unsigned Res, unsigned Op) { - validateTruncExt(Tys, true); - return buildInstr(TargetOpcode::G_ANYEXT, Tys).addDef(Res).addUse(Op); +MachineInstrBuilder MachineIRBuilder::buildAnyExt(unsigned Res, unsigned Op) { + validateTruncExt(Res, Op, true); + return buildInstr(TargetOpcode::G_ANYEXT).addDef(Res).addUse(Op); } -MachineInstrBuilder MachineIRBuilder::buildSExt(ArrayRef Tys, unsigned Res, - unsigned Op) { - validateTruncExt(Tys, true); - return buildInstr(TargetOpcode::G_SEXT, Tys).addDef(Res).addUse(Op); +MachineInstrBuilder MachineIRBuilder::buildSExt(unsigned Res, unsigned Op) { + validateTruncExt(Res, Op, true); + return buildInstr(TargetOpcode::G_SEXT).addDef(Res).addUse(Op); } -MachineInstrBuilder MachineIRBuilder::buildZExt(ArrayRef Tys, unsigned Res, - unsigned Op) { - validateTruncExt(Tys, true); - return buildInstr(TargetOpcode::G_ZEXT, Tys).addDef(Res).addUse(Op); +MachineInstrBuilder MachineIRBuilder::buildZExt(unsigned Res, unsigned Op) { + validateTruncExt(Res, Op, true); + return buildInstr(TargetOpcode::G_ZEXT).addDef(Res).addUse(Op); } -MachineInstrBuilder MachineIRBuilder::buildExtract(ArrayRef ResTys, - ArrayRef Results, +MachineInstrBuilder MachineIRBuilder::buildExtract(ArrayRef Results, ArrayRef Indices, - LLT SrcTy, unsigned Src) { - assert(ResTys.size() == Results.size() && Results.size() == Indices.size() && - "inconsistent number of regs"); + unsigned Src) { + assert(Results.size() == Indices.size() && "inconsistent number of regs"); assert(!Results.empty() && "invalid trivial extract"); assert(std::is_sorted(Indices.begin(), Indices.end()) && "extract offsets must be in ascending order"); auto MIB = BuildMI(getMF(), DL, getTII().get(TargetOpcode::G_EXTRACT)); - for (unsigned i = 0; i < ResTys.size(); ++i) - MIB->setType(LLT::scalar(ResTys[i].getSizeInBits()), i); - MIB->setType(LLT::scalar(SrcTy.getSizeInBits()), ResTys.size()); - for (auto Res : Results) MIB.addDef(Res); @@ -222,89 +201,79 @@ MachineInstrBuilder MachineIRBuilder::buildExtract(ArrayRef ResTys, } MachineInstrBuilder -MachineIRBuilder::buildSequence(LLT ResTy, unsigned Res, - ArrayRef OpTys, +MachineIRBuilder::buildSequence(unsigned Res, ArrayRef Ops, ArrayRef Indices) { - assert(OpTys.size() == Ops.size() && Ops.size() == Indices.size() && - "incompatible args"); + assert(Ops.size() == Indices.size() && "incompatible args"); assert(!Ops.empty() && "invalid trivial sequence"); assert(std::is_sorted(Indices.begin(), Indices.end()) && "sequence offsets must be in ascending order"); - MachineInstrBuilder MIB = - buildInstr(TargetOpcode::G_SEQUENCE, LLT::scalar(ResTy.getSizeInBits())); + MachineInstrBuilder MIB = buildInstr(TargetOpcode::G_SEQUENCE); MIB.addDef(Res); for (unsigned i = 0; i < Ops.size(); ++i) { MIB.addUse(Ops[i]); MIB.addImm(Indices[i]); - MIB->setType(LLT::scalar(OpTys[i].getSizeInBits()), MIB->getNumTypes()); } return MIB; } -MachineInstrBuilder MachineIRBuilder::buildIntrinsic(ArrayRef Tys, - Intrinsic::ID ID, +MachineInstrBuilder MachineIRBuilder::buildIntrinsic(Intrinsic::ID ID, unsigned Res, bool HasSideEffects) { auto MIB = buildInstr(HasSideEffects ? TargetOpcode::G_INTRINSIC_W_SIDE_EFFECTS - : TargetOpcode::G_INTRINSIC, - Tys); + : TargetOpcode::G_INTRINSIC); if (Res) MIB.addDef(Res); MIB.addIntrinsicID(ID); return MIB; } -MachineInstrBuilder MachineIRBuilder::buildTrunc(ArrayRef Tys, - unsigned Res, unsigned Op) { - validateTruncExt(Tys, false); - return buildInstr(TargetOpcode::G_TRUNC, Tys).addDef(Res).addUse(Op); +MachineInstrBuilder MachineIRBuilder::buildTrunc(unsigned Res, unsigned Op) { + validateTruncExt(Res, Op, false); + return buildInstr(TargetOpcode::G_TRUNC).addDef(Res).addUse(Op); } -MachineInstrBuilder MachineIRBuilder::buildFPTrunc(ArrayRef Tys, - unsigned Res, unsigned Op) { - validateTruncExt(Tys, false); - return buildInstr(TargetOpcode::G_FPTRUNC, Tys).addDef(Res).addUse(Op); +MachineInstrBuilder MachineIRBuilder::buildFPTrunc(unsigned Res, unsigned Op) { + validateTruncExt(Res, Op, false); + return buildInstr(TargetOpcode::G_FPTRUNC).addDef(Res).addUse(Op); } -MachineInstrBuilder MachineIRBuilder::buildICmp(ArrayRef Tys, - CmpInst::Predicate Pred, +MachineInstrBuilder MachineIRBuilder::buildICmp(CmpInst::Predicate Pred, unsigned Res, unsigned Op0, unsigned Op1) { - return buildInstr(TargetOpcode::G_ICMP, Tys) + return buildInstr(TargetOpcode::G_ICMP) .addDef(Res) .addPredicate(Pred) .addUse(Op0) .addUse(Op1); } -MachineInstrBuilder MachineIRBuilder::buildFCmp(ArrayRef Tys, - CmpInst::Predicate Pred, +MachineInstrBuilder MachineIRBuilder::buildFCmp(CmpInst::Predicate Pred, unsigned Res, unsigned Op0, unsigned Op1) { - return buildInstr(TargetOpcode::G_FCMP, Tys) + return buildInstr(TargetOpcode::G_FCMP) .addDef(Res) .addPredicate(Pred) .addUse(Op0) .addUse(Op1); } -MachineInstrBuilder MachineIRBuilder::buildSelect(LLT Ty, unsigned Res, - unsigned Tst, +MachineInstrBuilder MachineIRBuilder::buildSelect(unsigned Res, unsigned Tst, unsigned Op0, unsigned Op1) { - return buildInstr(TargetOpcode::G_SELECT, {Ty, LLT::scalar(1)}) + return buildInstr(TargetOpcode::G_SELECT) .addDef(Res) .addUse(Tst) .addUse(Op0) .addUse(Op1); } -void MachineIRBuilder::validateTruncExt(ArrayRef Tys, bool IsExtend) { +void MachineIRBuilder::validateTruncExt(unsigned Dst, unsigned Src, + bool IsExtend) { #ifndef NDEBUG - assert(Tys.size() == 2 && "cast should have a source and a dest type"); - LLT DstTy{Tys[0]}, SrcTy{Tys[1]}; + LLT SrcTy = MRI->getType(Src); + LLT DstTy = MRI->getType(Dst); if (DstTy.isVector()) { assert(SrcTy.isVector() && "mismatched cast between vecot and non-vector"); -- cgit v1.2.3