diff options
Diffstat (limited to 'llvm/lib')
-rw-r--r-- | llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp | 64 | ||||
-rw-r--r-- | llvm/lib/Target/AArch64/AArch64LegalizerInfo.cpp | 19 | ||||
-rw-r--r-- | llvm/lib/Target/AMDGPU/AMDGPULegalizerInfo.cpp | 2 | ||||
-rw-r--r-- | llvm/lib/Target/ARM/ARMLegalizerInfo.cpp | 7 | ||||
-rw-r--r-- | llvm/lib/Target/Mips/MipsLegalizerInfo.cpp | 7 | ||||
-rw-r--r-- | llvm/lib/Target/X86/X86InstructionSelector.cpp | 23 | ||||
-rw-r--r-- | llvm/lib/Target/X86/X86LegalizerInfo.cpp | 23 | ||||
-rw-r--r-- | llvm/lib/Target/X86/X86RegisterBankInfo.cpp | 18 |
8 files changed, 115 insertions, 48 deletions
diff --git a/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp b/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp index 7ec2c3d6891..7e98a9b7a3d 100644 --- a/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp +++ b/llvm/lib/CodeGen/GlobalISel/LegalizerHelper.cpp @@ -282,10 +282,6 @@ LegalizerHelper::libcall(MachineInstr &MI) { LegalizerHelper::LegalizeResult LegalizerHelper::narrowScalar(MachineInstr &MI, unsigned TypeIdx, LLT NarrowTy) { - // FIXME: Don't know how to handle secondary types yet. - if (TypeIdx != 0 && MI.getOpcode() != TargetOpcode::G_EXTRACT) - return UnableToLegalize; - MIRBuilder.setInstr(MI); uint64_t SizeOp0 = MRI.getType(MI.getOperand(0).getReg()).getSizeInBits(); @@ -408,6 +404,10 @@ LegalizerHelper::LegalizeResult LegalizerHelper::narrowScalar(MachineInstr &MI, return Legalized; } case TargetOpcode::G_INSERT: { + // FIXME: Don't know how to handle secondary types yet. + if (TypeIdx != 0) + return UnableToLegalize; + // FIXME: add support for when SizeOp0 isn't an exact multiple of // NarrowSize. if (SizeOp0 % NarrowSize != 0) @@ -659,6 +659,14 @@ LegalizerHelper::LegalizeResult LegalizerHelper::narrowScalar(MachineInstr &MI, MI.eraseFromParent(); return Legalized; } + case TargetOpcode::G_SHL: + case TargetOpcode::G_LSHR: + case TargetOpcode::G_ASHR: { + if (TypeIdx != 1) + return UnableToLegalize; // TODO + narrowScalarSrc(MI, NarrowTy, 2); + return Legalized; + } } } @@ -669,6 +677,14 @@ void LegalizerHelper::widenScalarSrc(MachineInstr &MI, LLT WideTy, MO.setReg(ExtB->getOperand(0).getReg()); } +void LegalizerHelper::narrowScalarSrc(MachineInstr &MI, LLT NarrowTy, + unsigned OpIdx) { + MachineOperand &MO = MI.getOperand(OpIdx); + auto ExtB = MIRBuilder.buildInstr(TargetOpcode::G_TRUNC, {NarrowTy}, + {MO.getReg()}); + MO.setReg(ExtB->getOperand(0).getReg()); +} + void LegalizerHelper::widenScalarDst(MachineInstr &MI, LLT WideTy, unsigned OpIdx, unsigned TruncOpcode) { MachineOperand &MO = MI.getOperand(OpIdx); @@ -766,12 +782,18 @@ LegalizerHelper::widenScalar(MachineInstr &MI, unsigned TypeIdx, LLT WideTy) { return Legalized; case TargetOpcode::G_SHL: - Observer.changingInstr(MI); - widenScalarSrc(MI, WideTy, 1, TargetOpcode::G_ANYEXT); - // The "number of bits to shift" operand must preserve its value as an - // unsigned integer: - widenScalarSrc(MI, WideTy, 2, TargetOpcode::G_ZEXT); - widenScalarDst(MI, WideTy); + Observer.changingInstr(MI); + + if (TypeIdx == 0) { + widenScalarSrc(MI, WideTy, 1, TargetOpcode::G_ANYEXT); + widenScalarDst(MI, WideTy); + } else { + assert(TypeIdx == 1); + // The "number of bits to shift" operand must preserve its value as an + // unsigned integer: + widenScalarSrc(MI, WideTy, 2, TargetOpcode::G_ZEXT); + } + Observer.changedInstr(MI); return Legalized; @@ -785,18 +807,26 @@ LegalizerHelper::widenScalar(MachineInstr &MI, unsigned TypeIdx, LLT WideTy) { return Legalized; case TargetOpcode::G_ASHR: + case TargetOpcode::G_LSHR: Observer.changingInstr(MI); - widenScalarSrc(MI, WideTy, 1, TargetOpcode::G_SEXT); - // The "number of bits to shift" operand must preserve its value as an - // unsigned integer: - widenScalarSrc(MI, WideTy, 2, TargetOpcode::G_ZEXT); - widenScalarDst(MI, WideTy); + + if (TypeIdx == 0) { + unsigned CvtOp = MI.getOpcode() == TargetOpcode::G_ASHR ? + TargetOpcode::G_SEXT : TargetOpcode::G_ZEXT; + + widenScalarSrc(MI, WideTy, 1, CvtOp); + widenScalarDst(MI, WideTy); + } else { + assert(TypeIdx == 1); + // The "number of bits to shift" operand must preserve its value as an + // unsigned integer: + widenScalarSrc(MI, WideTy, 2, TargetOpcode::G_ZEXT); + } + Observer.changedInstr(MI); return Legalized; - case TargetOpcode::G_UDIV: case TargetOpcode::G_UREM: - case TargetOpcode::G_LSHR: Observer.changingInstr(MI); widenScalarSrc(MI, WideTy, 1, TargetOpcode::G_ZEXT); widenScalarSrc(MI, WideTy, 2, TargetOpcode::G_ZEXT); diff --git a/llvm/lib/Target/AArch64/AArch64LegalizerInfo.cpp b/llvm/lib/Target/AArch64/AArch64LegalizerInfo.cpp index 7798b42a446..05607896d49 100644 --- a/llvm/lib/Target/AArch64/AArch64LegalizerInfo.cpp +++ b/llvm/lib/Target/AArch64/AArch64LegalizerInfo.cpp @@ -73,7 +73,7 @@ AArch64LegalizerInfo::AArch64LegalizerInfo(const AArch64Subtarget &ST) { .clampScalar(0, s16, s64) .widenScalarToNextPow2(0); - getActionDefinitionsBuilder({G_ADD, G_SUB, G_MUL, G_AND, G_OR, G_XOR, G_SHL}) + getActionDefinitionsBuilder({G_ADD, G_SUB, G_MUL, G_AND, G_OR, G_XOR}) .legalFor({s32, s64, v2s32, v4s32, v2s64}) .clampScalar(0, s32, s64) .widenScalarToNextPow2(0) @@ -81,17 +81,32 @@ AArch64LegalizerInfo::AArch64LegalizerInfo(const AArch64Subtarget &ST) { .clampNumElements(0, v2s64, v2s64) .moreElementsToNextPow2(0); + getActionDefinitionsBuilder(G_SHL) + .legalFor({{s32, s32}, {s64, s64}, + {v2s32, v2s32}, {v4s32, v4s32}, {v2s64, v2s64}}) + .clampScalar(0, s32, s64) + .widenScalarToNextPow2(0) + .clampNumElements(0, v2s32, v4s32) + .clampNumElements(0, v2s64, v2s64) + .moreElementsToNextPow2(0) + .minScalarSameAs(1, 0); + getActionDefinitionsBuilder(G_GEP) .legalFor({{p0, s64}}) .clampScalar(1, s64, s64); getActionDefinitionsBuilder(G_PTR_MASK).legalFor({p0}); - getActionDefinitionsBuilder({G_LSHR, G_ASHR, G_SDIV, G_UDIV}) + getActionDefinitionsBuilder({G_SDIV, G_UDIV}) .legalFor({s32, s64}) .clampScalar(0, s32, s64) .widenScalarToNextPow2(0); + getActionDefinitionsBuilder({G_LSHR, G_ASHR}) + .legalFor({{s32, s32}, {s64, s64}}) + .clampScalar(0, s32, s64) + .minScalarSameAs(1, 0); + getActionDefinitionsBuilder({G_SREM, G_UREM}) .lowerFor({s1, s8, s16, s32, s64}); diff --git a/llvm/lib/Target/AMDGPU/AMDGPULegalizerInfo.cpp b/llvm/lib/Target/AMDGPU/AMDGPULegalizerInfo.cpp index d898cb6c7e2..94f4914d19b 100644 --- a/llvm/lib/Target/AMDGPU/AMDGPULegalizerInfo.cpp +++ b/llvm/lib/Target/AMDGPU/AMDGPULegalizerInfo.cpp @@ -98,6 +98,7 @@ AMDGPULegalizerInfo::AMDGPULegalizerInfo(const GCNSubtarget &ST, setAction({G_ADD, S32}, Legal); setAction({G_ASHR, S32}, Legal); + setAction({G_ASHR, 1, S32}, Legal); setAction({G_SUB, S32}, Legal); setAction({G_MUL, S32}, Legal); @@ -274,6 +275,7 @@ AMDGPULegalizerInfo::AMDGPULegalizerInfo(const GCNSubtarget &ST, .clampScalar(0, S32, S64); setAction({G_SHL, S32}, Legal); + setAction({G_SHL, 1, S32}, Legal); // FIXME: When RegBankSelect inserts copies, it will only create new diff --git a/llvm/lib/Target/ARM/ARMLegalizerInfo.cpp b/llvm/lib/Target/ARM/ARMLegalizerInfo.cpp index e1f7af1a6d8..37a5f3d1e02 100644 --- a/llvm/lib/Target/ARM/ARMLegalizerInfo.cpp +++ b/llvm/lib/Target/ARM/ARMLegalizerInfo.cpp @@ -135,7 +135,12 @@ ARMLegalizerInfo::ARMLegalizerInfo(const ARMSubtarget &ST) { setAction({Op, s32}, Libcall); } - getActionDefinitionsBuilder({G_ASHR, G_LSHR, G_SHL}).legalFor({s32}); + getActionDefinitionsBuilder(G_INTTOPTR).legalFor({{p0, s32}}); + getActionDefinitionsBuilder(G_PTRTOINT).legalFor({{s32, p0}}); + + getActionDefinitionsBuilder({G_ASHR, G_LSHR, G_SHL}) + .legalFor({{s32, s32}}) + .clampScalar(1, s32, s32); if (ST.hasV5TOps()) { getActionDefinitionsBuilder(G_CTLZ) diff --git a/llvm/lib/Target/Mips/MipsLegalizerInfo.cpp b/llvm/lib/Target/Mips/MipsLegalizerInfo.cpp index ce0bc6b429a..eaecd4b8717 100644 --- a/llvm/lib/Target/Mips/MipsLegalizerInfo.cpp +++ b/llvm/lib/Target/Mips/MipsLegalizerInfo.cpp @@ -43,14 +43,15 @@ MipsLegalizerInfo::MipsLegalizerInfo(const MipsSubtarget &ST) { .legalFor({s32}) .clampScalar(0, s32, s32); - getActionDefinitionsBuilder({G_SHL, G_ASHR, G_LSHR}) - .legalFor({s32}); - getActionDefinitionsBuilder({G_SDIV, G_SREM, G_UREM, G_UDIV}) .legalFor({s32}) .minScalar(0, s32) .libcallFor({s64}); + getActionDefinitionsBuilder({G_SHL, G_ASHR, G_LSHR}) + .legalFor({s32, s32}) + .minScalar(1, s32); + getActionDefinitionsBuilder(G_ICMP) .legalFor({{s32, s32}}) .minScalar(0, s32); diff --git a/llvm/lib/Target/X86/X86InstructionSelector.cpp b/llvm/lib/Target/X86/X86InstructionSelector.cpp index f6407065e28..0fdd6e379b4 100644 --- a/llvm/lib/Target/X86/X86InstructionSelector.cpp +++ b/llvm/lib/Target/X86/X86InstructionSelector.cpp @@ -1529,15 +1529,14 @@ bool X86InstructionSelector::selectShift(MachineInstr &I, const static struct ShiftEntry { unsigned SizeInBits; - unsigned CReg; unsigned OpLSHR; unsigned OpASHR; unsigned OpSHL; } OpTable[] = { - {8, X86::CL, X86::SHR8rCL, X86::SAR8rCL, X86::SHL8rCL}, // i8 - {16, X86::CX, X86::SHR16rCL, X86::SAR16rCL, X86::SHL16rCL}, // i16 - {32, X86::ECX, X86::SHR32rCL, X86::SAR32rCL, X86::SHL32rCL}, // i32 - {64, X86::RCX, X86::SHR64rCL, X86::SAR64rCL, X86::SHL64rCL} // i64 + {8, X86::SHR8rCL, X86::SAR8rCL, X86::SHL8rCL}, // i8 + {16, X86::SHR16rCL, X86::SAR16rCL, X86::SHL16rCL}, // i16 + {32, X86::SHR32rCL, X86::SAR32rCL, X86::SHL32rCL}, // i32 + {64, X86::SHR64rCL, X86::SAR64rCL, X86::SHL64rCL} // i64 }; if (DstRB.getID() != X86::GPRRegBankID) @@ -1550,7 +1549,6 @@ bool X86InstructionSelector::selectShift(MachineInstr &I, if (ShiftEntryIt == std::end(OpTable)) return false; - unsigned CReg = ShiftEntryIt->CReg; unsigned Opcode = 0; switch (I.getOpcode()) { case TargetOpcode::G_SHL: @@ -1569,16 +1567,11 @@ bool X86InstructionSelector::selectShift(MachineInstr &I, unsigned Op0Reg = I.getOperand(1).getReg(); unsigned Op1Reg = I.getOperand(2).getReg(); - BuildMI(*I.getParent(), I, I.getDebugLoc(), TII.get(TargetOpcode::COPY), - ShiftEntryIt->CReg) - .addReg(Op1Reg); + assert(MRI.getType(Op1Reg).getSizeInBits() == 8); - // The shift instruction uses X86::CL. If we defined a super-register - // of X86::CL, emit a subreg KILL to precisely describe what we're doing here. - if (CReg != X86::CL) - BuildMI(*I.getParent(), I, I.getDebugLoc(), TII.get(TargetOpcode::KILL), - X86::CL) - .addReg(CReg, RegState::Kill); + BuildMI(*I.getParent(), I, I.getDebugLoc(), TII.get(TargetOpcode::COPY), + X86::CL) + .addReg(Op1Reg); MachineInstr &ShiftInst = *BuildMI(*I.getParent(), I, I.getDebugLoc(), TII.get(Opcode), DstReg) diff --git a/llvm/lib/Target/X86/X86LegalizerInfo.cpp b/llvm/lib/Target/X86/X86LegalizerInfo.cpp index 2fd9e634aca..00fb1b57385 100644 --- a/llvm/lib/Target/X86/X86LegalizerInfo.cpp +++ b/llvm/lib/Target/X86/X86LegalizerInfo.cpp @@ -133,9 +133,15 @@ void X86LegalizerInfo::setLegalizerInfo32bit() { // Shifts and SDIV getActionDefinitionsBuilder( - {G_SHL, G_LSHR, G_ASHR, G_SDIV, G_SREM, G_UDIV, G_UREM}) - .legalFor({s8, s16, s32}) - .clampScalar(0, s8, s32); + {G_SDIV, G_SREM, G_UDIV, G_UREM}) + .legalFor({s8, s16, s32}) + .clampScalar(0, s8, s32); + + getActionDefinitionsBuilder( + {G_SHL, G_LSHR, G_ASHR}) + .legalFor({{s8, s8}, {s16, s8}, {s32, s8}}) + .clampScalar(0, s8, s32) + .clampScalar(1, s8, s8); } // Control-flow @@ -235,12 +241,19 @@ void X86LegalizerInfo::setLegalizerInfo64bit() { .clampScalar(1, s32, s64) .widenScalarToNextPow2(1); - // Shifts and SDIV + // Divisions getActionDefinitionsBuilder( - {G_SHL, G_LSHR, G_ASHR, G_SDIV, G_SREM, G_UDIV, G_UREM}) + {G_SDIV, G_SREM, G_UDIV, G_UREM}) .legalFor({s8, s16, s32, s64}) .clampScalar(0, s8, s64); + // Shifts + getActionDefinitionsBuilder( + {G_SHL, G_LSHR, G_ASHR}) + .legalFor({{s8, s8}, {s16, s8}, {s32, s8}, {s64, s8}}) + .clampScalar(0, s8, s64) + .clampScalar(1, s8, s8); + // Merge/Unmerge setAction({G_MERGE_VALUES, s128}, Legal); setAction({G_UNMERGE_VALUES, 1, s128}, Legal); diff --git a/llvm/lib/Target/X86/X86RegisterBankInfo.cpp b/llvm/lib/Target/X86/X86RegisterBankInfo.cpp index f8aef0c0dc3..3ea4c59aa49 100644 --- a/llvm/lib/Target/X86/X86RegisterBankInfo.cpp +++ b/llvm/lib/Target/X86/X86RegisterBankInfo.cpp @@ -173,17 +173,25 @@ X86RegisterBankInfo::getInstrMapping(const MachineInstr &MI) const { case TargetOpcode::G_ADD: case TargetOpcode::G_SUB: case TargetOpcode::G_MUL: - case TargetOpcode::G_SHL: - case TargetOpcode::G_LSHR: - case TargetOpcode::G_ASHR: return getSameOperandsMapping(MI, false); - break; case TargetOpcode::G_FADD: case TargetOpcode::G_FSUB: case TargetOpcode::G_FMUL: case TargetOpcode::G_FDIV: return getSameOperandsMapping(MI, true); - break; + case TargetOpcode::G_SHL: + case TargetOpcode::G_LSHR: + case TargetOpcode::G_ASHR: { + const MachineFunction &MF = *MI.getParent()->getParent(); + const MachineRegisterInfo &MRI = MF.getRegInfo(); + + unsigned NumOperands = MI.getNumOperands(); + LLT Ty = MRI.getType(MI.getOperand(0).getReg()); + + auto Mapping = getValueMapping(getPartialMappingIdx(Ty, false), 3); + return getInstructionMapping(DefaultMappingID, 1, Mapping, NumOperands); + + } default: break; } |