diff options
Diffstat (limited to 'include/llvm/MC')
-rw-r--r-- | include/llvm/MC/EDInstInfo.h | 4 | ||||
-rw-r--r-- | include/llvm/MC/MCAsmInfo.h | 59 | ||||
-rw-r--r-- | include/llvm/MC/MCAssembler.h | 44 | ||||
-rw-r--r-- | include/llvm/MC/MCContext.h | 4 | ||||
-rw-r--r-- | include/llvm/MC/MCDirectives.h | 8 | ||||
-rw-r--r-- | include/llvm/MC/MCDisassembler.h | 12 | ||||
-rw-r--r-- | include/llvm/MC/MCELFObjectWriter.h | 44 | ||||
-rw-r--r-- | include/llvm/MC/MCExpr.h | 6 | ||||
-rw-r--r-- | include/llvm/MC/MCFixupKindInfo.h | 2 | ||||
-rw-r--r-- | include/llvm/MC/MCInstrItineraries.h | 46 | ||||
-rw-r--r-- | include/llvm/MC/MCMachObjectWriter.h | 3 | ||||
-rw-r--r-- | include/llvm/MC/MCObjectFileInfo.h | 24 | ||||
-rw-r--r-- | include/llvm/MC/MCObjectWriter.h | 5 | ||||
-rw-r--r-- | include/llvm/MC/MCRegisterInfo.h | 303 | ||||
-rw-r--r-- | include/llvm/MC/MCSchedule.h | 114 | ||||
-rw-r--r-- | include/llvm/MC/MCStreamer.h | 57 | ||||
-rw-r--r-- | include/llvm/MC/MCSubtargetInfo.h | 15 | ||||
-rw-r--r-- | include/llvm/MC/MCTargetAsmLexer.h | 34 | ||||
-rw-r--r-- | include/llvm/MC/MCTargetAsmParser.h | 13 | ||||
-rw-r--r-- | include/llvm/MC/MachineLocation.h | 10 | ||||
-rw-r--r-- | include/llvm/MC/SubtargetFeature.h | 22 |
21 files changed, 559 insertions, 270 deletions
diff --git a/include/llvm/MC/EDInstInfo.h b/include/llvm/MC/EDInstInfo.h index 0b9d3f6..5b02467 100644 --- a/include/llvm/MC/EDInstInfo.h +++ b/include/llvm/MC/EDInstInfo.h @@ -12,7 +12,7 @@ #include "llvm/Support/DataTypes.h" namespace llvm { - + #define EDIS_MAX_OPERANDS 13 #define EDIS_MAX_SYNTAXES 2 @@ -23,7 +23,7 @@ struct EDInstInfo { uint8_t operandFlags[EDIS_MAX_OPERANDS]; const signed char operandOrders[EDIS_MAX_SYNTAXES][EDIS_MAX_OPERANDS]; }; - + } // namespace llvm #endif diff --git a/include/llvm/MC/MCAsmInfo.h b/include/llvm/MC/MCAsmInfo.h index 0f67c99..9f5230b 100644 --- a/include/llvm/MC/MCAsmInfo.h +++ b/include/llvm/MC/MCAsmInfo.h @@ -147,6 +147,11 @@ namespace llvm { // FIXME: Make this a more general encoding setting? bool AllowUTF8; + /// UseDataRegionDirectives - This is true if data region markers should + /// be printed as ".data_region/.end_data_region" directives. If false, + /// use "$d/$a" labels instead. + bool UseDataRegionDirectives; + //===--- Data Emission Directives -------------------------------------===// /// ZeroDirective - this should be set to the directive used to get some @@ -172,18 +177,6 @@ namespace llvm { const char *Data32bitsDirective; // Defaults to "\t.long\t" const char *Data64bitsDirective; // Defaults to "\t.quad\t" - /// [Data|Code]Begin - These magic labels are used to marked a region as - /// data or code, and are used to provide additional information for - /// correct disassembly on targets that like to mix data and code within - /// a segment. These labels will be implicitly suffixed by the streamer - /// to give them unique names. - const char *DataBegin; // Defaults to "$d." - const char *CodeBegin; // Defaults to "$a." - const char *JT8Begin; // Defaults to "$a." - const char *JT16Begin; // Defaults to "$a." - const char *JT32Begin; // Defaults to "$a." - bool SupportsDataRegions; - /// GPRel64Directive - if non-null, a directive that is used to emit a word /// which should be relocated as a 64-bit GP-relative offset, e.g. .gpdword /// on Mips. @@ -322,26 +315,14 @@ namespace llvm { /// DwarfSectionOffsetDirective - Special section offset directive. const char* DwarfSectionOffsetDirective; // Defaults to NULL - /// DwarfRequiresRelocationForSectionOffset - True if we need to produce a - /// relocation when we want a section offset in dwarf. - bool DwarfRequiresRelocationForSectionOffset; // Defaults to true; - - /// DwarfUsesLabelOffsetDifference - True if Dwarf2 output can - /// use EmitLabelOffsetDifference. - bool DwarfUsesLabelOffsetForRanges; - - /// DwarfUsesRelocationsForStringPool - True if this Dwarf output must use - /// relocations to refer to entries in the string pool. - bool DwarfUsesRelocationsForStringPool; + /// DwarfUsesRelocationsAcrossSections - True if Dwarf2 output generally + /// uses relocations for references to other .debug_* sections. + bool DwarfUsesRelocationsAcrossSections; /// DwarfRegNumForCFI - True if dwarf register numbers are printed /// instead of symbolic register names in .cfi_* directives. bool DwarfRegNumForCFI; // Defaults to false; - //===--- CBE Asm Translation Table -----------------------------------===// - - const char *const *AsmTransCBE; // Defaults to empty - //===--- Prologue State ----------------------------------------------===// std::vector<MachineMove> InitialFrameState; @@ -388,14 +369,6 @@ namespace llvm { const char *getGPRel64Directive() const { return GPRel64Directive; } const char *getGPRel32Directive() const { return GPRel32Directive; } - /// [Code|Data]Begin label name accessors. - const char *getCodeBeginLabelName() const { return CodeBegin; } - const char *getDataBeginLabelName() const { return DataBegin; } - const char *getJumpTable8BeginLabelName() const { return JT8Begin; } - const char *getJumpTable16BeginLabelName() const { return JT16Begin; } - const char *getJumpTable32BeginLabelName() const { return JT32Begin; } - bool getSupportsDataRegions() const { return SupportsDataRegions; } - /// getNonexecutableStackSection - Targets can implement this method to /// specify a section to switch to if the translation unit doesn't have any /// trampolines that require an executable stack. @@ -492,6 +465,9 @@ namespace llvm { bool doesAllowUTF8() const { return AllowUTF8; } + bool doesSupportDataRegionDirectives() const { + return UseDataRegionDirectives; + } const char *getZeroDirective() const { return ZeroDirective; } @@ -565,21 +541,12 @@ namespace llvm { const char *getDwarfSectionOffsetDirective() const { return DwarfSectionOffsetDirective; } - bool doesDwarfRequireRelocationForSectionOffset() const { - return DwarfRequiresRelocationForSectionOffset; - } - bool doesDwarfUseLabelOffsetForRanges() const { - return DwarfUsesLabelOffsetForRanges; - } - bool doesDwarfUseRelocationsForStringPool() const { - return DwarfUsesRelocationsForStringPool; + bool doesDwarfUseRelocationsAcrossSections() const { + return DwarfUsesRelocationsAcrossSections; } bool useDwarfRegNumForCFI() const { return DwarfRegNumForCFI; } - const char *const *getAsmCBE() const { - return AsmTransCBE; - } void addInitialFrameState(MCSymbol *label, const MachineLocation &D, const MachineLocation &S) { diff --git a/include/llvm/MC/MCAssembler.h b/include/llvm/MC/MCAssembler.h index d139173..b7b2d66 100644 --- a/include/llvm/MC/MCAssembler.h +++ b/include/llvm/MC/MCAssembler.h @@ -130,7 +130,7 @@ public: void addFixup(MCFixup Fixup) { // Enforce invariant that fixups are in offset order. - assert((Fixups.empty() || Fixup.getOffset() > Fixups.back().getOffset()) && + assert((Fixups.empty() || Fixup.getOffset() >= Fixups.back().getOffset()) && "Fixups must be added in order!"); Fixups.push_back(Fixup); } @@ -651,6 +651,16 @@ struct IndirectSymbolData { MCSectionData *SectionData; }; +// FIXME: Ditto this. Purely so the Streamer and the ObjectWriter can talk +// to one another. +struct DataRegionData { + // This enum should be kept in sync w/ the mach-o definition in + // llvm/Object/MachOFormat.h. + enum KindTy { Data = 1, JumpTable8, JumpTable16, JumpTable32 } Kind; + MCSymbol *Start; + MCSymbol *End; +}; + class MCAssembler { friend class MCAsmLayout; @@ -668,6 +678,10 @@ public: const_indirect_symbol_iterator; typedef std::vector<IndirectSymbolData>::iterator indirect_symbol_iterator; + typedef std::vector<DataRegionData>::const_iterator + const_data_region_iterator; + typedef std::vector<DataRegionData>::iterator data_region_iterator; + private: MCAssembler(const MCAssembler&); // DO NOT IMPLEMENT void operator=(const MCAssembler&); // DO NOT IMPLEMENT @@ -698,6 +712,7 @@ private: std::vector<IndirectSymbolData> IndirectSymbols; + std::vector<DataRegionData> DataRegions; /// The set of function symbols for which a .thumb_func directive has /// been seen. // @@ -884,6 +899,33 @@ public: size_t indirect_symbol_size() const { return IndirectSymbols.size(); } /// @} + /// @name Data Region List Access + /// @{ + + // FIXME: This is a total hack, this should not be here. Once things are + // factored so that the streamer has direct access to the .o writer, it can + // disappear. + std::vector<DataRegionData> &getDataRegions() { + return DataRegions; + } + + data_region_iterator data_region_begin() { + return DataRegions.begin(); + } + const_data_region_iterator data_region_begin() const { + return DataRegions.begin(); + } + + data_region_iterator data_region_end() { + return DataRegions.end(); + } + const_data_region_iterator data_region_end() const { + return DataRegions.end(); + } + + size_t data_region_size() const { return DataRegions.size(); } + + /// @} /// @name Backend Data Access /// @{ diff --git a/include/llvm/MC/MCContext.h b/include/llvm/MC/MCContext.h index b586319..59545d3 100644 --- a/include/llvm/MC/MCContext.h +++ b/include/llvm/MC/MCContext.h @@ -161,6 +161,10 @@ namespace llvm { /// with a unique but unspecified name. MCSymbol *CreateTempSymbol(); + /// getUniqueSymbolID() - Return a unique identifier for use in constructing + /// symbol names. + unsigned getUniqueSymbolID() { return NextUniqueID++; } + /// CreateDirectionalLocalSymbol - Create the definition of a directional /// local symbol for numbered label (used for "1:" definitions). MCSymbol *CreateDirectionalLocalSymbol(int64_t LocalLabelVal); diff --git a/include/llvm/MC/MCDirectives.h b/include/llvm/MC/MCDirectives.h index 9180d1b..0461766 100644 --- a/include/llvm/MC/MCDirectives.h +++ b/include/llvm/MC/MCDirectives.h @@ -52,6 +52,14 @@ enum MCAssemblerFlag { MCAF_Code64 ///< .code64 (X86) }; +enum MCDataRegionType { + MCDR_DataRegion, ///< .data_region + MCDR_DataRegionJT8, ///< .data_region jt8 + MCDR_DataRegionJT16, ///< .data_region jt16 + MCDR_DataRegionJT32, ///< .data_region jt32 + MCDR_DataRegionEnd ///< .end_data_region +}; + } // end namespace llvm #endif diff --git a/include/llvm/MC/MCDisassembler.h b/include/llvm/MC/MCDisassembler.h index 4b5fbec..53a9ce0 100644 --- a/include/llvm/MC/MCDisassembler.h +++ b/include/llvm/MC/MCDisassembler.h @@ -13,13 +13,13 @@ #include "llvm-c/Disassembler.h" namespace llvm { - + class MCInst; class MCSubtargetInfo; class MemoryObject; class raw_ostream; class MCContext; - + struct EDInstInfo; /// MCDisassembler - Superclass for all disassemblers. Consumes a memory region @@ -58,12 +58,12 @@ public: MCDisassembler(const MCSubtargetInfo &STI) : GetOpInfo(0), SymbolLookUp(0), DisInfo(0), Ctx(0), STI(STI), CommentStream(0) {} - + virtual ~MCDisassembler(); - + /// getInstruction - Returns the disassembly of a single instruction. /// - /// @param instr - An MCInst to populate with the contents of the + /// @param instr - An MCInst to populate with the contents of the /// instruction. /// @param size - A value to populate with the size of the instruction, or /// the number of bytes consumed while attempting to decode @@ -74,7 +74,7 @@ public: /// @param vStream - The stream to print warnings and diagnostic messages on. /// @param cStream - The stream to print comments and annotations on. /// @return - MCDisassembler::Success if the instruction is valid, - /// MCDisassembler::SoftFail if the instruction was + /// MCDisassembler::SoftFail if the instruction was /// disassemblable but invalid, /// MCDisassembler::Fail if the instruction was invalid. virtual DecodeStatus getInstruction(MCInst& instr, diff --git a/include/llvm/MC/MCELFObjectWriter.h b/include/llvm/MC/MCELFObjectWriter.h index f153cb0..abbe188 100644 --- a/include/llvm/MC/MCELFObjectWriter.h +++ b/include/llvm/MC/MCELFObjectWriter.h @@ -54,11 +54,13 @@ class MCELFObjectTargetWriter { const uint16_t EMachine; const unsigned HasRelocationAddend : 1; const unsigned Is64Bit : 1; + const unsigned IsN64 : 1; protected: MCELFObjectTargetWriter(bool Is64Bit_, uint8_t OSABI_, - uint16_t EMachine_, bool HasRelocationAddend_); + uint16_t EMachine_, bool HasRelocationAddend, + bool IsN64=false); public: static uint8_t getOSABI(Triple::OSType OSType) { @@ -95,7 +97,47 @@ public: uint16_t getEMachine() { return EMachine; } bool hasRelocationAddend() { return HasRelocationAddend; } bool is64Bit() const { return Is64Bit; } + bool isN64() const { return IsN64; } /// @} + + // Instead of changing everyone's API we pack the N64 Type fields + // into the existing 32 bit data unsigned. +#define R_TYPE_SHIFT 0 +#define R_TYPE_MASK 0xffffff00 +#define R_TYPE2_SHIFT 8 +#define R_TYPE2_MASK 0xffff00ff +#define R_TYPE3_SHIFT 16 +#define R_TYPE3_MASK 0xff00ffff +#define R_SSYM_SHIFT 24 +#define R_SSYM_MASK 0x00ffffff + + // N64 relocation type accessors + unsigned getRType(uint32_t Type) const { + return (unsigned)((Type >> R_TYPE_SHIFT) & 0xff); + } + unsigned getRType2(uint32_t Type) const { + return (unsigned)((Type >> R_TYPE2_SHIFT) & 0xff); + } + unsigned getRType3(uint32_t Type) const { + return (unsigned)((Type >> R_TYPE3_SHIFT) & 0xff); + } + unsigned getRSsym(uint32_t Type) const { + return (unsigned)((Type >> R_SSYM_SHIFT) & 0xff); + } + + // N64 relocation type setting + unsigned setRType(unsigned Value, unsigned Type) const { + return ((Type & R_TYPE_MASK) | ((Value & 0xff) << R_TYPE_SHIFT)); + } + unsigned setRType2(unsigned Value, unsigned Type) const { + return (Type & R_TYPE2_MASK) | ((Value & 0xff) << R_TYPE2_SHIFT); + } + unsigned setRType3(unsigned Value, unsigned Type) const { + return (Type & R_TYPE3_MASK) | ((Value & 0xff) << R_TYPE3_SHIFT); + } + unsigned setRSsym(unsigned Value, unsigned Type) const { + return (Type & R_SSYM_MASK) | ((Value & 0xff) << R_SSYM_SHIFT); + } }; /// \brief Construct a new ELF writer instance. diff --git a/include/llvm/MC/MCExpr.h b/include/llvm/MC/MCExpr.h index ff33641..aa62eb2 100644 --- a/include/llvm/MC/MCExpr.h +++ b/include/llvm/MC/MCExpr.h @@ -176,6 +176,8 @@ public: VK_PPC_DARWIN_LO16, // lo16(symbol) VK_PPC_GAS_HA16, // symbol@ha VK_PPC_GAS_LO16, // symbol@l + VK_PPC_TPREL16_HA, // symbol@tprel@ha + VK_PPC_TPREL16_LO, // symbol@tprel@l VK_Mips_GPREL, VK_Mips_GOT_CALL, @@ -194,7 +196,9 @@ public: VK_Mips_GPOFF_LO, VK_Mips_GOT_DISP, VK_Mips_GOT_PAGE, - VK_Mips_GOT_OFST + VK_Mips_GOT_OFST, + VK_Mips_HIGHER, + VK_Mips_HIGHEST }; private: diff --git a/include/llvm/MC/MCFixupKindInfo.h b/include/llvm/MC/MCFixupKindInfo.h index 1961687..6979ad5 100644 --- a/include/llvm/MC/MCFixupKindInfo.h +++ b/include/llvm/MC/MCFixupKindInfo.h @@ -18,7 +18,7 @@ struct MCFixupKindInfo { /// Is this fixup kind PCrelative? This is used by the assembler backend to /// evaluate fixup values in a target independent manner when possible. FKF_IsPCRel = (1 << 0), - + /// Should this fixup kind force a 4-byte aligned effective PC value? FKF_IsAlignedDownTo32Bits = (1 << 1) }; diff --git a/include/llvm/MC/MCInstrItineraries.h b/include/llvm/MC/MCInstrItineraries.h index e942892..65d1559 100644 --- a/include/llvm/MC/MCInstrItineraries.h +++ b/include/llvm/MC/MCInstrItineraries.h @@ -16,6 +16,7 @@ #ifndef LLVM_MC_MCINSTRITINERARIES_H #define LLVM_MC_MCINSTRITINERARIES_H +#include "llvm/MC/MCSchedule.h" #include <algorithm> namespace llvm { @@ -95,7 +96,7 @@ struct InstrStage { /// operands are read and written. /// struct InstrItinerary { - unsigned NumMicroOps; ///< # of micro-ops, 0 means it's variable + int NumMicroOps; ///< # of micro-ops, -1 means it's variable unsigned FirstStage; ///< Index of first stage in itinerary unsigned LastStage; ///< Index of last + 1 stage in itinerary unsigned FirstOperandCycle; ///< Index of first operand rd/wr @@ -109,21 +110,22 @@ struct InstrItinerary { /// class InstrItineraryData { public: + const MCSchedModel *SchedModel; ///< Basic machine properties. const InstrStage *Stages; ///< Array of stages selected const unsigned *OperandCycles; ///< Array of operand cycles selected const unsigned *Forwardings; ///< Array of pipeline forwarding pathes const InstrItinerary *Itineraries; ///< Array of itineraries selected - unsigned IssueWidth; ///< Max issue per cycle. 0=Unknown. /// Ctors. /// - InstrItineraryData() : Stages(0), OperandCycles(0), Forwardings(0), - Itineraries(0), IssueWidth(0) {} + InstrItineraryData() : SchedModel(&MCSchedModel::DefaultSchedModel), + Stages(0), OperandCycles(0), + Forwardings(0), Itineraries(0) {} - InstrItineraryData(const InstrStage *S, const unsigned *OS, - const unsigned *F, const InstrItinerary *I) - : Stages(S), OperandCycles(OS), Forwardings(F), Itineraries(I), - IssueWidth(0) {} + InstrItineraryData(const MCSchedModel *SM, const InstrStage *S, + const unsigned *OS, const unsigned *F) + : SchedModel(SM), Stages(S), OperandCycles(OS), Forwardings(F), + Itineraries(SchedModel->InstrItineraries) {} /// isEmpty - Returns true if there are no itineraries. /// @@ -155,15 +157,17 @@ public: /// class. The latency is the maximum completion time for any stage /// in the itinerary. /// + /// InstrStages override the itinerary's MinLatency property. In fact, if the + /// stage latencies, which may be zero, are less than MinLatency, + /// getStageLatency returns a value less than MinLatency. + /// + /// If no stages exist, MinLatency is used. If MinLatency is invalid (<0), + /// then it defaults to one cycle. unsigned getStageLatency(unsigned ItinClassIndx) const { // If the target doesn't provide itinerary information, use a simple - // non-zero default value for all instructions. Some target's provide a - // dummy (Generic) itinerary which should be handled as if it's itinerary is - // empty. We identify this by looking for a reference to stage zero (invalid - // stage). This is different from beginStage == endState != 0, which could - // be used for zero-latency pseudo ops. - if (isEmpty() || Itineraries[ItinClassIndx].FirstStage == 0) - return 1; + // non-zero default value for all instructions. + if (isEmpty()) + return SchedModel->MinLatency < 0 ? 1 : SchedModel->MinLatency; // Calculate the maximum completion time for any stage. unsigned Latency = 0, StartCycle = 0; @@ -238,16 +242,16 @@ public: return UseCycle; } - /// isMicroCoded - Return true if the instructions in the given class decode - /// to more than one micro-ops. - bool isMicroCoded(unsigned ItinClassIndx) const { + /// getNumMicroOps - Return the number of micro-ops that the given class + /// decodes to. Return -1 for classes that require dynamic lookup via + /// TargetInstrInfo. + int getNumMicroOps(unsigned ItinClassIndx) const { if (isEmpty()) - return false; - return Itineraries[ItinClassIndx].NumMicroOps != 1; + return 1; + return Itineraries[ItinClassIndx].NumMicroOps; } }; - } // End llvm namespace #endif diff --git a/include/llvm/MC/MCMachObjectWriter.h b/include/llvm/MC/MCMachObjectWriter.h index 9bb598f..949d907 100644 --- a/include/llvm/MC/MCMachObjectWriter.h +++ b/include/llvm/MC/MCMachObjectWriter.h @@ -179,6 +179,9 @@ public: void WriteNlist(MachSymbolData &MSD, const MCAsmLayout &Layout); + void WriteLinkeditLoadCommand(uint32_t Type, uint32_t DataOffset, + uint32_t DataSize); + // FIXME: We really need to improve the relocation validation. Basically, we // want to implement a separate computation which evaluates the relocation // entry as the linker would, and verifies that the resultant fixup value is diff --git a/include/llvm/MC/MCObjectFileInfo.h b/include/llvm/MC/MCObjectFileInfo.h index aea4b41..74e2263 100644 --- a/include/llvm/MC/MCObjectFileInfo.h +++ b/include/llvm/MC/MCObjectFileInfo.h @@ -22,17 +22,17 @@ namespace llvm { class StringRef; class Triple; -class MCObjectFileInfo { +class MCObjectFileInfo { protected: /// CommDirectiveSupportsAlignment - True if .comm supports alignment. This /// is a hack for as long as we support 10.4 Tiger, whose assembler doesn't /// support alignment on comm. bool CommDirectiveSupportsAlignment; - + /// SupportsWeakEmptyEHFrame - True if target object file supports a /// weak_definition of constant 0 for an omitted EH frame. bool SupportsWeakOmittedEHFrame; - + /// IsFunctionEHFrameSymbolPrivate - This flag is set to true if the /// "EH_frame" symbol for EH information should be an assembler temporary (aka /// private linkage, aka an L or .L label) or false if it should be a normal @@ -53,20 +53,20 @@ protected: /// TextSection - Section directive for standard text. /// const MCSection *TextSection; - + /// DataSection - Section directive for standard data. /// const MCSection *DataSection; - + /// BSSSection - Section that is default initialized to zero. const MCSection *BSSSection; - + /// ReadOnlySection - Section that is readonly and can contain arbitrary /// initialized data. Targets are not required to have a readonly section. /// If they don't, various bits of code will fall back to using the data /// section for constants. const MCSection *ReadOnlySection; - + /// StaticCtorSection - This section contains the static constructor pointer /// list. const MCSection *StaticCtorSection; @@ -74,7 +74,7 @@ protected: /// StaticDtorSection - This section contains the static destructor pointer /// list. const MCSection *StaticDtorSection; - + /// LSDASection - If exception handling is supported by the target, this is /// the section the Language Specific Data Area information is emitted to. const MCSection *LSDASection; @@ -109,7 +109,7 @@ protected: // Extra TLS Variable Data section. If the target needs to put additional // information for a TLS variable, it'll go here. const MCSection *TLSExtraDataSection; - + /// TLSDataSection - Section directive for Thread Local data. /// ELF, MachO and COFF. const MCSection *TLSDataSection; // Defaults to ".tdata". @@ -141,11 +141,11 @@ protected: /// Contains the source code name of the variable, visibility and a pointer /// to the initial value (.tdata or .tbss). const MCSection *TLSTLVSection; // Defaults to ".tlv". - + /// TLSThreadInitSection - Section for thread local data initialization /// functions. const MCSection *TLSThreadInitSection; // Defaults to ".thread_init_func". - + const MCSection *CStringSection; const MCSection *UStringSection; const MCSection *TextCoalSection; @@ -169,7 +169,7 @@ protected: public: void InitMCObjectFileInfo(StringRef TT, Reloc::Model RM, CodeModel::Model CM, MCContext &ctx); - + bool isFunctionEHFrameSymbolPrivate() const { return IsFunctionEHFrameSymbolPrivate; } diff --git a/include/llvm/MC/MCObjectWriter.h b/include/llvm/MC/MCObjectWriter.h index 6e44e6ce..9591a00 100644 --- a/include/llvm/MC/MCObjectWriter.h +++ b/include/llvm/MC/MCObjectWriter.h @@ -182,11 +182,6 @@ public: /// @} - /// Utility function to encode a SLEB128 value. - static void EncodeSLEB128(int64_t Value, raw_ostream &OS); - /// Utility function to encode a ULEB128 value. - static void EncodeULEB128(uint64_t Value, raw_ostream &OS, - unsigned Padding = 0); }; } // End llvm namespace diff --git a/include/llvm/MC/MCRegisterInfo.h b/include/llvm/MC/MCRegisterInfo.h index 27acf2f..46a9d71 100644 --- a/include/llvm/MC/MCRegisterInfo.h +++ b/include/llvm/MC/MCRegisterInfo.h @@ -106,10 +106,18 @@ public: /// of AX. /// struct MCRegisterDesc { - const char *Name; // Printable name for the reg (for debugging) - uint32_t Overlaps; // Overlapping registers, described above - uint32_t SubRegs; // Sub-register set, described above - uint32_t SuperRegs; // Super-register set, described above + uint32_t Name; // Printable name for the reg (for debugging) + uint32_t Overlaps; // Overlapping registers, described above + uint32_t SubRegs; // Sub-register set, described above + uint32_t SuperRegs; // Super-register set, described above + + // Offset into MCRI::SubRegIndices of a list of sub-register indices for each + // sub-register in SubRegs. + uint32_t SubRegIndices; + + // RegUnits - Points to the list of register units. The low 4 bits holds the + // Scale, the high bits hold an offset into DiffLists. See MCRegUnitIterator. + uint32_t RegUnits; }; /// MCRegisterInfo base class - We assume that the target defines a static @@ -142,10 +150,15 @@ private: unsigned RAReg; // Return address register const MCRegisterClass *Classes; // Pointer to the regclass array unsigned NumClasses; // Number of entries in the array - const uint16_t *RegLists; // Pointer to the reglists array + unsigned NumRegUnits; // Number of regunits. + const uint16_t (*RegUnitRoots)[2]; // Pointer to regunit root table. + const uint16_t *DiffLists; // Pointer to the difflists array + const char *RegStrings; // Pointer to the string table. const uint16_t *SubRegIndices; // Pointer to the subreg lookup // array. unsigned NumSubRegIndices; // Number of subreg indices. + const uint16_t *RegEncodingTable; // Pointer to array of register + // encodings. unsigned L2DwarfRegsSize; unsigned EHL2DwarfRegsSize; @@ -158,21 +171,83 @@ private: DenseMap<unsigned, int> L2SEHRegs; // LLVM to SEH regs mapping public: + /// DiffListIterator - Base iterator class that can traverse the + /// differentially encoded register and regunit lists in DiffLists. + /// Don't use this class directly, use one of the specialized sub-classes + /// defined below. + class DiffListIterator { + uint16_t Val; + const uint16_t *List; + + protected: + /// Create an invalid iterator. Call init() to point to something useful. + DiffListIterator() : Val(0), List(0) {} + + /// init - Point the iterator to InitVal, decoding subsequent values from + /// DiffList. The iterator will initially point to InitVal, sub-classes are + /// responsible for skipping the seed value if it is not part of the list. + void init(uint16_t InitVal, const uint16_t *DiffList) { + Val = InitVal; + List = DiffList; + } + + /// advance - Move to the next list position, return the applied + /// differential. This function does not detect the end of the list, that + /// is the caller's responsibility (by checking for a 0 return value). + unsigned advance() { + assert(isValid() && "Cannot move off the end of the list."); + uint16_t D = *List++; + Val += D; + return D; + } + + public: + + /// isValid - returns true if this iterator is not yet at the end. + bool isValid() const { return List; } + + /// Dereference the iterator to get the value at the current position. + unsigned operator*() const { return Val; } + + /// Pre-increment to move to the next position. + void operator++() { + // The end of the list is encoded as a 0 differential. + if (!advance()) + List = 0; + } + }; + + // These iterators are allowed to sub-class DiffListIterator and access + // internal list pointers. + friend class MCSubRegIterator; + friend class MCSuperRegIterator; + friend class MCRegAliasIterator; + friend class MCRegUnitIterator; + friend class MCRegUnitRootIterator; + /// InitMCRegisterInfo - Initialize MCRegisterInfo, called by TableGen /// auto-generated routines. *DO NOT USE*. void InitMCRegisterInfo(const MCRegisterDesc *D, unsigned NR, unsigned RA, const MCRegisterClass *C, unsigned NC, - const uint16_t *RL, + const uint16_t (*RURoots)[2], + unsigned NRU, + const uint16_t *DL, + const char *Strings, const uint16_t *SubIndices, - unsigned NumIndices) { + unsigned NumIndices, + const uint16_t *RET) { Desc = D; NumRegs = NR; RAReg = RA; Classes = C; - RegLists = RL; + DiffLists = DL; + RegStrings = Strings; NumClasses = NC; + RegUnitRoots = RURoots; + NumRegUnits = NRU; SubRegIndices = SubIndices; NumSubRegIndices = NumIndices; + RegEncodingTable = RET; } /// mapLLVMRegsToDwarfRegs - Used to initialize LLVM register to Dwarf @@ -231,73 +306,25 @@ public: return operator[](RegNo); } - /// getAliasSet - Return the set of registers aliased by the specified - /// register, or a null list of there are none. The list returned is zero - /// terminated. - /// - const uint16_t *getAliasSet(unsigned RegNo) const { - // The Overlaps set always begins with Reg itself. - return RegLists + get(RegNo).Overlaps + 1; - } - - /// getOverlaps - Return a list of registers that overlap Reg, including - /// itself. This is the same as the alias set except Reg is included in the - /// list. - /// These are exactly the registers in { x | regsOverlap(x, Reg) }. - /// - const uint16_t *getOverlaps(unsigned RegNo) const { - return RegLists + get(RegNo).Overlaps; - } - - /// getSubRegisters - Return the list of registers that are sub-registers of - /// the specified register, or a null list of there are none. The list - /// returned is zero terminated and sorted according to super-sub register - /// relations. e.g. X86::RAX's sub-register list is EAX, AX, AL, AH. - /// - const uint16_t *getSubRegisters(unsigned RegNo) const { - return RegLists + get(RegNo).SubRegs; - } - /// getSubReg - Returns the physical register number of sub-register "Index" /// for physical register RegNo. Return zero if the sub-register does not /// exist. - unsigned getSubReg(unsigned Reg, unsigned Idx) const { - return *(SubRegIndices + (Reg - 1) * NumSubRegIndices + Idx - 1); - } + unsigned getSubReg(unsigned Reg, unsigned Idx) const; /// getMatchingSuperReg - Return a super-register of the specified register /// Reg so its sub-register of index SubIdx is Reg. unsigned getMatchingSuperReg(unsigned Reg, unsigned SubIdx, - const MCRegisterClass *RC) const { - for (const uint16_t *SRs = getSuperRegisters(Reg); unsigned SR = *SRs;++SRs) - if (Reg == getSubReg(SR, SubIdx) && RC->contains(SR)) - return SR; - return 0; - } + const MCRegisterClass *RC) const; /// getSubRegIndex - For a given register pair, return the sub-register index /// if the second register is a sub-register of the first. Return zero /// otherwise. - unsigned getSubRegIndex(unsigned RegNo, unsigned SubRegNo) const { - for (unsigned I = 1; I <= NumSubRegIndices; ++I) - if (getSubReg(RegNo, I) == SubRegNo) - return I; - return 0; - } - - /// getSuperRegisters - Return the list of registers that are super-registers - /// of the specified register, or a null list of there are none. The list - /// returned is zero terminated and sorted according to super-sub register - /// relations. e.g. X86::AL's super-register list is AX, EAX, RAX. - /// - const uint16_t *getSuperRegisters(unsigned RegNo) const { - return RegLists + get(RegNo).SuperRegs; - } + unsigned getSubRegIndex(unsigned RegNo, unsigned SubRegNo) const; /// getName - Return the human-readable symbolic target-specific name for the /// specified physical register. const char *getName(unsigned RegNo) const { - return get(RegNo).Name; + return RegStrings + get(RegNo).Name; } /// getNumRegs - Return the number of registers this target has (useful for @@ -306,40 +333,26 @@ public: return NumRegs; } + /// getNumRegUnits - Return the number of (native) register units in the + /// target. Register units are numbered from 0 to getNumRegUnits() - 1. They + /// can be accessed through MCRegUnitIterator defined below. + unsigned getNumRegUnits() const { + return NumRegUnits; + } + /// getDwarfRegNum - Map a target register to an equivalent dwarf register /// number. Returns -1 if there is no equivalent value. The second /// parameter allows targets to use different numberings for EH info and /// debugging info. - int getDwarfRegNum(unsigned RegNum, bool isEH) const { - const DwarfLLVMRegPair *M = isEH ? EHL2DwarfRegs : L2DwarfRegs; - unsigned Size = isEH ? EHL2DwarfRegsSize : L2DwarfRegsSize; - - DwarfLLVMRegPair Key = { RegNum, 0 }; - const DwarfLLVMRegPair *I = std::lower_bound(M, M+Size, Key); - if (I == M+Size || I->FromReg != RegNum) - return -1; - return I->ToReg; - } + int getDwarfRegNum(unsigned RegNum, bool isEH) const; /// getLLVMRegNum - Map a dwarf register back to a target register. /// - int getLLVMRegNum(unsigned RegNum, bool isEH) const { - const DwarfLLVMRegPair *M = isEH ? EHDwarf2LRegs : Dwarf2LRegs; - unsigned Size = isEH ? EHDwarf2LRegsSize : Dwarf2LRegsSize; - - DwarfLLVMRegPair Key = { RegNum, 0 }; - const DwarfLLVMRegPair *I = std::lower_bound(M, M+Size, Key); - assert(I != M+Size && I->FromReg == RegNum && "Invalid RegNum"); - return I->ToReg; - } + int getLLVMRegNum(unsigned RegNum, bool isEH) const; /// getSEHRegNum - Map a target register to an equivalent SEH register /// number. Returns LLVM register number if there is no equivalent value. - int getSEHRegNum(unsigned RegNum) const { - const DenseMap<unsigned, int>::const_iterator I = L2SEHRegs.find(RegNum); - if (I == L2SEHRegs.end()) return (int)RegNum; - return I->second; - } + int getSEHRegNum(unsigned RegNum) const; regclass_iterator regclass_begin() const { return Classes; } regclass_iterator regclass_end() const { return Classes+NumClasses; } @@ -354,6 +367,128 @@ public: assert(i < getNumRegClasses() && "Register Class ID out of range"); return Classes[i]; } + + /// getEncodingValue - Returns the encoding for RegNo + uint16_t getEncodingValue(unsigned RegNo) const { + assert(RegNo < NumRegs && + "Attempting to get encoding for invalid register number!"); + return RegEncodingTable[RegNo]; + } + +}; + +//===----------------------------------------------------------------------===// +// Register List Iterators +//===----------------------------------------------------------------------===// + +// MCRegisterInfo provides lists of super-registers, sub-registers, and +// aliasing registers. Use these iterator classes to traverse the lists. + +/// MCSubRegIterator enumerates all sub-registers of Reg. +class MCSubRegIterator : public MCRegisterInfo::DiffListIterator { +public: + MCSubRegIterator(unsigned Reg, const MCRegisterInfo *MCRI) { + init(Reg, MCRI->DiffLists + MCRI->get(Reg).SubRegs); + ++*this; + } +}; + +/// MCSuperRegIterator enumerates all super-registers of Reg. +class MCSuperRegIterator : public MCRegisterInfo::DiffListIterator { +public: + MCSuperRegIterator(unsigned Reg, const MCRegisterInfo *MCRI) { + init(Reg, MCRI->DiffLists + MCRI->get(Reg).SuperRegs); + ++*this; + } +}; + +/// MCRegAliasIterator enumerates all registers aliasing Reg. +/// If IncludeSelf is set, Reg itself is included in the list. +class MCRegAliasIterator : public MCRegisterInfo::DiffListIterator { +public: + MCRegAliasIterator(unsigned Reg, const MCRegisterInfo *MCRI, + bool IncludeSelf) { + init(Reg, MCRI->DiffLists + MCRI->get(Reg).Overlaps); + // Initially, the iterator points to Reg itself. + if (!IncludeSelf) + ++*this; + } +}; + +//===----------------------------------------------------------------------===// +// Register Units +//===----------------------------------------------------------------------===// + +// Register units are used to compute register aliasing. Every register has at +// least one register unit, but it can have more. Two registers overlap if and +// only if they have a common register unit. +// +// A target with a complicated sub-register structure will typically have many +// fewer register units than actual registers. MCRI::getNumRegUnits() returns +// the number of register units in the target. + +// MCRegUnitIterator enumerates a list of register units for Reg. The list is +// in ascending numerical order. +class MCRegUnitIterator : public MCRegisterInfo::DiffListIterator { +public: + /// MCRegUnitIterator - Create an iterator that traverses the register units + /// in Reg. + MCRegUnitIterator(unsigned Reg, const MCRegisterInfo *MCRI) { + // Decode the RegUnits MCRegisterDesc field. + unsigned RU = MCRI->get(Reg).RegUnits; + unsigned Scale = RU & 15; + unsigned Offset = RU >> 4; + + // Initialize the iterator to Reg * Scale, and the List pointer to + // DiffLists + Offset. + init(Reg * Scale, MCRI->DiffLists + Offset); + + // That may not be a valid unit, we need to advance by one to get the real + // unit number. The first differential can be 0 which would normally + // terminate the list, but since we know every register has at least one + // unit, we can allow a 0 differential here. + advance(); + } +}; + +// Each register unit has one or two root registers. The complete set of +// registers containing a register unit is the union of the roots and their +// super-registers. All registers aliasing Unit can be visited like this: +// +// for (MCRegUnitRootIterator RI(Unit, MCRI); RI.isValid(); ++RI) { +// unsigned Root = *RI; +// visit(Root); +// for (MCSuperRegIterator SI(Root, MCRI); SI.isValid(); ++SI) +// visit(*SI); +// } + +/// MCRegUnitRootIterator enumerates the root registers of a register unit. +class MCRegUnitRootIterator { + uint16_t Reg0; + uint16_t Reg1; +public: + MCRegUnitRootIterator(unsigned RegUnit, const MCRegisterInfo *MCRI) { + assert(RegUnit < MCRI->getNumRegUnits() && "Invalid register unit"); + Reg0 = MCRI->RegUnitRoots[RegUnit][0]; + Reg1 = MCRI->RegUnitRoots[RegUnit][1]; + } + + /// Dereference to get the current root register. + unsigned operator*() const { + return Reg0; + } + + /// isValid - Check if the iterator is at the end of the list. + bool isValid() const { + return Reg0; + } + + /// Preincrement to move to the next root register. + void operator++() { + assert(isValid() && "Cannot move off the end of the list."); + Reg0 = Reg1; + Reg1 = 0; + } }; } // End llvm namespace diff --git a/include/llvm/MC/MCSchedule.h b/include/llvm/MC/MCSchedule.h new file mode 100644 index 0000000..3b1cdf1 --- /dev/null +++ b/include/llvm/MC/MCSchedule.h @@ -0,0 +1,114 @@ +//===-- llvm/MC/MCSchedule.h - Scheduling -----------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +// +// This file defines the classes used to describe a subtarget's machine model +// for scheduling and other instruction cost heuristics. +// +//===----------------------------------------------------------------------===// + +#ifndef LLVM_MC_MCSCHEDMODEL_H +#define LLVM_MC_MCSCHEDMODEL_H + +#include "llvm/Support/DataTypes.h" + +namespace llvm { + +struct InstrItinerary; + +/// Machine model for scheduling, bundling, and heuristics. +/// +/// The machine model directly provides basic information about the +/// microarchitecture to the scheduler in the form of properties. It also +/// optionally refers to scheduler resources tables and itinerary +/// tables. Scheduler resources tables model the latency and cost for each +/// instruction type. Itinerary tables are an independant mechanism that +/// provides a detailed reservation table describing each cycle of instruction +/// execution. Subtargets may define any or all of the above categories of data +/// depending on the type of CPU and selected scheduler. +class MCSchedModel { +public: + static MCSchedModel DefaultSchedModel; // For unknown processors. + + // IssueWidth is the maximum number of instructions that may be scheduled in + // the same per-cycle group. + unsigned IssueWidth; + static const unsigned DefaultIssueWidth = 1; + + // MinLatency is the minimum latency between a register write + // followed by a data dependent read. This determines which + // instructions may be scheduled in the same per-cycle group. This + // is distinct from *expected* latency, which determines the likely + // critical path but does not guarantee a pipeline + // hazard. MinLatency can always be overridden by the number of + // InstrStage cycles. + // + // (-1) Standard in-order processor. + // Use InstrItinerary OperandCycles as MinLatency. + // If no OperandCycles exist, then use the cycle of the last InstrStage. + // + // (0) Out-of-order processor, or in-order with bundled dependencies. + // RAW dependencies may be dispatched in the same cycle. + // Optional InstrItinerary OperandCycles provides expected latency. + // + // (>0) In-order processor with variable latencies. + // Use the greater of this value or the cycle of the last InstrStage. + // Optional InstrItinerary OperandCycles provides expected latency. + // TODO: can't yet specify both min and expected latency per operand. + int MinLatency; + static const unsigned DefaultMinLatency = -1; + + // LoadLatency is the expected latency of load instructions. + // + // If MinLatency >= 0, this may be overriden for individual load opcodes by + // InstrItinerary OperandCycles. + unsigned LoadLatency; + static const unsigned DefaultLoadLatency = 4; + + // HighLatency is the expected latency of "very high latency" operations. + // See TargetInstrInfo::isHighLatencyDef(). + // By default, this is set to an arbitrarily high number of cycles + // likely to have some impact on scheduling heuristics. + // If MinLatency >= 0, this may be overriden by InstrItinData OperandCycles. + unsigned HighLatency; + static const unsigned DefaultHighLatency = 10; + + // MispredictPenalty is the typical number of extra cycles the processor + // takes to recover from a branch misprediction. + unsigned MispredictPenalty; + static const unsigned DefaultMispredictPenalty = 10; + +private: + // TODO: Add a reference to proc resource types and sched resource tables. + + // Instruction itinerary tables used by InstrItineraryData. + friend class InstrItineraryData; + const InstrItinerary *InstrItineraries; + +public: + // Default's must be specified as static const literals so that tablegenerated + // target code can use it in static initializers. The defaults need to be + // initialized in this default ctor because some clients directly instantiate + // MCSchedModel instead of using a generated itinerary. + MCSchedModel(): IssueWidth(DefaultIssueWidth), + MinLatency(DefaultMinLatency), + LoadLatency(DefaultLoadLatency), + HighLatency(DefaultHighLatency), + MispredictPenalty(DefaultMispredictPenalty), + InstrItineraries(0) {} + + // Table-gen driven ctor. + MCSchedModel(unsigned iw, int ml, unsigned ll, unsigned hl, unsigned mp, + const InstrItinerary *ii): + IssueWidth(iw), MinLatency(ml), LoadLatency(ll), HighLatency(hl), + MispredictPenalty(mp), InstrItineraries(ii){} +}; + +} // End llvm namespace + +#endif diff --git a/include/llvm/MC/MCStreamer.h b/include/llvm/MC/MCStreamer.h index 2595600..e8c3e59 100644 --- a/include/llvm/MC/MCStreamer.h +++ b/include/llvm/MC/MCStreamer.h @@ -69,22 +69,7 @@ namespace llvm { SmallVector<std::pair<const MCSection *, const MCSection *>, 4> SectionStack; - unsigned UniqueCodeBeginSuffix; - unsigned UniqueDataBeginSuffix; - protected: - /// Indicator of whether the previous data-or-code indicator was for - /// code or not. Used to determine when we need to emit a new indicator. - enum DataType { - Data, - Code, - JumpTable8, - JumpTable16, - JumpTable32 - }; - DataType RegionIndicator; - - MCStreamer(MCContext &Ctx); const MCExpr *BuildSymbolDiff(MCContext &Context, const MCSymbol *A, @@ -241,47 +226,15 @@ namespace llvm { /// used in an assignment. virtual void EmitLabel(MCSymbol *Symbol); - /// EmitDataRegion - Emit a label that marks the beginning of a data - /// region. - /// On ELF targets, this corresponds to an assembler statement such as: - /// $d.1: - virtual void EmitDataRegion(); - - /// EmitJumpTable8Region - Emit a label that marks the beginning of a - /// jump table composed of 8-bit offsets. - /// On ELF targets, this corresponds to an assembler statement such as: - /// $d.1: - virtual void EmitJumpTable8Region(); - - /// EmitJumpTable16Region - Emit a label that marks the beginning of a - /// jump table composed of 16-bit offsets. - /// On ELF targets, this corresponds to an assembler statement such as: - /// $d.1: - virtual void EmitJumpTable16Region(); - - /// EmitJumpTable32Region - Emit a label that marks the beginning of a - /// jump table composed of 32-bit offsets. - /// On ELF targets, this corresponds to an assembler statement such as: - /// $d.1: - virtual void EmitJumpTable32Region(); - - /// EmitCodeRegion - Emit a label that marks the beginning of a code - /// region. - /// On ELF targets, this corresponds to an assembler statement such as: - /// $a.1: - virtual void EmitCodeRegion(); - - /// ForceCodeRegion - Forcibly sets the current region mode to code. Used - /// at function entry points. - void ForceCodeRegion() { RegionIndicator = Code; } - - virtual void EmitEHSymAttributes(const MCSymbol *Symbol, MCSymbol *EHSymbol); - /// EmitAssemblerFlag - Note in the output the specified @p Flag + /// EmitAssemblerFlag - Note in the output the specified @p Flag. virtual void EmitAssemblerFlag(MCAssemblerFlag Flag) = 0; + /// EmitDataRegion - Note in the output the specified region @p Kind. + virtual void EmitDataRegion(MCDataRegionType Kind) {} + /// EmitThumbFunc - Note in the output that the specified @p Func is /// a Thumb mode function (ARM target only). virtual void EmitThumbFunc(MCSymbol *Func) = 0; @@ -373,7 +326,7 @@ namespace llvm { /// @param ByteAlignment - The alignment of the zerofill symbol if /// non-zero. This must be a power of 2 on some targets. virtual void EmitZerofill(const MCSection *Section, MCSymbol *Symbol = 0, - unsigned Size = 0,unsigned ByteAlignment = 0) = 0; + uint64_t Size = 0,unsigned ByteAlignment = 0) = 0; /// EmitTBSSSymbol - Emit a thread local bss (.tbss) symbol. /// diff --git a/include/llvm/MC/MCSubtargetInfo.h b/include/llvm/MC/MCSubtargetInfo.h index 3b53f20..31d632d 100644 --- a/include/llvm/MC/MCSubtargetInfo.h +++ b/include/llvm/MC/MCSubtargetInfo.h @@ -30,10 +30,10 @@ class MCSubtargetInfo { std::string TargetTriple; // Target triple const SubtargetFeatureKV *ProcFeatures; // Processor feature list const SubtargetFeatureKV *ProcDesc; // Processor descriptions - const SubtargetInfoKV *ProcItins; // Scheduling itineraries - const InstrStage *Stages; // Instruction stages - const unsigned *OperandCycles; // Operand cycles - const unsigned *ForwardingPathes; // Forwarding pathes + const SubtargetInfoKV *ProcSchedModel; // Scheduler machine model + const InstrStage *Stages; // Instruction itinerary stages + const unsigned *OperandCycles; // Itinerary operand cycles + const unsigned *ForwardingPaths; // Forwarding paths unsigned NumFeatures; // Number of processor features unsigned NumProcs; // Number of processors uint64_t FeatureBits; // Feature bits for current CPU + FS @@ -42,7 +42,8 @@ public: void InitMCSubtargetInfo(StringRef TT, StringRef CPU, StringRef FS, const SubtargetFeatureKV *PF, const SubtargetFeatureKV *PD, - const SubtargetInfoKV *PI, const InstrStage *IS, + const SubtargetInfoKV *ProcSched, + const InstrStage *IS, const unsigned *OC, const unsigned *FP, unsigned NF, unsigned NP); @@ -69,6 +70,10 @@ public: /// bits. This version will also change all implied bits. uint64_t ToggleFeature(StringRef FS); + /// getSchedModelForCPU - Get the machine model of a CPU. + /// + MCSchedModel *getSchedModelForCPU(StringRef CPU) const; + /// getInstrItineraryForCPU - Get scheduling itinerary of a CPU. /// InstrItineraryData getInstrItineraryForCPU(StringRef CPU) const; diff --git a/include/llvm/MC/MCTargetAsmLexer.h b/include/llvm/MC/MCTargetAsmLexer.h index acb3d4d..f5c8c09 100644 --- a/include/llvm/MC/MCTargetAsmLexer.h +++ b/include/llvm/MC/MCTargetAsmLexer.h @@ -14,72 +14,72 @@ namespace llvm { class Target; - + /// MCTargetAsmLexer - Generic interface to target specific assembly lexers. class MCTargetAsmLexer { /// The current token AsmToken CurTok; - + /// The location and description of the current error SMLoc ErrLoc; std::string Err; - + MCTargetAsmLexer(const MCTargetAsmLexer &); // DO NOT IMPLEMENT void operator=(const MCTargetAsmLexer &); // DO NOT IMPLEMENT protected: // Can only create subclasses. MCTargetAsmLexer(const Target &); - + virtual AsmToken LexToken() = 0; - + void SetError(const SMLoc &errLoc, const std::string &err) { ErrLoc = errLoc; Err = err; } - + /// TheTarget - The Target that this machine was created for. const Target &TheTarget; MCAsmLexer *Lexer; - + public: virtual ~MCTargetAsmLexer(); - + const Target &getTarget() const { return TheTarget; } - + /// InstallLexer - Set the lexer to get tokens from lower-level lexer \arg L. void InstallLexer(MCAsmLexer &L) { Lexer = &L; } - + MCAsmLexer *getLexer() { return Lexer; } - + /// Lex - Consume the next token from the input stream and return it. const AsmToken &Lex() { return CurTok = LexToken(); } - + /// getTok - Get the current (last) lexed token. const AsmToken &getTok() { return CurTok; } - + /// getErrLoc - Get the current error location const SMLoc &getErrLoc() { return ErrLoc; } - + /// getErr - Get the current error string const std::string &getErr() { return Err; } - + /// getKind - Get the kind of current token. AsmToken::TokenKind getKind() const { return CurTok.getKind(); } - + /// is - Check if the current token has kind \arg K. bool is(AsmToken::TokenKind K) const { return CurTok.is(K); } - + /// isNot - Check if the current token has kind \arg K. bool isNot(AsmToken::TokenKind K) const { return CurTok.isNot(K); } }; diff --git a/include/llvm/MC/MCTargetAsmParser.h b/include/llvm/MC/MCTargetAsmParser.h index 4e3fd0d..929a204 100644 --- a/include/llvm/MC/MCTargetAsmParser.h +++ b/include/llvm/MC/MCTargetAsmParser.h @@ -79,6 +79,19 @@ public: /// \param DirectiveID - the identifier token of the directive. virtual bool ParseDirective(AsmToken DirectiveID) = 0; + /// MatchInstruction - Recognize a series of operands of a parsed instruction + /// as an actual MCInst. This returns false on success and returns true on + /// failure to match. + /// + /// On failure, the target parser is responsible for emitting a diagnostic + /// explaining the match failure. + virtual bool + MatchInstruction(SMLoc IDLoc, + SmallVectorImpl<MCParsedAsmOperand*> &Operands, + SmallVectorImpl<MCInst> &MCInsts) { + return true; + } + /// MatchAndEmitInstruction - Recognize a series of operands of a parsed /// instruction as an actual MCInst and emit it to the specified MCStreamer. /// This returns false on success and returns true on failure to match. diff --git a/include/llvm/MC/MachineLocation.h b/include/llvm/MC/MachineLocation.h index 8ddfdbc..5caad33 100644 --- a/include/llvm/MC/MachineLocation.h +++ b/include/llvm/MC/MachineLocation.h @@ -11,7 +11,7 @@ // from a base address plus an offset. Register indirection can be specified by // using an offset of zero. // -// The MachineMove class is used to represent abstract move operations in the +// The MachineMove class is used to represent abstract move operations in the // prolog/epilog of a compiled function. A collection of these objects can be // used by a debug consumer to track the location of values when unwinding stack // frames. @@ -23,7 +23,7 @@ namespace llvm { class MCSymbol; - + class MachineLocation { private: bool IsRegister; // True if location is a register. @@ -46,7 +46,7 @@ public: return IsRegister == Other.IsRegister && Register == Other.Register && Offset == Other.Offset; } - + // Accessors bool isReg() const { return IsRegister; } unsigned getReg() const { return Register; } @@ -77,7 +77,7 @@ private: /// Label - Symbol for post-instruction address when result of move takes /// effect. MCSymbol *Label; - + // Move to & from location. MachineLocation Destination, Source; public: @@ -86,7 +86,7 @@ public: MachineMove(MCSymbol *label, const MachineLocation &D, const MachineLocation &S) : Label(label), Destination(D), Source(S) {} - + // Accessors MCSymbol *getLabel() const { return Label; } const MachineLocation &getDestination() const { return Destination; } diff --git a/include/llvm/MC/SubtargetFeature.h b/include/llvm/MC/SubtargetFeature.h index 1a7dc92..507d882 100644 --- a/include/llvm/MC/SubtargetFeature.h +++ b/include/llvm/MC/SubtargetFeature.h @@ -25,7 +25,7 @@ namespace llvm { class raw_ostream; class StringRef; - + //===----------------------------------------------------------------------===// /// /// SubtargetFeatureKV - Used to provide key value pairs for feature and @@ -36,13 +36,13 @@ struct SubtargetFeatureKV { const char *Desc; // Help descriptor uint64_t Value; // K-V integer value uint64_t Implies; // K-V bit mask - + // Compare routine for std binary search bool operator<(const SubtargetFeatureKV &S) const { return strcmp(Key, S.Key) < 0; } }; - + //===----------------------------------------------------------------------===// /// /// SubtargetInfoKV - Used to provide key value pairs for CPU and arbitrary @@ -51,16 +51,16 @@ struct SubtargetFeatureKV { struct SubtargetInfoKV { const char *Key; // K-V key string void *Value; // K-V pointer value - + // Compare routine for std binary search bool operator<(const SubtargetInfoKV &S) const { return strcmp(Key, S.Key) < 0; } }; - + //===----------------------------------------------------------------------===// /// -/// SubtargetFeatures - Manages the enabling and disabling of subtarget +/// SubtargetFeatures - Manages the enabling and disabling of subtarget /// specific features. Features are encoded as a string of the form /// "cpu,+attr1,+attr2,-attr3,...,+attrN" /// A comma separates each feature from the next (all lowercase.) @@ -81,27 +81,27 @@ public: /// Adding Features. void AddFeature(const StringRef String, bool IsEnabled = true); - + /// ToggleFeature - Toggle a feature and returns the newly updated feature /// bits. uint64_t ToggleFeature(uint64_t Bits, const StringRef String, const SubtargetFeatureKV *FeatureTable, size_t FeatureTableSize); - + /// Get feature bits of a CPU. uint64_t getFeatureBits(const StringRef CPU, const SubtargetFeatureKV *CPUTable, size_t CPUTableSize, const SubtargetFeatureKV *FeatureTable, size_t FeatureTableSize); - + /// Get scheduling itinerary of a CPU. void *getItinerary(const StringRef CPU, const SubtargetInfoKV *Table, size_t TableSize); - + /// Print feature string. void print(raw_ostream &OS) const; - + // Dump feature info. void dump() const; |