diff options
Diffstat (limited to 'llvm/lib')
14 files changed, 158 insertions, 6 deletions
diff --git a/llvm/lib/Target/SystemZ/AsmParser/SystemZAsmParser.cpp b/llvm/lib/Target/SystemZ/AsmParser/SystemZAsmParser.cpp index 3f373de4d89..a94717c9345 100644 --- a/llvm/lib/Target/SystemZ/AsmParser/SystemZAsmParser.cpp +++ b/llvm/lib/Target/SystemZ/AsmParser/SystemZAsmParser.cpp @@ -484,9 +484,15 @@ public: OperandMatchResultTy parseBDVAddr64(OperandVector &Operands) { return parseAddress(Operands, BDVMem, SystemZMC::GR64Regs, ADDR64Reg); } + OperandMatchResultTy parsePCRel12(OperandVector &Operands) { + return parsePCRel(Operands, -(1LL << 12), (1LL << 12) - 1, false); + } OperandMatchResultTy parsePCRel16(OperandVector &Operands) { return parsePCRel(Operands, -(1LL << 16), (1LL << 16) - 1, false); } + OperandMatchResultTy parsePCRel24(OperandVector &Operands) { + return parsePCRel(Operands, -(1LL << 24), (1LL << 24) - 1, false); + } OperandMatchResultTy parsePCRel32(OperandVector &Operands) { return parsePCRel(Operands, -(1LL << 32), (1LL << 32) - 1, false); } diff --git a/llvm/lib/Target/SystemZ/Disassembler/SystemZDisassembler.cpp b/llvm/lib/Target/SystemZ/Disassembler/SystemZDisassembler.cpp index a1b8422e9e8..1806e015f61 100644 --- a/llvm/lib/Target/SystemZ/Disassembler/SystemZDisassembler.cpp +++ b/llvm/lib/Target/SystemZ/Disassembler/SystemZDisassembler.cpp @@ -247,12 +247,24 @@ static DecodeStatus decodePCDBLOperand(MCInst &Inst, uint64_t Imm, return MCDisassembler::Success; } +static DecodeStatus decodePC12DBLBranchOperand(MCInst &Inst, uint64_t Imm, + uint64_t Address, + const void *Decoder) { + return decodePCDBLOperand<12>(Inst, Imm, Address, true, Decoder); +} + static DecodeStatus decodePC16DBLBranchOperand(MCInst &Inst, uint64_t Imm, uint64_t Address, const void *Decoder) { return decodePCDBLOperand<16>(Inst, Imm, Address, true, Decoder); } +static DecodeStatus decodePC24DBLBranchOperand(MCInst &Inst, uint64_t Imm, + uint64_t Address, + const void *Decoder) { + return decodePCDBLOperand<24>(Inst, Imm, Address, true, Decoder); +} + static DecodeStatus decodePC32DBLBranchOperand(MCInst &Inst, uint64_t Imm, uint64_t Address, const void *Decoder) { diff --git a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCAsmBackend.cpp b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCAsmBackend.cpp index d1aad2bcd16..5a340955d06 100644 --- a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCAsmBackend.cpp +++ b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCAsmBackend.cpp @@ -25,7 +25,9 @@ static uint64_t extractBitsForFixup(MCFixupKind Kind, uint64_t Value) { return Value; switch (unsigned(Kind)) { + case SystemZ::FK_390_PC12DBL: case SystemZ::FK_390_PC16DBL: + case SystemZ::FK_390_PC24DBL: case SystemZ::FK_390_PC32DBL: return (int64_t)Value / 2; @@ -72,7 +74,9 @@ public: const MCFixupKindInfo & SystemZMCAsmBackend::getFixupKindInfo(MCFixupKind Kind) const { const static MCFixupKindInfo Infos[SystemZ::NumTargetFixupKinds] = { + { "FK_390_PC12DBL", 4, 12, MCFixupKindInfo::FKF_IsPCRel }, { "FK_390_PC16DBL", 0, 16, MCFixupKindInfo::FKF_IsPCRel }, + { "FK_390_PC24DBL", 0, 24, MCFixupKindInfo::FKF_IsPCRel }, { "FK_390_PC32DBL", 0, 32, MCFixupKindInfo::FKF_IsPCRel }, { "FK_390_TLS_CALL", 0, 0, 0 } }; diff --git a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCCodeEmitter.cpp b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCCodeEmitter.cpp index ec82c9cb5a6..7082abad716 100644 --- a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCCodeEmitter.cpp +++ b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCCodeEmitter.cpp @@ -113,6 +113,24 @@ private: return getPCRelEncoding(MI, OpNum, Fixups, SystemZ::FK_390_PC32DBL, 2, true); } + uint64_t getPC12DBLBPPEncoding(const MCInst &MI, unsigned OpNum, + SmallVectorImpl<MCFixup> &Fixups, + const MCSubtargetInfo &STI) const { + return getPCRelEncoding(MI, OpNum, Fixups, + SystemZ::FK_390_PC12DBL, 1, false); + } + uint64_t getPC16DBLBPPEncoding(const MCInst &MI, unsigned OpNum, + SmallVectorImpl<MCFixup> &Fixups, + const MCSubtargetInfo &STI) const { + return getPCRelEncoding(MI, OpNum, Fixups, + SystemZ::FK_390_PC16DBL, 4, false); + } + uint64_t getPC24DBLBPPEncoding(const MCInst &MI, unsigned OpNum, + SmallVectorImpl<MCFixup> &Fixups, + const MCSubtargetInfo &STI) const { + return getPCRelEncoding(MI, OpNum, Fixups, + SystemZ::FK_390_PC24DBL, 3, false); + } private: uint64_t computeAvailableFeatures(const FeatureBitset &FB) const; diff --git a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCFixups.h b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCFixups.h index 229ab5dc86f..c012accc14d 100644 --- a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCFixups.h +++ b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCFixups.h @@ -16,7 +16,9 @@ namespace llvm { namespace SystemZ { enum FixupKind { // These correspond directly to R_390_* relocations. - FK_390_PC16DBL = FirstTargetFixupKind, + FK_390_PC12DBL = FirstTargetFixupKind, + FK_390_PC16DBL, + FK_390_PC24DBL, FK_390_PC32DBL, FK_390_TLS_CALL, diff --git a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCObjectWriter.cpp b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCObjectWriter.cpp index 368c95f7bac..43a96e84289 100644 --- a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCObjectWriter.cpp +++ b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZMCObjectWriter.cpp @@ -53,7 +53,9 @@ static unsigned getPCRelReloc(unsigned Kind) { case FK_Data_2: return ELF::R_390_PC16; case FK_Data_4: return ELF::R_390_PC32; case FK_Data_8: return ELF::R_390_PC64; + case SystemZ::FK_390_PC12DBL: return ELF::R_390_PC12DBL; case SystemZ::FK_390_PC16DBL: return ELF::R_390_PC16DBL; + case SystemZ::FK_390_PC24DBL: return ELF::R_390_PC24DBL; case SystemZ::FK_390_PC32DBL: return ELF::R_390_PC32DBL; } llvm_unreachable("Unsupported PC-relative address"); @@ -100,7 +102,9 @@ static unsigned getTLSGDReloc(unsigned Kind) { // Return the PLT relocation counterpart of MCFixupKind Kind. static unsigned getPLTReloc(unsigned Kind) { switch (Kind) { + case SystemZ::FK_390_PC12DBL: return ELF::R_390_PLT12DBL; case SystemZ::FK_390_PC16DBL: return ELF::R_390_PLT16DBL; + case SystemZ::FK_390_PC24DBL: return ELF::R_390_PLT24DBL; case SystemZ::FK_390_PC32DBL: return ELF::R_390_PLT32DBL; } llvm_unreachable("Unsupported absolute address"); diff --git a/llvm/lib/Target/SystemZ/SystemZFeatures.td b/llvm/lib/Target/SystemZ/SystemZFeatures.td index 0fb3c55ebe0..716e5add805 100644 --- a/llvm/lib/Target/SystemZ/SystemZFeatures.td +++ b/llvm/lib/Target/SystemZ/SystemZFeatures.td @@ -84,6 +84,11 @@ def Arch9NewFeatures : SystemZFeatureList<[ // //===----------------------------------------------------------------------===// +def FeatureExecutionHint : SystemZFeature< + "execution-hint", "ExecutionHint", + "Assume that the execution-hint facility is installed" +>; + def FeatureLoadAndTrap : SystemZFeature< "load-and-trap", "LoadAndTrap", "Assume that the load-and-trap facility is installed" @@ -105,6 +110,7 @@ def FeatureTransactionalExecution : SystemZFeature< >; def Arch10NewFeatures : SystemZFeatureList<[ + FeatureExecutionHint, FeatureLoadAndTrap, FeatureMiscellaneousExtensions, FeatureProcessorAssist, diff --git a/llvm/lib/Target/SystemZ/SystemZInstrFormats.td b/llvm/lib/Target/SystemZ/SystemZInstrFormats.td index a5c1c2680d5..ad7c08be88d 100644 --- a/llvm/lib/Target/SystemZ/SystemZInstrFormats.td +++ b/llvm/lib/Target/SystemZ/SystemZInstrFormats.td @@ -177,6 +177,35 @@ class InstI<bits<8> op, dag outs, dag ins, string asmstr, list<dag> pattern> let Inst{7-0} = I1; } +class InstIE<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern> + : InstSystemZ<4, outs, ins, asmstr, pattern> { + field bits<32> Inst; + field bits<32> SoftFail = 0; + + bits<4> I1; + bits<4> I2; + + let Inst{31-16} = op; + let Inst{15-8} = 0; + let Inst{7-4} = I1; + let Inst{3-0} = I2; +} + +class InstMII<bits<8> op, dag outs, dag ins, string asmstr, list<dag> pattern> + : InstSystemZ<6, outs, ins, asmstr, pattern> { + field bits<48> Inst; + field bits<48> SoftFail = 0; + + bits<4> M1; + bits<12> RI2; + bits<24> RI3; + + let Inst{47-40} = op; + let Inst{39-36} = M1; + let Inst{35-24} = RI2; + let Inst{23-0} = RI3; +} + class InstRIa<bits<12> op, dag outs, dag ins, string asmstr, list<dag> pattern> : InstSystemZ<4, outs, ins, asmstr, pattern> { field bits<32> Inst; @@ -759,6 +788,22 @@ class InstSIY<bits<16> op, dag outs, dag ins, string asmstr, list<dag> pattern> let Has20BitOffset = 1; } +class InstSMI<bits<8> op, dag outs, dag ins, string asmstr, list<dag> pattern> + : InstSystemZ<6, outs, ins, asmstr, pattern> { + field bits<48> Inst; + field bits<48> SoftFail = 0; + + bits<4> M1; + bits<16> RI2; + bits<16> BD3; + + let Inst{47-40} = op; + let Inst{39-36} = M1; + let Inst{35-32} = 0; + let Inst{31-16} = BD3; + let Inst{15-0} = RI2; +} + class InstSSa<bits<8> op, dag outs, dag ins, string asmstr, list<dag> pattern> : InstSystemZ<6, outs, ins, asmstr, pattern> { field bits<48> Inst; @@ -1605,6 +1650,9 @@ class ICV<string name> // One 4-bit immediate operand and one address operand. The immediate // operand is 1 for a load prefetch and 2 for a store prefetch. // +// BranchPreload: +// One 4-bit immediate operand and two address operands. +// // The format determines which input operands are tied to output operands, // and also determines the shape of any address operand. // @@ -2504,6 +2552,13 @@ class SideEffectBinaryRILPC<string mnemonic, bits<12> opcode, let AddedComplexity = 7; } +class SideEffectBinaryIE<string mnemonic, bits<16> opcode, + Immediate imm1, Immediate imm2> + : InstIE<opcode, (outs), (ins imm1:$I1, imm2:$I2), + mnemonic#"\t$I1, $I2", []> { + let hasSideEffects = 1; +} + class SideEffectBinarySIL<string mnemonic, bits<16> opcode, SDPatternOperator operator, Immediate imm> : InstSIL<opcode, (outs), (ins bdaddr12only:$BD1, imm:$I2), @@ -3620,6 +3675,16 @@ class PrefetchRILPC<string mnemonic, bits<12> opcode, let AddedComplexity = 7; } +class BranchPreloadSMI<string mnemonic, bits<8> opcode> + : InstSMI<opcode, (outs), + (ins imm32zx4:$M1, brtarget16bpp:$RI2, bdxaddr12only:$BD3), + mnemonic#"\t$M1, $RI2, $BD3", []>; + +class BranchPreloadMII<string mnemonic, bits<8> opcode> + : InstMII<opcode, (outs), + (ins imm32zx4:$M1, brtarget12bpp:$RI2, brtarget24bpp:$RI3), + mnemonic#"\t$M1, $RI2, $RI3", []>; + // A floating-point load-and test operation. Create both a normal unary // operation and one that acts as a comparison against zero. // Note that the comparison against zero operation is not available if we diff --git a/llvm/lib/Target/SystemZ/SystemZInstrInfo.td b/llvm/lib/Target/SystemZ/SystemZInstrInfo.td index c180d405419..d97a92dd109 100644 --- a/llvm/lib/Target/SystemZ/SystemZInstrInfo.td +++ b/llvm/lib/Target/SystemZ/SystemZInstrInfo.td @@ -1382,12 +1382,21 @@ def TML : InstAlias<"tml\t$R, $I", (TMLL GR32:$R, imm32ll16:$I), 0>; def TMH : InstAlias<"tmh\t$R, $I", (TMLH GR32:$R, imm32lh16:$I), 0>; //===----------------------------------------------------------------------===// -// Prefetch +// Prefetch and execution hint //===----------------------------------------------------------------------===// def PFD : PrefetchRXY<"pfd", 0xE336, z_prefetch>; def PFDRL : PrefetchRILPC<"pfdrl", 0xC62, z_prefetch>; +let Predicates = [FeatureExecutionHint] in { + // Branch Prediction Preload + def BPP : BranchPreloadSMI<"bpp", 0xC7>; + def BPRP : BranchPreloadMII<"bprp", 0xC5>; + + // Next Instruction Access Intent + def NIAI : SideEffectBinaryIE<"niai", 0xB2FA, imm32zx4, imm32zx4>; +} + //===----------------------------------------------------------------------===// // Atomic operations //===----------------------------------------------------------------------===// diff --git a/llvm/lib/Target/SystemZ/SystemZOperands.td b/llvm/lib/Target/SystemZ/SystemZOperands.td index 3b747496a1b..7bb4fe5afb3 100644 --- a/llvm/lib/Target/SystemZ/SystemZOperands.td +++ b/llvm/lib/Target/SystemZ/SystemZOperands.td @@ -460,7 +460,9 @@ def fpimmneg0 : PatLeaf<(fpimm), [{ return N->isExactlyValue(-0.0); }]>; //===----------------------------------------------------------------------===// // PC-relative asm operands. +def PCRel12 : PCRelAsmOperand<"12">; def PCRel16 : PCRelAsmOperand<"16">; +def PCRel24 : PCRelAsmOperand<"24">; def PCRel32 : PCRelAsmOperand<"32">; def PCRelTLS16 : PCRelTLSAsmOperand<"16">; def PCRelTLS32 : PCRelTLSAsmOperand<"32">; @@ -476,6 +478,20 @@ def brtarget32 : PCRelOperand<OtherVT, PCRel32> { let DecoderMethod = "decodePC32DBLBranchOperand"; } +// Variants of brtarget for use with branch prediction preload. +def brtarget12bpp : PCRelOperand<OtherVT, PCRel12> { + let EncoderMethod = "getPC12DBLBPPEncoding"; + let DecoderMethod = "decodePC12DBLBranchOperand"; +} +def brtarget16bpp : PCRelOperand<OtherVT, PCRel16> { + let EncoderMethod = "getPC16DBLBPPEncoding"; + let DecoderMethod = "decodePC16DBLBranchOperand"; +} +def brtarget24bpp : PCRelOperand<OtherVT, PCRel24> { + let EncoderMethod = "getPC24DBLBPPEncoding"; + let DecoderMethod = "decodePC24DBLBranchOperand"; +} + // Variants of brtarget16/32 with an optional additional TLS symbol. // These are used to annotate calls to __tls_get_offset. def tlssym : Operand<i64> { } diff --git a/llvm/lib/Target/SystemZ/SystemZScheduleZ13.td b/llvm/lib/Target/SystemZ/SystemZScheduleZ13.td index f712d2b0f9b..ae6885f0913 100644 --- a/llvm/lib/Target/SystemZ/SystemZScheduleZ13.td +++ b/llvm/lib/Target/SystemZ/SystemZScheduleZ13.td @@ -517,10 +517,13 @@ def : InstRW<[FXb], (instregex "TMLH(64)?$")>; def : InstRW<[FXb], (instregex "TMLL(64)?$")>; //===----------------------------------------------------------------------===// -// Prefetch +// Prefetch and execution hint //===----------------------------------------------------------------------===// def : InstRW<[LSU], (instregex "PFD(RL)?$")>; +def : InstRW<[FXb, Lat2], (instregex "BPP$")>; +def : InstRW<[FXb, EndGroup], (instregex "BPRP$")>; +def : InstRW<[FXb], (instregex "NIAI$")>; //===----------------------------------------------------------------------===// // Atomic operations diff --git a/llvm/lib/Target/SystemZ/SystemZScheduleZEC12.td b/llvm/lib/Target/SystemZ/SystemZScheduleZEC12.td index 49353eb1d3d..38d4402a74b 100644 --- a/llvm/lib/Target/SystemZ/SystemZScheduleZEC12.td +++ b/llvm/lib/Target/SystemZ/SystemZScheduleZEC12.td @@ -487,10 +487,12 @@ def : InstRW<[FXU], (instregex "TMLH(64)?$")>; def : InstRW<[FXU], (instregex "TMLL(64)?$")>; //===----------------------------------------------------------------------===// -// Prefetch +// Prefetch and execution hint //===----------------------------------------------------------------------===// def : InstRW<[LSU], (instregex "PFD(RL)?$")>; +def : InstRW<[LSU], (instregex "BP(R)?P$")>; +def : InstRW<[FXU], (instregex "NIAI$")>; //===----------------------------------------------------------------------===// // Atomic operations diff --git a/llvm/lib/Target/SystemZ/SystemZSubtarget.cpp b/llvm/lib/Target/SystemZ/SystemZSubtarget.cpp index bf7277a6ef1..ce07ea3318a 100644 --- a/llvm/lib/Target/SystemZ/SystemZSubtarget.cpp +++ b/llvm/lib/Target/SystemZ/SystemZSubtarget.cpp @@ -39,8 +39,9 @@ SystemZSubtarget::SystemZSubtarget(const Triple &TT, const std::string &CPU, HasLoadStoreOnCond(false), HasHighWord(false), HasFPExtension(false), HasPopulationCount(false), HasFastSerialization(false), HasInterlockedAccess1(false), HasMiscellaneousExtensions(false), - HasLoadAndTrap(false), HasTransactionalExecution(false), - HasProcessorAssist(false), HasVector(false), HasLoadStoreOnCond2(false), + HasExecutionHint(false), HasLoadAndTrap(false), + HasTransactionalExecution(false), HasProcessorAssist(false), + HasVector(false), HasLoadStoreOnCond2(false), HasLoadAndZeroRightmostByte(false), TargetTriple(TT), InstrInfo(initializeSubtargetDependencies(CPU, FS)), TLInfo(TM, *this), TSInfo(), FrameLowering() {} diff --git a/llvm/lib/Target/SystemZ/SystemZSubtarget.h b/llvm/lib/Target/SystemZ/SystemZSubtarget.h index 8475e2edaf2..cdb61327a16 100644 --- a/llvm/lib/Target/SystemZ/SystemZSubtarget.h +++ b/llvm/lib/Target/SystemZ/SystemZSubtarget.h @@ -42,6 +42,7 @@ protected: bool HasFastSerialization; bool HasInterlockedAccess1; bool HasMiscellaneousExtensions; + bool HasExecutionHint; bool HasLoadAndTrap; bool HasTransactionalExecution; bool HasProcessorAssist; @@ -114,6 +115,9 @@ public: return HasMiscellaneousExtensions; } + // Return true if the target has the execution-hint facility. + bool hasExecutionHint() const { return HasExecutionHint; } + // Return true if the target has the load-and-trap facility. bool hasLoadAndTrap() const { return HasLoadAndTrap; } |