diff options
author | rdivacky <rdivacky@FreeBSD.org> | 2010-05-27 15:15:58 +0000 |
---|---|---|
committer | rdivacky <rdivacky@FreeBSD.org> | 2010-05-27 15:15:58 +0000 |
commit | 1e3dec662ea18131c495db50caccc57f77b7a5fe (patch) | |
tree | 9fad9a5d5dd8c4ff54af48edad9c8cc26dd5fda1 /include/llvm/Target | |
parent | 377552607e51dc1d3e6ff33833f9620bcfe815ac (diff) | |
download | FreeBSD-src-1e3dec662ea18131c495db50caccc57f77b7a5fe.zip FreeBSD-src-1e3dec662ea18131c495db50caccc57f77b7a5fe.tar.gz |
Update LLVM to r104832.
Diffstat (limited to 'include/llvm/Target')
-rw-r--r-- | include/llvm/Target/SubtargetFeature.h | 7 | ||||
-rw-r--r-- | include/llvm/Target/Target.td | 54 | ||||
-rw-r--r-- | include/llvm/Target/TargetAsmBackend.h | 27 | ||||
-rw-r--r-- | include/llvm/Target/TargetInstrInfo.h | 15 | ||||
-rw-r--r-- | include/llvm/Target/TargetLowering.h | 211 | ||||
-rw-r--r-- | include/llvm/Target/TargetLoweringObjectFile.h | 7 | ||||
-rw-r--r-- | include/llvm/Target/TargetMachine.h | 32 | ||||
-rw-r--r-- | include/llvm/Target/TargetRegisterInfo.h | 42 | ||||
-rw-r--r-- | include/llvm/Target/TargetRegistry.h | 46 | ||||
-rw-r--r-- | include/llvm/Target/TargetSelectionDAGInfo.h | 69 |
10 files changed, 296 insertions, 214 deletions
diff --git a/include/llvm/Target/SubtargetFeature.h b/include/llvm/Target/SubtargetFeature.h index 38a3cc2..4546871 100644 --- a/include/llvm/Target/SubtargetFeature.h +++ b/include/llvm/Target/SubtargetFeature.h @@ -108,9 +108,10 @@ public: // Dump feature info. void dump() const; - /// Retrieve a formatted string of the default features for - /// the specified target triple. - static std::string getDefaultSubtargetFeatures(const Triple &Triple); + /// Retrieve a formatted string of the default features for the specified + /// target triple. + void getDefaultSubtargetFeatures(const std::string &CPU, + const Triple& Triple); }; } // End namespace llvm diff --git a/include/llvm/Target/Target.td b/include/llvm/Target/Target.td index cc19e0d..ca551e5 100644 --- a/include/llvm/Target/Target.td +++ b/include/llvm/Target/Target.td @@ -21,6 +21,11 @@ include "llvm/Intrinsics.td" class RegisterClass; // Forward def +// SubRegIndex - Use instances of SubRegIndex to identify subregisters. +class SubRegIndex { + string Namespace = ""; +} + // Register - You should define one instance of this class for each register // in the target machine. String n will become the "name" of the register. class Register<string n> { @@ -49,6 +54,23 @@ class Register<string n> { // not [AX, AH, AL]. list<Register> SubRegs = []; + // SubRegIndices - For each register in SubRegs, specify the SubRegIndex used + // to address it. Sub-sub-register indices are automatically inherited from + // SubRegs. + list<SubRegIndex> SubRegIndices = []; + + // CompositeIndices - Specify subreg indices that don't correspond directly to + // a register in SubRegs and are not inherited. The following formats are + // supported: + // + // (a) Identity - Reg:a == Reg + // (a b) Alias - Reg:a == Reg:b + // (a b,c) Composite - Reg:a == (Reg:b):c + // + // This can be used to disambiguate a sub-sub-register that exists in more + // than one subregister and other weird stuff. + list<dag> CompositeIndices = []; + // DwarfNumbers - Numbers used internally by gcc/gdb to identify the register. // These values can be determined by locating the <target>.h file in the // directory llvmgcc/gcc/config/<target>/ and looking for REGISTER_NAMES. The @@ -68,17 +90,6 @@ class RegisterWithSubRegs<string n, list<Register> subregs> : Register<n> { let SubRegs = subregs; } -// SubRegSet - This can be used to define a specific mapping of registers to -// indices, for use as named subregs of a particular physical register. Each -// register in 'subregs' becomes an addressable subregister at index 'n' of the -// corresponding register in 'regs'. -class SubRegSet<int n, list<Register> regs, list<Register> subregs> { - int index = n; - - list<Register> From = regs; - list<Register> To = subregs; -} - // RegisterClass - Now that all of the registers are defined, and aliases // between registers are defined, specify which registers belong to which // register classes. This also defines the default allocation order of @@ -117,9 +128,9 @@ class RegisterClass<string namespace, list<ValueType> regTypes, int alignment, // list<Register> MemberList = regList; - // SubClassList - Specify which register classes correspond to subregisters - // of this class. The order should be by subregister set index. - list<RegisterClass> SubRegClassList = []; + // SubRegClasses - Specify the register class of subregisters as a list of + // dags: (RegClass SubRegIndex, SubRegindex, ...) + list<dag> SubRegClasses = []; // MethodProtos/MethodBodies - These members can be used to insert arbitrary // code into a generated register class. The normal usage of this is to @@ -221,6 +232,9 @@ class Instruction { // purposes. bit isCodeGenOnly = 0; + // Is this instruction a pseudo instruction for use by the assembler parser. + bit isAsmParserOnly = 0; + InstrItinClass Itinerary = NoItinerary;// Execution steps used for scheduling. string Constraints = ""; // OperandConstraint, e.g. $src = $dst. @@ -296,8 +310,8 @@ class AsmOperandClass { /// The name to use for this class, which should be usable as an enum value. string Name = ?; - /// The super class of this operand. - AsmOperandClass SuperClass = ?; + /// The super classes of this operand. + list<AsmOperandClass> SuperClasses = []; /// The name of the method on the target specific operand to call to test /// whether the operand is an instance of this class. If not set, this will @@ -331,10 +345,10 @@ class Operand<ValueType ty> { // in. Match classes are used to define the order in which instructions are // match, to ensure that which instructions gets matched is deterministic. // - // The target specific parser must be able to classify an parsed operand - // into a unique class, which does not partially overlap with any other - // classes. It can match a subset of some other class, in which case - // ParserMatchSuperClass should be set to the name of that class. + // The target specific parser must be able to classify an parsed operand into + // a unique class, which does not partially overlap with any other classes. It + // can match a subset of some other class, in which case the AsmOperandClass + // should declare the other operand as one of its super classes. AsmOperandClass ParserMatchClass = ImmAsmOperand; } diff --git a/include/llvm/Target/TargetAsmBackend.h b/include/llvm/Target/TargetAsmBackend.h index f350ecc..979595a 100644 --- a/include/llvm/Target/TargetAsmBackend.h +++ b/include/llvm/Target/TargetAsmBackend.h @@ -13,10 +13,9 @@ #include "llvm/System/DataTypes.h" namespace llvm { -class MCAsmFixup; class MCDataFragment; +class MCFixup; class MCInst; -class MCInstFragment; class MCObjectWriter; class MCSection; template<typename T> @@ -90,6 +89,14 @@ public: return false; } + /// isSectionAtomizable - Check whether the given section can be split into + /// atoms. + /// + /// \see MCAssembler::isSymbolLinkerVisible(). + virtual bool isSectionAtomizable(const MCSection &Section) const { + return true; + } + /// isVirtualSection - Check whether the given section is "virtual", that is /// has no actual object file contents. virtual bool isVirtualSection(const MCSection &Section) const = 0; @@ -97,22 +104,22 @@ public: /// ApplyFixup - Apply the \arg Value for given \arg Fixup into the provided /// data fragment, at the offset specified by the fixup and following the /// fixup kind as appropriate. - virtual void ApplyFixup(const MCAsmFixup &Fixup, MCDataFragment &Fragment, + virtual void ApplyFixup(const MCFixup &Fixup, MCDataFragment &Fragment, uint64_t Value) const = 0; /// MayNeedRelaxation - Check whether the given instruction may need /// relaxation. /// - /// \arg Inst - The instruction to test. - /// \arg Fixups - The actual fixups this instruction encoded to, for potential - /// use by the target backend. - virtual bool MayNeedRelaxation(const MCInst &Inst, - const SmallVectorImpl<MCAsmFixup> &Fixups) const = 0; + /// \param Inst - The instruction to test. + virtual bool MayNeedRelaxation(const MCInst &Inst) const = 0; /// RelaxInstruction - Relax the instruction in the given fragment to the next /// wider instruction. - virtual void RelaxInstruction(const MCInstFragment *IF, - MCInst &Res) const = 0; + /// + /// \param Inst - The instruction to relax, which may be the same as the + /// output. + /// \parm Res [output] - On return, the relaxed instruction. + virtual void RelaxInstruction(const MCInst &Inst, MCInst &Res) const = 0; /// WriteNopData - Write an (optimal) nop sequence of Count bytes to the given /// output. If the target cannot generate such a sequence, it should return an diff --git a/include/llvm/Target/TargetInstrInfo.h b/include/llvm/Target/TargetInstrInfo.h index 143dbcc..2e5697e 100644 --- a/include/llvm/Target/TargetInstrInfo.h +++ b/include/llvm/Target/TargetInstrInfo.h @@ -315,7 +315,8 @@ public: MachineBasicBlock::iterator MI, unsigned DestReg, unsigned SrcReg, const TargetRegisterClass *DestRC, - const TargetRegisterClass *SrcRC) const { + const TargetRegisterClass *SrcRC, + DebugLoc DL) const { assert(0 && "Target didn't implement TargetInstrInfo::copyRegToReg!"); return false; } @@ -328,7 +329,8 @@ public: virtual void storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI, unsigned SrcReg, bool isKill, int FrameIndex, - const TargetRegisterClass *RC) const { + const TargetRegisterClass *RC, + const TargetRegisterInfo *TRI) const { assert(0 && "Target didn't implement TargetInstrInfo::storeRegToStackSlot!"); } @@ -339,7 +341,8 @@ public: virtual void loadRegFromStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI, unsigned DestReg, int FrameIndex, - const TargetRegisterClass *RC) const { + const TargetRegisterClass *RC, + const TargetRegisterInfo *TRI) const { assert(0 && "Target didn't implement TargetInstrInfo::loadRegFromStackSlot!"); } @@ -349,7 +352,8 @@ public: /// storeRegToStackSlot(). Returns false otherwise. virtual bool spillCalleeSavedRegisters(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI, - const std::vector<CalleeSavedInfo> &CSI) const { + const std::vector<CalleeSavedInfo> &CSI, + const TargetRegisterInfo *TRI) const { return false; } @@ -359,7 +363,8 @@ public: /// Returns false otherwise. virtual bool restoreCalleeSavedRegisters(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI, - const std::vector<CalleeSavedInfo> &CSI) const { + const std::vector<CalleeSavedInfo> &CSI, + const TargetRegisterInfo *TRI) const { return false; } diff --git a/include/llvm/Target/TargetLowering.h b/include/llvm/Target/TargetLowering.h index 4ea6c94..5efebe6 100644 --- a/include/llvm/Target/TargetLowering.h +++ b/include/llvm/Target/TargetLowering.h @@ -55,7 +55,6 @@ namespace llvm { class TargetData; class TargetMachine; class TargetRegisterClass; - class TargetSubtarget; class TargetLoweringObjectFile; class Value; @@ -98,11 +97,6 @@ public: ZeroOrNegativeOneBooleanContent // All bits equal to bit 0. }; - enum SchedPreference { - SchedulingForLatency, // Scheduling for shortest total latency. - SchedulingForRegPressure // Scheduling for lowest register pressure. - }; - /// NOTE: The constructor takes ownership of TLOF. explicit TargetLowering(const TargetMachine &TM, const TargetLoweringObjectFile *TLOF); @@ -151,13 +145,20 @@ public: BooleanContent getBooleanContents() const { return BooleanContents;} /// getSchedulingPreference - Return target scheduling preference. - SchedPreference getSchedulingPreference() const { + Sched::Preference getSchedulingPreference() const { return SchedPreferenceInfo; } + /// getSchedulingPreference - Some scheduler, e.g. hybrid, can switch to + /// different scheduling heuristics for different nodes. This function returns + /// the preference (or none) for the given node. + virtual Sched::Preference getSchedulingPreference(SDNode *N) const { + return Sched::None; + } + /// getRegClassFor - Return the register class that should be used for the - /// specified value type. This may only be called on legal types. - TargetRegisterClass *getRegClassFor(EVT VT) const { + /// specified value type. + virtual TargetRegisterClass *getRegClassFor(EVT VT) const { assert(VT.isSimple() && "getRegClassFor called on illegal type!"); TargetRegisterClass *RC = RegClassForVT[VT.getSimpleVT().SimpleTy]; assert(RC && "This value type is not natively supported!"); @@ -181,11 +182,9 @@ public: } class ValueTypeActionImpl { - /// ValueTypeActions - This is a bitvector that contains two bits for each - /// value type, where the two bits correspond to the LegalizeAction enum. - /// This can be queried with "getTypeAction(VT)". - /// dimension by (MVT::MAX_ALLOWED_VALUETYPE/32) * 2 - uint32_t ValueTypeActions[(MVT::MAX_ALLOWED_VALUETYPE/32)*2]; + /// ValueTypeActions - For each value type, keep a LegalizeAction enum + /// that indicates how instruction selection should deal with the type. + uint8_t ValueTypeActions[MVT::LAST_VALUETYPE]; public: ValueTypeActionImpl() { std::fill(ValueTypeActions, array_endof(ValueTypeActions), 0); @@ -202,13 +201,11 @@ public: return Legal; } unsigned I = VT.getSimpleVT().SimpleTy; - assert(I<4*array_lengthof(ValueTypeActions)*sizeof(ValueTypeActions[0])); - return (LegalizeAction)((ValueTypeActions[I>>4] >> ((2*I) & 31)) & 3); + return (LegalizeAction)ValueTypeActions[I]; } void setTypeAction(EVT VT, LegalizeAction Action) { unsigned I = VT.getSimpleVT().SimpleTy; - assert(I<4*array_lengthof(ValueTypeActions)*sizeof(ValueTypeActions[0])); - ValueTypeActions[I>>4] |= Action << ((I*2) & 31); + ValueTypeActions[I] = Action; } }; @@ -357,13 +354,9 @@ public: /// for it. LegalizeAction getOperationAction(unsigned Op, EVT VT) const { if (VT.isExtended()) return Expand; - assert(Op < array_lengthof(OpActions[0]) && - (unsigned)VT.getSimpleVT().SimpleTy < sizeof(OpActions[0][0])*8 && - "Table isn't big enough!"); + assert(Op < array_lengthof(OpActions[0]) && "Table isn't big enough!"); unsigned I = (unsigned) VT.getSimpleVT().SimpleTy; - unsigned J = I & 31; - I = I >> 5; - return (LegalizeAction)((OpActions[I][Op] >> (J*2) ) & 3); + return (LegalizeAction)OpActions[I][Op]; } /// isOperationLegalOrCustom - Return true if the specified operation is @@ -386,35 +379,31 @@ public: /// either it is legal, needs to be promoted to a larger size, needs to be /// expanded to some other code sequence, or the target has a custom expander /// for it. - LegalizeAction getLoadExtAction(unsigned LType, EVT VT) const { - assert(LType < array_lengthof(LoadExtActions) && - (unsigned)VT.getSimpleVT().SimpleTy < sizeof(LoadExtActions[0])*4 && + LegalizeAction getLoadExtAction(unsigned ExtType, EVT VT) const { + assert(ExtType < ISD::LAST_LOADEXT_TYPE && + (unsigned)VT.getSimpleVT().SimpleTy < MVT::LAST_VALUETYPE && "Table isn't big enough!"); - return (LegalizeAction)((LoadExtActions[LType] >> - (2*VT.getSimpleVT().SimpleTy)) & 3); + return (LegalizeAction)LoadExtActions[VT.getSimpleVT().SimpleTy][ExtType]; } /// isLoadExtLegal - Return true if the specified load with extension is legal /// on this target. - bool isLoadExtLegal(unsigned LType, EVT VT) const { + bool isLoadExtLegal(unsigned ExtType, EVT VT) const { return VT.isSimple() && - (getLoadExtAction(LType, VT) == Legal || - getLoadExtAction(LType, VT) == Custom); + (getLoadExtAction(ExtType, VT) == Legal || + getLoadExtAction(ExtType, VT) == Custom); } /// getTruncStoreAction - Return how this store with truncation should be /// treated: either it is legal, needs to be promoted to a larger size, needs /// to be expanded to some other code sequence, or the target has a custom /// expander for it. - LegalizeAction getTruncStoreAction(EVT ValVT, - EVT MemVT) const { - assert((unsigned)ValVT.getSimpleVT().SimpleTy < - array_lengthof(TruncStoreActions) && - (unsigned)MemVT.getSimpleVT().SimpleTy < - sizeof(TruncStoreActions[0])*4 && + LegalizeAction getTruncStoreAction(EVT ValVT, EVT MemVT) const { + assert((unsigned)ValVT.getSimpleVT().SimpleTy < MVT::LAST_VALUETYPE && + (unsigned)MemVT.getSimpleVT().SimpleTy < MVT::LAST_VALUETYPE && "Table isn't big enough!"); - return (LegalizeAction)((TruncStoreActions[ValVT.getSimpleVT().SimpleTy] >> - (2*MemVT.getSimpleVT().SimpleTy)) & 3); + return (LegalizeAction)TruncStoreActions[ValVT.getSimpleVT().SimpleTy] + [MemVT.getSimpleVT().SimpleTy]; } /// isTruncStoreLegal - Return true if the specified store with truncation is @@ -431,11 +420,11 @@ public: /// for it. LegalizeAction getIndexedLoadAction(unsigned IdxMode, EVT VT) const { - assert( IdxMode < array_lengthof(IndexedModeActions[0][0]) && + assert( IdxMode < ISD::LAST_INDEXED_MODE && ((unsigned)VT.getSimpleVT().SimpleTy) < MVT::LAST_VALUETYPE && "Table isn't big enough!"); - return (LegalizeAction)((IndexedModeActions[ - (unsigned)VT.getSimpleVT().SimpleTy][0][IdxMode])); + unsigned Ty = (unsigned)VT.getSimpleVT().SimpleTy; + return (LegalizeAction)((IndexedModeActions[Ty][IdxMode] & 0xf0) >> 4); } /// isIndexedLoadLegal - Return true if the specified indexed load is legal @@ -452,11 +441,11 @@ public: /// for it. LegalizeAction getIndexedStoreAction(unsigned IdxMode, EVT VT) const { - assert(IdxMode < array_lengthof(IndexedModeActions[0][1]) && - (unsigned)VT.getSimpleVT().SimpleTy < MVT::LAST_VALUETYPE && + assert( IdxMode < ISD::LAST_INDEXED_MODE && + ((unsigned)VT.getSimpleVT().SimpleTy) < MVT::LAST_VALUETYPE && "Table isn't big enough!"); - return (LegalizeAction)((IndexedModeActions[ - (unsigned)VT.getSimpleVT().SimpleTy][1][IdxMode])); + unsigned Ty = (unsigned)VT.getSimpleVT().SimpleTy; + return (LegalizeAction)(IndexedModeActions[Ty][IdxMode] & 0x0f); } /// isIndexedStoreLegal - Return true if the specified indexed load is legal @@ -919,7 +908,7 @@ protected: void setBooleanContents(BooleanContent Ty) { BooleanContents = Ty; } /// setSchedulingPreference - Specify the target scheduling preference. - void setSchedulingPreference(SchedPreference Pref) { + void setSchedulingPreference(Sched::Preference Pref) { SchedPreferenceInfo = Pref; } @@ -991,33 +980,28 @@ protected: /// with the specified type and indicate what to do about it. void setOperationAction(unsigned Op, MVT VT, LegalizeAction Action) { - unsigned I = (unsigned)VT.SimpleTy; - unsigned J = I & 31; - I = I >> 5; - OpActions[I][Op] &= ~(uint64_t(3UL) << (J*2)); - OpActions[I][Op] |= (uint64_t)Action << (J*2); + assert(Op < array_lengthof(OpActions[0]) && "Table isn't big enough!"); + OpActions[(unsigned)VT.SimpleTy][Op] = (uint8_t)Action; } /// setLoadExtAction - Indicate that the specified load with extension does /// not work with the specified type and indicate what to do about it. void setLoadExtAction(unsigned ExtType, MVT VT, - LegalizeAction Action) { - assert((unsigned)VT.SimpleTy*2 < 63 && - ExtType < array_lengthof(LoadExtActions) && + LegalizeAction Action) { + assert(ExtType < ISD::LAST_LOADEXT_TYPE && + (unsigned)VT.SimpleTy < MVT::LAST_VALUETYPE && "Table isn't big enough!"); - LoadExtActions[ExtType] &= ~(uint64_t(3UL) << VT.SimpleTy*2); - LoadExtActions[ExtType] |= (uint64_t)Action << VT.SimpleTy*2; + LoadExtActions[VT.SimpleTy][ExtType] = (uint8_t)Action; } /// setTruncStoreAction - Indicate that the specified truncating store does /// not work with the specified type and indicate what to do about it. void setTruncStoreAction(MVT ValVT, MVT MemVT, LegalizeAction Action) { - assert((unsigned)ValVT.SimpleTy < array_lengthof(TruncStoreActions) && - (unsigned)MemVT.SimpleTy*2 < 63 && + assert((unsigned)ValVT.SimpleTy < MVT::LAST_VALUETYPE && + (unsigned)MemVT.SimpleTy < MVT::LAST_VALUETYPE && "Table isn't big enough!"); - TruncStoreActions[ValVT.SimpleTy] &= ~(uint64_t(3UL) << MemVT.SimpleTy*2); - TruncStoreActions[ValVT.SimpleTy] |= (uint64_t)Action << MemVT.SimpleTy*2; + TruncStoreActions[ValVT.SimpleTy][MemVT.SimpleTy] = (uint8_t)Action; } /// setIndexedLoadAction - Indicate that the specified indexed load does or @@ -1027,9 +1011,12 @@ protected: void setIndexedLoadAction(unsigned IdxMode, MVT VT, LegalizeAction Action) { assert((unsigned)VT.SimpleTy < MVT::LAST_VALUETYPE && - IdxMode < array_lengthof(IndexedModeActions[0][0]) && + IdxMode < ISD::LAST_INDEXED_MODE && + (unsigned)Action < 0xf && "Table isn't big enough!"); - IndexedModeActions[(unsigned)VT.SimpleTy][0][IdxMode] = (uint8_t)Action; + // Load action are kept in the upper half. + IndexedModeActions[(unsigned)VT.SimpleTy][IdxMode] &= ~0xf0; + IndexedModeActions[(unsigned)VT.SimpleTy][IdxMode] |= ((uint8_t)Action) <<4; } /// setIndexedStoreAction - Indicate that the specified indexed store does or @@ -1039,9 +1026,12 @@ protected: void setIndexedStoreAction(unsigned IdxMode, MVT VT, LegalizeAction Action) { assert((unsigned)VT.SimpleTy < MVT::LAST_VALUETYPE && - IdxMode < array_lengthof(IndexedModeActions[0][1] ) && + IdxMode < ISD::LAST_INDEXED_MODE && + (unsigned)Action < 0xf && "Table isn't big enough!"); - IndexedModeActions[(unsigned)VT.SimpleTy][1][IdxMode] = (uint8_t)Action; + // Store action are kept in the lower half. + IndexedModeActions[(unsigned)VT.SimpleTy][IdxMode] &= ~0x0f; + IndexedModeActions[(unsigned)VT.SimpleTy][IdxMode] |= ((uint8_t)Action); } /// setCondCodeAction - Indicate that the specified condition code is or isn't @@ -1103,12 +1093,6 @@ protected: } public: - - virtual const TargetSubtarget *getSubtarget() const { - assert(0 && "Not Implemented"); - return NULL; // this is here to silence compiler errors - } - //===--------------------------------------------------------------------===// // Lowering methods - These methods must be implemented by targets so that // the SelectionDAGLowering code knows how to lower these. @@ -1200,61 +1184,6 @@ public: return SDValue(); // this is here to silence compiler errors } - /// EmitTargetCodeForMemcpy - Emit target-specific code that performs a - /// memcpy. This can be used by targets to provide code sequences for cases - /// that don't fit the target's parameters for simple loads/stores and can be - /// more efficient than using a library call. This function can return a null - /// SDValue if the target declines to use custom code and a different - /// lowering strategy should be used. - /// - /// If AlwaysInline is true, the size is constant and the target should not - /// emit any calls and is strongly encouraged to attempt to emit inline code - /// even if it is beyond the usual threshold because this intrinsic is being - /// expanded in a place where calls are not feasible (e.g. within the prologue - /// for another call). If the target chooses to decline an AlwaysInline - /// request here, legalize will resort to using simple loads and stores. - virtual SDValue - EmitTargetCodeForMemcpy(SelectionDAG &DAG, DebugLoc dl, - SDValue Chain, - SDValue Op1, SDValue Op2, - SDValue Op3, unsigned Align, bool isVolatile, - bool AlwaysInline, - const Value *DstSV, uint64_t DstOff, - const Value *SrcSV, uint64_t SrcOff) const { - return SDValue(); - } - - /// EmitTargetCodeForMemmove - Emit target-specific code that performs a - /// memmove. This can be used by targets to provide code sequences for cases - /// that don't fit the target's parameters for simple loads/stores and can be - /// more efficient than using a library call. This function can return a null - /// SDValue if the target declines to use custom code and a different - /// lowering strategy should be used. - virtual SDValue - EmitTargetCodeForMemmove(SelectionDAG &DAG, DebugLoc dl, - SDValue Chain, - SDValue Op1, SDValue Op2, - SDValue Op3, unsigned Align, bool isVolatile, - const Value *DstSV, uint64_t DstOff, - const Value *SrcSV, uint64_t SrcOff) const { - return SDValue(); - } - - /// EmitTargetCodeForMemset - Emit target-specific code that performs a - /// memset. This can be used by targets to provide code sequences for cases - /// that don't fit the target's parameters for simple stores and can be more - /// efficient than using a library call. This function can return a null - /// SDValue if the target declines to use custom code and a different - /// lowering strategy should be used. - virtual SDValue - EmitTargetCodeForMemset(SelectionDAG &DAG, DebugLoc dl, - SDValue Chain, - SDValue Op1, SDValue Op2, - SDValue Op3, unsigned Align, bool isVolatile, - const Value *DstSV, uint64_t DstOff) const { - return SDValue(); - } - /// LowerOperationWrapper - This callback is invoked by the type legalizer /// to legalize nodes with an illegal operand type but legal result types. /// It replaces the LowerOperation callback in the type Legalizer. @@ -1594,7 +1523,7 @@ private: /// SchedPreferenceInfo - The target scheduling preference: shortest possible /// total cycles or lowest register usage. - SchedPreference SchedPreferenceInfo; + Sched::Preference SchedPreferenceInfo; /// JumpBufSize - The size, in bytes, of the target's jmp_buf buffers unsigned JumpBufSize; @@ -1653,26 +1582,24 @@ private: /// Most operations are Legal (aka, supported natively by the target), but /// operations that are not should be described. Note that operations on /// non-legal value types are not described here. - /// This array is accessed using VT.getSimpleVT(), so it is subject to - /// the MVT::MAX_ALLOWED_VALUETYPE * 2 bits. - uint64_t OpActions[MVT::MAX_ALLOWED_VALUETYPE/(sizeof(uint64_t)*4)][ISD::BUILTIN_OP_END]; + uint8_t OpActions[MVT::LAST_VALUETYPE][ISD::BUILTIN_OP_END]; - /// LoadExtActions - For each load of load extension type and each value type, + /// LoadExtActions - For each load extension type and each value type, /// keep a LegalizeAction that indicates how instruction selection should deal - /// with the load. - uint64_t LoadExtActions[ISD::LAST_LOADEXT_TYPE]; + /// with a load of a specific value type and extension type. + uint8_t LoadExtActions[MVT::LAST_VALUETYPE][ISD::LAST_LOADEXT_TYPE]; - /// TruncStoreActions - For each truncating store, keep a LegalizeAction that - /// indicates how instruction selection should deal with the store. - uint64_t TruncStoreActions[MVT::LAST_VALUETYPE]; + /// TruncStoreActions - For each value type pair keep a LegalizeAction that + /// indicates whether a truncating store of a specific value type and + /// truncating type is legal. + uint8_t TruncStoreActions[MVT::LAST_VALUETYPE][MVT::LAST_VALUETYPE]; /// IndexedModeActions - For each indexed mode and each value type, /// keep a pair of LegalizeAction that indicates how instruction - /// selection should deal with the load / store. The first - /// dimension is now the value_type for the reference. The second - /// dimension is the load [0] vs. store[1]. The third dimension - /// represents the various modes for load store. - uint8_t IndexedModeActions[MVT::LAST_VALUETYPE][2][ISD::LAST_INDEXED_MODE]; + /// selection should deal with the load / store. The first dimension is the + /// value_type for the reference. The second dimension represents the various + /// modes for load store. + uint8_t IndexedModeActions[MVT::LAST_VALUETYPE][ISD::LAST_INDEXED_MODE]; /// CondCodeActions - For each condition code (ISD::CondCode) keep a /// LegalizeAction that indicates how instruction selection should diff --git a/include/llvm/Target/TargetLoweringObjectFile.h b/include/llvm/Target/TargetLoweringObjectFile.h index 6c99598..819709f 100644 --- a/include/llvm/Target/TargetLoweringObjectFile.h +++ b/include/llvm/Target/TargetLoweringObjectFile.h @@ -88,6 +88,10 @@ protected: const MCSection *DwarfRangesSection; const MCSection *DwarfMacroInfoSection; + // Extra TLS Variable Data section. If the target needs to put additional + // information for a TLS variable, it'll go here. + const MCSection *TLSExtraDataSection; + /// SupportsWeakEmptyEHFrame - True if target object file supports a /// weak_definition of constant 0 for an omitted EH frame. bool SupportsWeakOmittedEHFrame; @@ -147,6 +151,9 @@ public: const MCSection *getDwarfMacroInfoSection() const { return DwarfMacroInfoSection; } + const MCSection *getTLSExtraDataSection() const { + return TLSExtraDataSection; + } /// shouldEmitUsedDirectiveFor - This hook allows targets to selectively /// decide not to emit the UsedDirective for some symbols in llvm.used. diff --git a/include/llvm/Target/TargetMachine.h b/include/llvm/Target/TargetMachine.h index c734cf4..227499b 100644 --- a/include/llvm/Target/TargetMachine.h +++ b/include/llvm/Target/TargetMachine.h @@ -70,6 +70,15 @@ namespace CodeGenOpt { }; } +namespace Sched { + enum Preference { + None, // No preference + Latency, // Scheduling for shortest total latency. + RegPressure, // Scheduling for lowest register pressure. + Hybrid // Scheduling for both latency and register pressure. + }; +} + //===----------------------------------------------------------------------===// /// /// TargetMachine - Primary interface to the complete machine description for @@ -92,7 +101,9 @@ protected: // Can only create subclasses. /// AsmInfo - Contains target specific asm information. /// const MCAsmInfo *AsmInfo; - + + unsigned MCRelaxAll : 1; + public: virtual ~TargetMachine(); @@ -149,6 +160,14 @@ public: /// virtual const TargetELFWriterInfo *getELFWriterInfo() const { return 0; } + /// hasMCRelaxAll - Check whether all machine code instructions should be + /// relaxed. + bool hasMCRelaxAll() const { return MCRelaxAll; } + + /// setMCRelaxAll - Set whether all machine code instructions should be + /// relaxed. + void setMCRelaxAll(bool Value) { MCRelaxAll = Value; } + /// getRelocationModel - Returns the code generation relocation model. The /// choices are static, PIC, and dynamic-no-pic, and target default. static Reloc::Model getRelocationModel(); @@ -225,17 +244,6 @@ public: bool = true) { return true; } - - /// addPassesToEmitWholeFile - This method can be implemented by targets that - /// require having the entire module at once. This is not recommended, do not - /// use this. - virtual bool WantsWholeFile() const { return false; } - virtual bool addPassesToEmitWholeFile(PassManager &, formatted_raw_ostream &, - CodeGenFileType, - CodeGenOpt::Level, - bool = true) { - return true; - } }; /// LLVMTargetMachine - This class describes a target machine that is diff --git a/include/llvm/Target/TargetRegisterInfo.h b/include/llvm/Target/TargetRegisterInfo.h index 29b862a..7c37b73 100644 --- a/include/llvm/Target/TargetRegisterInfo.h +++ b/include/llvm/Target/TargetRegisterInfo.h @@ -28,6 +28,7 @@ class BitVector; class MachineFunction; class MachineMove; class RegScavenger; +template<class T> class SmallVectorImpl; /// TargetRegisterDesc - This record contains all of the information known about /// a particular register. The AliasSet field (if not null) contains a pointer @@ -151,9 +152,6 @@ public: /// index SubIdx, or NULL if no such class exists. const TargetRegisterClass* getSubRegisterRegClass(unsigned SubIdx) const { assert(SubIdx>0 && "Invalid subregister index"); - for (unsigned s = 0; s != SubIdx-1; ++s) - if (!SubRegClasses[s]) - return NULL; return SubRegClasses[SubIdx-1]; } @@ -262,14 +260,13 @@ class TargetRegisterInfo { protected: const unsigned* SubregHash; const unsigned SubregHashSize; - const unsigned* SuperregHash; - const unsigned SuperregHashSize; const unsigned* AliasesHash; const unsigned AliasesHashSize; public: typedef const TargetRegisterClass * const * regclass_iterator; private: const TargetRegisterDesc *Desc; // Pointer to the descriptor array + const char *const *SubRegIndexNames; // Names of subreg indexes. unsigned NumRegs; // Number of entries in the array regclass_iterator RegClassBegin, RegClassEnd; // List of regclasses @@ -280,12 +277,11 @@ protected: TargetRegisterInfo(const TargetRegisterDesc *D, unsigned NR, regclass_iterator RegClassBegin, regclass_iterator RegClassEnd, + const char *const *subregindexnames, int CallFrameSetupOpcode = -1, int CallFrameDestroyOpcode = -1, const unsigned* subregs = 0, const unsigned subregsize = 0, - const unsigned* superregs = 0, - const unsigned superregsize = 0, const unsigned* aliases = 0, const unsigned aliasessize = 0); virtual ~TargetRegisterInfo(); @@ -380,6 +376,13 @@ public: return NumRegs; } + /// getSubRegIndexName - Return the human-readable symbolic target-specific + /// name for the specified SubRegIndex. + const char *getSubRegIndexName(unsigned SubIdx) const { + assert(SubIdx && "This is not a subregister index"); + return SubRegIndexNames[SubIdx-1]; + } + /// regsOverlap - Returns true if the two registers are equal or alias each /// other. The registers may be virtual register. bool regsOverlap(unsigned regA, unsigned regB) const { @@ -425,19 +428,7 @@ public: /// isSuperRegister - Returns true if regB is a super-register of regA. /// bool isSuperRegister(unsigned regA, unsigned regB) const { - // SuperregHash is a simple quadratically probed hash table. - size_t index = (regA + regB * 37) & (SuperregHashSize-1); - unsigned ProbeAmt = 2; - while (SuperregHash[index*2] != 0 && - SuperregHash[index*2+1] != 0) { - if (SuperregHash[index*2] == regA && SuperregHash[index*2+1] == regB) - return true; - - index = (index + ProbeAmt) & (SuperregHashSize-1); - ProbeAmt += 2; - } - - return false; + return isSubRegister(regB, regA); } /// getCalleeSavedRegs - Return a null-terminated list of all of the @@ -479,6 +470,17 @@ public: return 0; } + /// canCombinedSubRegIndex - Given a register class and a list of sub-register + /// indices, return true if it's possible to combine the sub-register indices + /// into one that corresponds to a larger sub-register. Return the new sub- + /// register index by reference. Note the new index by be zero if the given + /// sub-registers combined to form the whole register. + virtual bool canCombinedSubRegIndex(const TargetRegisterClass *RC, + SmallVectorImpl<unsigned> &SubIndices, + unsigned &NewSubIdx) const { + return 0; + } + /// getMatchingSuperRegClass - Return a subclass of the specified register /// class A so that each register in it has a sub-register of the /// specified sub-register index which is in the specified register class B. diff --git a/include/llvm/Target/TargetRegistry.h b/include/llvm/Target/TargetRegistry.h index 36bbe00..1418bee 100644 --- a/include/llvm/Target/TargetRegistry.h +++ b/include/llvm/Target/TargetRegistry.h @@ -73,6 +73,13 @@ namespace llvm { typedef MCCodeEmitter *(*CodeEmitterCtorTy)(const Target &T, TargetMachine &TM, MCContext &Ctx); + typedef MCStreamer *(*ObjectStreamerCtorTy)(const Target &T, + const std::string &TT, + MCContext &Ctx, + TargetAsmBackend &TAB, + raw_ostream &_OS, + MCCodeEmitter *_Emitter, + bool RelaxAll); private: /// Next - The next registered target in the linked list, maintained by the @@ -126,6 +133,10 @@ namespace llvm { /// if registered. CodeEmitterCtorTy CodeEmitterCtorFn; + /// ObjectStreamerCtorFn - Construction function for this target's + /// ObjectStreamer, if registered. + ObjectStreamerCtorTy ObjectStreamerCtorFn; + public: /// @name Target Information /// @{ @@ -170,6 +181,9 @@ namespace llvm { /// hasCodeEmitter - Check if this target supports instruction encoding. bool hasCodeEmitter() const { return CodeEmitterCtorFn != 0; } + /// hasObjectStreamer - Check if this target supports streaming to files. + bool hasObjectStreamer() const { return ObjectStreamerCtorFn != 0; } + /// @} /// @name Feature Constructors /// @{ @@ -258,6 +272,24 @@ namespace llvm { return CodeEmitterCtorFn(*this, TM, Ctx); } + /// createObjectStreamer - Create a target specific MCStreamer. + /// + /// \arg TT - The target triple. + /// \arg Ctx - The target context. + /// \arg TAB - The target assembler backend object. + /// \arg _OS - The stream object. + /// \arg _Emitter - The target independent assembler object. + /// \arg RelaxAll - Relax all fixups? + MCStreamer *createObjectStreamer(const std::string &TT, MCContext &Ctx, + TargetAsmBackend &TAB, + raw_ostream &_OS, + MCCodeEmitter *_Emitter, + bool RelaxAll) const { + if (!ObjectStreamerCtorFn) + return 0; + return ObjectStreamerCtorFn(*this, TT, Ctx, TAB, _OS, _Emitter, RelaxAll); + } + /// @} }; @@ -479,6 +511,20 @@ namespace llvm { T.CodeEmitterCtorFn = Fn; } + /// RegisterObjectStreamer - Register an MCStreamer implementation + /// for the given target. + /// + /// Clients are responsible for ensuring that registration doesn't occur + /// while another thread is attempting to access the registry. Typically + /// this is done by initializing all targets at program startup. + /// + /// @param T - The target being registered. + /// @param Fn - A function to construct an MCStreamer for the target. + static void RegisterObjectStreamer(Target &T, Target::ObjectStreamerCtorTy Fn) { + if (!T.ObjectStreamerCtorFn) + T.ObjectStreamerCtorFn = Fn; + } + /// @} }; diff --git a/include/llvm/Target/TargetSelectionDAGInfo.h b/include/llvm/Target/TargetSelectionDAGInfo.h index 943bdea..2be1834 100644 --- a/include/llvm/Target/TargetSelectionDAGInfo.h +++ b/include/llvm/Target/TargetSelectionDAGInfo.h @@ -16,19 +16,84 @@ #ifndef LLVM_TARGET_TARGETSELECTIONDAGINFO_H #define LLVM_TARGET_TARGETSELECTIONDAGINFO_H +#include "llvm/CodeGen/SelectionDAGNodes.h" + namespace llvm { +class TargetData; +class TargetMachine; + //===----------------------------------------------------------------------===// -/// TargetSelectionDAGLowering - Targets can subclass this to parameterize the +/// TargetSelectionDAGInfo - Targets can subclass this to parameterize the /// SelectionDAG lowering and instruction selection process. /// class TargetSelectionDAGInfo { TargetSelectionDAGInfo(const TargetSelectionDAGInfo &); // DO NOT IMPLEMENT void operator=(const TargetSelectionDAGInfo &); // DO NOT IMPLEMENT + const TargetData *TD; + +protected: + const TargetData *getTargetData() const { return TD; } + public: - TargetSelectionDAGInfo(); + explicit TargetSelectionDAGInfo(const TargetMachine &TM); virtual ~TargetSelectionDAGInfo(); + + /// EmitTargetCodeForMemcpy - Emit target-specific code that performs a + /// memcpy. This can be used by targets to provide code sequences for cases + /// that don't fit the target's parameters for simple loads/stores and can be + /// more efficient than using a library call. This function can return a null + /// SDValue if the target declines to use custom code and a different + /// lowering strategy should be used. + /// + /// If AlwaysInline is true, the size is constant and the target should not + /// emit any calls and is strongly encouraged to attempt to emit inline code + /// even if it is beyond the usual threshold because this intrinsic is being + /// expanded in a place where calls are not feasible (e.g. within the prologue + /// for another call). If the target chooses to decline an AlwaysInline + /// request here, legalize will resort to using simple loads and stores. + virtual SDValue + EmitTargetCodeForMemcpy(SelectionDAG &DAG, DebugLoc dl, + SDValue Chain, + SDValue Op1, SDValue Op2, + SDValue Op3, unsigned Align, bool isVolatile, + bool AlwaysInline, + const Value *DstSV, uint64_t DstOff, + const Value *SrcSV, uint64_t SrcOff) const { + return SDValue(); + } + + /// EmitTargetCodeForMemmove - Emit target-specific code that performs a + /// memmove. This can be used by targets to provide code sequences for cases + /// that don't fit the target's parameters for simple loads/stores and can be + /// more efficient than using a library call. This function can return a null + /// SDValue if the target declines to use custom code and a different + /// lowering strategy should be used. + virtual SDValue + EmitTargetCodeForMemmove(SelectionDAG &DAG, DebugLoc dl, + SDValue Chain, + SDValue Op1, SDValue Op2, + SDValue Op3, unsigned Align, bool isVolatile, + const Value *DstSV, uint64_t DstOff, + const Value *SrcSV, uint64_t SrcOff) const { + return SDValue(); + } + + /// EmitTargetCodeForMemset - Emit target-specific code that performs a + /// memset. This can be used by targets to provide code sequences for cases + /// that don't fit the target's parameters for simple stores and can be more + /// efficient than using a library call. This function can return a null + /// SDValue if the target declines to use custom code and a different + /// lowering strategy should be used. + virtual SDValue + EmitTargetCodeForMemset(SelectionDAG &DAG, DebugLoc dl, + SDValue Chain, + SDValue Op1, SDValue Op2, + SDValue Op3, unsigned Align, bool isVolatile, + const Value *DstSV, uint64_t DstOff) const { + return SDValue(); + } }; } // end llvm namespace |