summaryrefslogtreecommitdiffstats
path: root/include/llvm/MC
diff options
context:
space:
mode:
Diffstat (limited to 'include/llvm/MC')
-rw-r--r--include/llvm/MC/MCAsmBackend.h49
-rw-r--r--include/llvm/MC/MCAsmInfo.h44
-rw-r--r--include/llvm/MC/MCAsmInfoCOFF.h14
-rw-r--r--include/llvm/MC/MCAsmInfoDarwin.h4
-rw-r--r--include/llvm/MC/MCAsmLayout.h1
-rw-r--r--include/llvm/MC/MCAssembler.h47
-rw-r--r--include/llvm/MC/MCCodeEmitter.h6
-rw-r--r--include/llvm/MC/MCCodeGenInfo.h11
-rw-r--r--include/llvm/MC/MCContext.h62
-rw-r--r--include/llvm/MC/MCDisassembler.h2
-rw-r--r--include/llvm/MC/MCDwarf.h67
-rw-r--r--include/llvm/MC/MCELFObjectWriter.h75
-rw-r--r--include/llvm/MC/MCExpr.h28
-rw-r--r--include/llvm/MC/MCFixup.h19
-rw-r--r--include/llvm/MC/MCInst.h28
-rw-r--r--include/llvm/MC/MCInstPrinter.h11
-rw-r--r--include/llvm/MC/MCInstrAnalysis.h2
-rw-r--r--include/llvm/MC/MCInstrDesc.h208
-rw-r--r--include/llvm/MC/MCInstrInfo.h17
-rw-r--r--include/llvm/MC/MCObjectFileInfo.h44
-rw-r--r--include/llvm/MC/MCObjectStreamer.h7
-rw-r--r--include/llvm/MC/MCObjectWriter.h8
-rw-r--r--include/llvm/MC/MCParser/MCAsmLexer.h1
-rw-r--r--include/llvm/MC/MCParser/MCAsmParser.h14
-rw-r--r--include/llvm/MC/MCRegisterInfo.h184
-rw-r--r--include/llvm/MC/MCSection.h2
-rw-r--r--include/llvm/MC/MCSectionCOFF.h2
-rw-r--r--include/llvm/MC/MCSectionELF.h1
-rw-r--r--include/llvm/MC/MCSectionMachO.h1
-rw-r--r--include/llvm/MC/MCStreamer.h49
-rw-r--r--include/llvm/MC/MCWinCOFFObjectWriter.h36
31 files changed, 740 insertions, 304 deletions
diff --git a/include/llvm/MC/MCAsmBackend.h b/include/llvm/MC/MCAsmBackend.h
index 4a0cf37..05e6286 100644
--- a/include/llvm/MC/MCAsmBackend.h
+++ b/include/llvm/MC/MCAsmBackend.h
@@ -12,17 +12,20 @@
#include "llvm/MC/MCDirectives.h"
#include "llvm/MC/MCFixup.h"
-#include "llvm/MC/MCFixupKindInfo.h"
#include "llvm/Support/DataTypes.h"
+#include "llvm/Support/ErrorHandling.h"
namespace llvm {
+class MCAsmLayout;
+class MCAssembler;
class MCELFObjectTargetWriter;
-class MCFixup;
+struct MCFixupKindInfo;
+class MCFragment;
class MCInst;
+class MCInstFragment;
class MCObjectWriter;
class MCSection;
-template<typename T>
-class SmallVectorImpl;
+class MCValue;
class raw_ostream;
/// MCAsmBackend - Generic interface to target specific assembler backends.
@@ -44,8 +47,8 @@ public:
/// createELFObjectTargetWriter - Create a new ELFObjectTargetWriter to enable
/// non-standard ELFObjectWriters.
virtual MCELFObjectTargetWriter *createELFObjectTargetWriter() const {
- assert(0 && "createELFObjectTargetWriter is not supported by asm backend");
- return 0;
+ llvm_unreachable("createELFObjectTargetWriter is not supported by asm "
+ "backend");
}
/// hasReliableSymbolDifference - Check whether this target implements
@@ -85,12 +88,21 @@ public:
/// getFixupKindInfo - Get information on a fixup kind.
virtual const MCFixupKindInfo &getFixupKindInfo(MCFixupKind Kind) const;
+ /// processFixupValue - Target hook to adjust the literal value of a fixup
+ /// if necessary. IsResolved signals whether the caller believes a relocation
+ /// is needed; the target can modify the value. The default does nothing.
+ virtual void processFixupValue(const MCAssembler &Asm,
+ const MCAsmLayout &Layout,
+ const MCFixup &Fixup, const MCFragment *DF,
+ MCValue &Target, uint64_t &Value,
+ bool &IsResolved) {}
+
/// @}
- /// ApplyFixup - Apply the \arg Value for given \arg Fixup into the provided
+ /// 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 MCFixup &Fixup, char *Data, unsigned DataSize,
+ virtual void applyFixup(const MCFixup &Fixup, char *Data, unsigned DataSize,
uint64_t Value) const = 0;
/// @}
@@ -98,11 +110,18 @@ public:
/// @name Target Relaxation Interfaces
/// @{
- /// MayNeedRelaxation - Check whether the given instruction may need
+ /// mayNeedRelaxation - Check whether the given instruction may need
/// relaxation.
///
/// \param Inst - The instruction to test.
- virtual bool MayNeedRelaxation(const MCInst &Inst) const = 0;
+ virtual bool mayNeedRelaxation(const MCInst &Inst) const = 0;
+
+ /// fixupNeedsRelaxation - Target specific predicate for whether a given
+ /// fixup requires the associated instruction to be relaxed.
+ virtual bool fixupNeedsRelaxation(const MCFixup &Fixup,
+ uint64_t Value,
+ const MCInstFragment *DF,
+ const MCAsmLayout &Layout) const = 0;
/// RelaxInstruction - Relax the instruction in the given fragment to the next
/// wider instruction.
@@ -110,20 +129,20 @@ public:
/// \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;
+ virtual void relaxInstruction(const MCInst &Inst, MCInst &Res) const = 0;
/// @}
- /// WriteNopData - Write an (optimal) nop sequence of Count bytes to the given
+ /// 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
/// error.
///
/// \return - True on success.
- virtual bool WriteNopData(uint64_t Count, MCObjectWriter *OW) const = 0;
+ virtual bool writeNopData(uint64_t Count, MCObjectWriter *OW) const = 0;
- /// HandleAssemblerFlag - Handle any target-specific assembler flags.
+ /// handleAssemblerFlag - Handle any target-specific assembler flags.
/// By default, do nothing.
- virtual void HandleAssemblerFlag(MCAssemblerFlag Flag) {}
+ virtual void handleAssemblerFlag(MCAssemblerFlag Flag) {}
};
} // End llvm namespace
diff --git a/include/llvm/MC/MCAsmInfo.h b/include/llvm/MC/MCAsmInfo.h
index c3c296e..0f67c99 100644
--- a/include/llvm/MC/MCAsmInfo.h
+++ b/include/llvm/MC/MCAsmInfo.h
@@ -36,10 +36,6 @@ namespace llvm {
enum LCOMMType { None, NoAlignment, ByteAlignment };
}
- namespace Structors {
- enum OutputOrder { None, PriorityOrder, ReversePriorityOrder };
- }
-
/// MCAsmInfo - This class is intended to be used as a base class for asm
/// properties and features specific to the target.
class MCAsmInfo {
@@ -47,7 +43,7 @@ namespace llvm {
//===------------------------------------------------------------------===//
// Properties to be set by the target writer, used to configure asm printer.
//
-
+
/// PointerSize - Pointer size in bytes.
/// Default is 4.
unsigned PointerSize;
@@ -72,11 +68,6 @@ namespace llvm {
/// the macho-specific .tbss directive for emitting thread local BSS Symbols
bool HasMachoTBSSDirective; // Default is false.
- /// StructorOutputOrder - Whether the static ctor/dtor list should be output
- /// in no particular order, in order of increasing priority or the reverse:
- /// in order of decreasing priority (the default).
- Structors::OutputOrder StructorOutputOrder; // Default is reverse order.
-
/// HasStaticCtorDtorReferenceInStaticMode - True if the compiler should
/// emit a ".reference .constructors_used" or ".reference .destructors_used"
/// directive after the a static ctor/dtor list. This directive is only
@@ -152,6 +143,10 @@ namespace llvm {
/// symbol names. This defaults to true.
bool AllowPeriodsInName;
+ /// AllowUTF8 - This is true if the assembler accepts UTF-8 input.
+ // FIXME: Make this a more general encoding setting?
+ bool AllowUTF8;
+
//===--- Data Emission Directives -------------------------------------===//
/// ZeroDirective - this should be set to the directive used to get some
@@ -189,6 +184,11 @@ namespace llvm {
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.
+ const char *GPRel64Directive; // Defaults to NULL.
+
/// GPRel32Directive - if non-null, a directive that is used to emit a word
/// which should be relocated as a 32-bit GP-relative offset, e.g. .gpword
/// on Mips or .gprel32 on Alpha.
@@ -323,13 +323,17 @@ namespace llvm {
const char* DwarfSectionOffsetDirective; // Defaults to NULL
/// DwarfRequiresRelocationForSectionOffset - True if we need to produce a
- // relocation when we want a section offset in dwarf.
+ /// relocation when we want a section offset in dwarf.
bool DwarfRequiresRelocationForSectionOffset; // Defaults to true;
- // DwarfUsesLabelOffsetDifference - True if Dwarf2 output can
- // use EmitLabelOffsetDifference.
+ /// 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;
+
/// DwarfRegNumForCFI - True if dwarf register numbers are printed
/// instead of symbolic register names in .cfi_* directives.
bool DwarfRegNumForCFI; // Defaults to false;
@@ -381,6 +385,7 @@ namespace llvm {
const char *getData64bitsDirective(unsigned AS = 0) const {
return AS == 0 ? Data64bitsDirective : getDataASDirective(64, AS);
}
+ const char *getGPRel64Directive() const { return GPRel64Directive; }
const char *getGPRel32Directive() const { return GPRel32Directive; }
/// [Code|Data]Begin label name accessors.
@@ -424,9 +429,6 @@ namespace llvm {
//
bool hasMachoZeroFillDirective() const { return HasMachoZeroFillDirective; }
bool hasMachoTBSSDirective() const { return HasMachoTBSSDirective; }
- Structors::OutputOrder getStructorOutputOrder() const {
- return StructorOutputOrder;
- }
bool hasStaticCtorDtorReferenceInStaticMode() const {
return HasStaticCtorDtorReferenceInStaticMode;
}
@@ -487,6 +489,9 @@ namespace llvm {
bool doesAllowPeriodsInName() const {
return AllowPeriodsInName;
}
+ bool doesAllowUTF8() const {
+ return AllowUTF8;
+ }
const char *getZeroDirective() const {
return ZeroDirective;
}
@@ -554,7 +559,7 @@ namespace llvm {
ExceptionsType == ExceptionHandling::ARM ||
ExceptionsType == ExceptionHandling::Win64);
}
- bool doesDwarfUsesInlineInfoSection() const {
+ bool doesDwarfUseInlineInfoSection() const {
return DwarfUsesInlineInfoSection;
}
const char *getDwarfSectionOffsetDirective() const {
@@ -563,9 +568,12 @@ namespace llvm {
bool doesDwarfRequireRelocationForSectionOffset() const {
return DwarfRequiresRelocationForSectionOffset;
}
- bool doesDwarfUsesLabelOffsetForRanges() const {
+ bool doesDwarfUseLabelOffsetForRanges() const {
return DwarfUsesLabelOffsetForRanges;
}
+ bool doesDwarfUseRelocationsForStringPool() const {
+ return DwarfUsesRelocationsForStringPool;
+ }
bool useDwarfRegNumForCFI() const {
return DwarfRegNumForCFI;
}
diff --git a/include/llvm/MC/MCAsmInfoCOFF.h b/include/llvm/MC/MCAsmInfoCOFF.h
index a3ee159..0ff3e12 100644
--- a/include/llvm/MC/MCAsmInfoCOFF.h
+++ b/include/llvm/MC/MCAsmInfoCOFF.h
@@ -14,9 +14,21 @@
namespace llvm {
class MCAsmInfoCOFF : public MCAsmInfo {
+ virtual void anchor();
protected:
explicit MCAsmInfoCOFF();
-
+ };
+
+ class MCAsmInfoMicrosoft : public MCAsmInfoCOFF {
+ virtual void anchor();
+ protected:
+ explicit MCAsmInfoMicrosoft();
+ };
+
+ class MCAsmInfoGNUCOFF : public MCAsmInfoCOFF {
+ virtual void anchor();
+ protected:
+ explicit MCAsmInfoGNUCOFF();
};
}
diff --git a/include/llvm/MC/MCAsmInfoDarwin.h b/include/llvm/MC/MCAsmInfoDarwin.h
index 1f6c499..af552de 100644
--- a/include/llvm/MC/MCAsmInfoDarwin.h
+++ b/include/llvm/MC/MCAsmInfoDarwin.h
@@ -18,7 +18,9 @@
#include "llvm/MC/MCAsmInfo.h"
namespace llvm {
- struct MCAsmInfoDarwin : public MCAsmInfo {
+ class MCAsmInfoDarwin : public MCAsmInfo {
+ virtual void anchor();
+ public:
explicit MCAsmInfoDarwin();
};
}
diff --git a/include/llvm/MC/MCAsmLayout.h b/include/llvm/MC/MCAsmLayout.h
index a4585d1..cf79216 100644
--- a/include/llvm/MC/MCAsmLayout.h
+++ b/include/llvm/MC/MCAsmLayout.h
@@ -10,6 +10,7 @@
#ifndef LLVM_MC_MCASMLAYOUT_H
#define LLVM_MC_MCASMLAYOUT_H
+#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/SmallVector.h"
namespace llvm {
diff --git a/include/llvm/MC/MCAssembler.h b/include/llvm/MC/MCAssembler.h
index b8f8cc4..d139173 100644
--- a/include/llvm/MC/MCAssembler.h
+++ b/include/llvm/MC/MCAssembler.h
@@ -25,7 +25,6 @@ namespace llvm {
class raw_ostream;
class MCAsmLayout;
class MCAssembler;
-class MCBinaryExpr;
class MCContext;
class MCCodeEmitter;
class MCExpr;
@@ -106,6 +105,7 @@ public:
};
class MCDataFragment : public MCFragment {
+ virtual void anchor();
SmallString<32> Contents;
/// Fixups - The list of fixups in this fragment.
@@ -160,6 +160,8 @@ public:
// object with just the MCInst and a code size, then we should just change
// MCDataFragment to have an optional MCInst at its end.
class MCInstFragment : public MCFragment {
+ virtual void anchor();
+
/// Inst - The instruction this is a fragment for.
MCInst Inst;
@@ -215,6 +217,8 @@ public:
};
class MCAlignFragment : public MCFragment {
+ virtual void anchor();
+
/// Alignment - The alignment to ensure, in bytes.
unsigned Alignment;
@@ -263,6 +267,8 @@ public:
};
class MCFillFragment : public MCFragment {
+ virtual void anchor();
+
/// Value - Value to use for filling bytes.
int64_t Value;
@@ -300,6 +306,8 @@ public:
};
class MCOrgFragment : public MCFragment {
+ virtual void anchor();
+
/// Offset - The offset this fragment should start at.
const MCExpr *Offset;
@@ -327,6 +335,8 @@ public:
};
class MCLEBFragment : public MCFragment {
+ virtual void anchor();
+
/// Value - The value this fragment should contain.
const MCExpr *Value;
@@ -358,6 +368,8 @@ public:
};
class MCDwarfLineAddrFragment : public MCFragment {
+ virtual void anchor();
+
/// LineDelta - the value of the difference between the two line numbers
/// between two .loc dwarf directives.
int64_t LineDelta;
@@ -393,6 +405,8 @@ public:
};
class MCDwarfCallFrameFragment : public MCFragment {
+ virtual void anchor();
+
/// AddrDelta - The expression for the difference of the two symbols that
/// make up the address delta between two .cfi_* dwarf directives.
const MCExpr *AddrDelta;
@@ -711,43 +725,44 @@ private:
/// \return Whether the fixup value was fully resolved. This is true if the
/// \arg Value result is fixed, otherwise the value may change due to
/// relocation.
- bool EvaluateFixup(const MCAsmLayout &Layout,
+ bool evaluateFixup(const MCAsmLayout &Layout,
const MCFixup &Fixup, const MCFragment *DF,
MCValue &Target, uint64_t &Value) const;
/// Check whether a fixup can be satisfied, or whether it needs to be relaxed
/// (increased in size, in order to hold its value correctly).
- bool FixupNeedsRelaxation(const MCFixup &Fixup, const MCFragment *DF,
+ bool fixupNeedsRelaxation(const MCFixup &Fixup, const MCInstFragment *DF,
const MCAsmLayout &Layout) const;
/// Check whether the given fragment needs relaxation.
- bool FragmentNeedsRelaxation(const MCInstFragment *IF,
+ bool fragmentNeedsRelaxation(const MCInstFragment *IF,
const MCAsmLayout &Layout) const;
- /// LayoutOnce - Perform one layout iteration and return true if any offsets
+ /// layoutOnce - Perform one layout iteration and return true if any offsets
/// were adjusted.
- bool LayoutOnce(MCAsmLayout &Layout);
+ bool layoutOnce(MCAsmLayout &Layout);
- bool LayoutSectionOnce(MCAsmLayout &Layout, MCSectionData &SD);
+ bool layoutSectionOnce(MCAsmLayout &Layout, MCSectionData &SD);
- bool RelaxInstruction(MCAsmLayout &Layout, MCInstFragment &IF);
+ bool relaxInstruction(MCAsmLayout &Layout, MCInstFragment &IF);
- bool RelaxLEB(MCAsmLayout &Layout, MCLEBFragment &IF);
+ bool relaxLEB(MCAsmLayout &Layout, MCLEBFragment &IF);
- bool RelaxDwarfLineAddr(MCAsmLayout &Layout, MCDwarfLineAddrFragment &DF);
- bool RelaxDwarfCallFrameFragment(MCAsmLayout &Layout,
+ bool relaxDwarfLineAddr(MCAsmLayout &Layout, MCDwarfLineAddrFragment &DF);
+ bool relaxDwarfCallFrameFragment(MCAsmLayout &Layout,
MCDwarfCallFrameFragment &DF);
- /// FinishLayout - Finalize a layout, including fragment lowering.
- void FinishLayout(MCAsmLayout &Layout);
+ /// finishLayout - Finalize a layout, including fragment lowering.
+ void finishLayout(MCAsmLayout &Layout);
- uint64_t HandleFixup(const MCAsmLayout &Layout,
+ uint64_t handleFixup(const MCAsmLayout &Layout,
MCFragment &F, const MCFixup &Fixup);
public:
/// Compute the effective fragment size assuming it is laid out at the given
/// \arg SectionAddress and \arg FragmentOffset.
- uint64_t ComputeFragmentSize(const MCAsmLayout &Layout, const MCFragment &F) const;
+ uint64_t computeFragmentSize(const MCAsmLayout &Layout,
+ const MCFragment &F) const;
/// Find the symbol which defines the atom containing the given symbol, or
/// null if there is no such symbol.
@@ -760,7 +775,7 @@ public:
bool isSymbolLinkerVisible(const MCSymbol &SD) const;
/// Emit the section contents using the given object writer.
- void WriteSectionData(const MCSectionData *Section,
+ void writeSectionData(const MCSectionData *Section,
const MCAsmLayout &Layout) const;
/// Check whether a given symbol has been flagged with .thumb_func.
diff --git a/include/llvm/MC/MCCodeEmitter.h b/include/llvm/MC/MCCodeEmitter.h
index bc63241..934ef69 100644
--- a/include/llvm/MC/MCCodeEmitter.h
+++ b/include/llvm/MC/MCCodeEmitter.h
@@ -10,12 +10,8 @@
#ifndef LLVM_MC_MCCODEEMITTER_H
#define LLVM_MC_MCCODEEMITTER_H
-#include "llvm/MC/MCFixup.h"
-
-#include <cassert>
-
namespace llvm {
-class MCExpr;
+class MCFixup;
class MCInst;
class raw_ostream;
template<typename T> class SmallVectorImpl;
diff --git a/include/llvm/MC/MCCodeGenInfo.h b/include/llvm/MC/MCCodeGenInfo.h
index 1c54c47..d1765e1 100644
--- a/include/llvm/MC/MCCodeGenInfo.h
+++ b/include/llvm/MC/MCCodeGenInfo.h
@@ -20,7 +20,7 @@
namespace llvm {
class MCCodeGenInfo {
- /// RelocationModel - Relocation model: statcic, pic, etc.
+ /// RelocationModel - Relocation model: static, pic, etc.
///
Reloc::Model RelocationModel;
@@ -28,13 +28,20 @@ namespace llvm {
///
CodeModel::Model CMModel;
+ /// OptLevel - Optimization level.
+ ///
+ CodeGenOpt::Level OptLevel;
+
public:
void InitMCCodeGenInfo(Reloc::Model RM = Reloc::Default,
- CodeModel::Model CM = CodeModel::Default);
+ CodeModel::Model CM = CodeModel::Default,
+ CodeGenOpt::Level OL = CodeGenOpt::Default);
Reloc::Model getRelocationModel() const { return RelocationModel; }
CodeModel::Model getCodeModel() const { return CMModel; }
+
+ CodeGenOpt::Level getOptLevel() const { return OptLevel; }
};
} // namespace llvm
diff --git a/include/llvm/MC/MCContext.h b/include/llvm/MC/MCContext.h
index a49a35c..b586319 100644
--- a/include/llvm/MC/MCContext.h
+++ b/include/llvm/MC/MCContext.h
@@ -15,6 +15,7 @@
#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/StringMap.h"
#include "llvm/Support/Allocator.h"
+#include "llvm/Support/Compiler.h"
#include "llvm/Support/raw_ostream.h"
#include <vector> // FIXME: Shouldn't be needed.
@@ -29,6 +30,7 @@ namespace llvm {
class MCObjectFileInfo;
class MCRegisterInfo;
class MCLineSection;
+ class SMLoc;
class StringRef;
class Twine;
class MCSectionMachO;
@@ -43,6 +45,8 @@ namespace llvm {
public:
typedef StringMap<MCSymbol*, BumpPtrAllocator&> SymbolTable;
private:
+ /// The SourceMgr for this object, if any.
+ const SourceMgr *SrcMgr;
/// The MCAsmInfo for this target.
const MCAsmInfo &MAI;
@@ -98,6 +102,27 @@ namespace llvm {
MCDwarfLoc CurrentDwarfLoc;
bool DwarfLocSeen;
+ /// Generate dwarf debugging info for assembly source files.
+ bool GenDwarfForAssembly;
+
+ /// The current dwarf file number when generate dwarf debugging info for
+ /// assembly source files.
+ unsigned GenDwarfFileNumber;
+
+ /// The default initial text section that we generate dwarf debugging line
+ /// info for when generating dwarf assembly source files.
+ const MCSection *GenDwarfSection;
+ /// Symbols created for the start and end of this section.
+ MCSymbol *GenDwarfSectionStartSym, *GenDwarfSectionEndSym;
+
+ /// The information gathered from labels that will have dwarf label
+ /// entries when generating dwarf assembly source files.
+ std::vector<const MCGenDwarfLabelEntry *> MCGenDwarfLabelEntries;
+
+ /// The string to embed in the debug information for the compile unit, if
+ /// non-empty.
+ StringRef DwarfDebugFlags;
+
/// Honor temporary labels, this is useful for debugging semantic
/// differences between temporary and non-temporary labels (primarily on
/// Darwin).
@@ -116,9 +141,11 @@ namespace llvm {
public:
explicit MCContext(const MCAsmInfo &MAI, const MCRegisterInfo &MRI,
- const MCObjectFileInfo *MOFI);
+ const MCObjectFileInfo *MOFI, const SourceMgr *Mgr = 0);
~MCContext();
+ const SourceMgr *getSourceManager() const { return SrcMgr; }
+
const MCAsmInfo &getAsmInfo() const { return MAI; }
const MCRegisterInfo &getRegisterInfo() const { return MRI; }
@@ -204,7 +231,8 @@ namespace llvm {
/// @{
/// GetDwarfFile - creates an entry in the dwarf file and directory tables.
- unsigned GetDwarfFile(StringRef FileName, unsigned FileNumber);
+ unsigned GetDwarfFile(StringRef Directory, StringRef FileName,
+ unsigned FileNumber);
bool isValidDwarfFileNumber(unsigned FileNumber);
@@ -251,6 +279,31 @@ namespace llvm {
bool getDwarfLocSeen() { return DwarfLocSeen; }
const MCDwarfLoc &getCurrentDwarfLoc() { return CurrentDwarfLoc; }
+ bool getGenDwarfForAssembly() { return GenDwarfForAssembly; }
+ void setGenDwarfForAssembly(bool Value) { GenDwarfForAssembly = Value; }
+ unsigned getGenDwarfFileNumber() { return GenDwarfFileNumber; }
+ unsigned nextGenDwarfFileNumber() { return ++GenDwarfFileNumber; }
+ const MCSection *getGenDwarfSection() { return GenDwarfSection; }
+ void setGenDwarfSection(const MCSection *Sec) { GenDwarfSection = Sec; }
+ MCSymbol *getGenDwarfSectionStartSym() { return GenDwarfSectionStartSym; }
+ void setGenDwarfSectionStartSym(MCSymbol *Sym) {
+ GenDwarfSectionStartSym = Sym;
+ }
+ MCSymbol *getGenDwarfSectionEndSym() { return GenDwarfSectionEndSym; }
+ void setGenDwarfSectionEndSym(MCSymbol *Sym) {
+ GenDwarfSectionEndSym = Sym;
+ }
+ const std::vector<const MCGenDwarfLabelEntry *>
+ &getMCGenDwarfLabelEntries() const {
+ return MCGenDwarfLabelEntries;
+ }
+ void addMCGenDwarfLabelEntry(const MCGenDwarfLabelEntry *E) {
+ MCGenDwarfLabelEntries.push_back(E);
+ }
+
+ void setDwarfDebugFlags(StringRef S) { DwarfDebugFlags = S; }
+ StringRef getDwarfDebugFlags() { return DwarfDebugFlags; }
+
/// @}
char *getSecureLogFile() { return SecureLogFile; }
@@ -268,6 +321,11 @@ namespace llvm {
}
void Deallocate(void *Ptr) {
}
+
+ // Unrecoverable error has occured. Display the best diagnostic we can
+ // and bail via exit(1). For now, most MC backend errors are unrecoverable.
+ // FIXME: We should really do something about that.
+ LLVM_ATTRIBUTE_NORETURN void FatalError(SMLoc L, const Twine &Msg);
};
} // end namespace llvm
diff --git a/include/llvm/MC/MCDisassembler.h b/include/llvm/MC/MCDisassembler.h
index 454277d..4b5fbec 100644
--- a/include/llvm/MC/MCDisassembler.h
+++ b/include/llvm/MC/MCDisassembler.h
@@ -90,7 +90,7 @@ public:
/// @return - An array of instruction information, with one entry for
/// each MCInst opcode this disassembler returns.
/// NULL if there is no info for this target.
- virtual EDInstInfo *getEDInfo() const { return (EDInstInfo*)0; }
+ virtual const EDInstInfo *getEDInfo() const { return (EDInstInfo*)0; }
private:
//
diff --git a/include/llvm/MC/MCDwarf.h b/include/llvm/MC/MCDwarf.h
index 431e3c4..fdb7ab2 100644
--- a/include/llvm/MC/MCDwarf.h
+++ b/include/llvm/MC/MCDwarf.h
@@ -17,20 +17,18 @@
#include "llvm/ADT/StringRef.h"
#include "llvm/MC/MachineLocation.h"
-#include "llvm/MC/MCObjectWriter.h"
#include "llvm/Support/raw_ostream.h"
#include "llvm/Support/Dwarf.h"
#include <vector>
namespace llvm {
class MCContext;
- class MCExpr;
+ class MCObjectWriter;
class MCSection;
- class MCSectionData;
class MCStreamer;
class MCSymbol;
- class MCObjectStreamer;
- class raw_ostream;
+ class SourceMgr;
+ class SMLoc;
/// MCDwarfFile - Instances of this class represent the name of the dwarf
/// .file directive and its associated dwarf file number in the MC file,
@@ -210,7 +208,7 @@ namespace llvm {
//
// This emits the Dwarf file and the line tables.
//
- static void Emit(MCStreamer *MCOS);
+ static const MCSymbol *Emit(MCStreamer *MCOS);
};
class MCDwarfLineAddr {
@@ -227,23 +225,63 @@ namespace llvm {
int64_t LineDelta, uint64_t AddrDelta);
};
+ class MCGenDwarfInfo {
+ public:
+ //
+ // When generating dwarf for assembly source files this emits the Dwarf
+ // sections.
+ //
+ static void Emit(MCStreamer *MCOS, const MCSymbol *LineSectionSymbol);
+ };
+
+ // When generating dwarf for assembly source files this is the info that is
+ // needed to be gathered for each symbol that will have a dwarf label.
+ class MCGenDwarfLabelEntry {
+ private:
+ // Name of the symbol without a leading underbar, if any.
+ StringRef Name;
+ // The dwarf file number this symbol is in.
+ unsigned FileNumber;
+ // The line number this symbol is at.
+ unsigned LineNumber;
+ // The low_pc for the dwarf label is taken from this symbol.
+ MCSymbol *Label;
+
+ public:
+ MCGenDwarfLabelEntry(StringRef name, unsigned fileNumber,
+ unsigned lineNumber, MCSymbol *label) :
+ Name(name), FileNumber(fileNumber), LineNumber(lineNumber), Label(label){}
+
+ StringRef getName() const { return Name; }
+ unsigned getFileNumber() const { return FileNumber; }
+ unsigned getLineNumber() const { return LineNumber; }
+ MCSymbol *getLabel() const { return Label; }
+
+ // This is called when label is created when we are generating dwarf for
+ // assembly source files.
+ static void Make(MCSymbol *Symbol, MCStreamer *MCOS, SourceMgr &SrcMgr,
+ SMLoc &Loc);
+ };
+
class MCCFIInstruction {
public:
- enum OpType { SameValue, Remember, Restore, Move, RelMove };
+ enum OpType { SameValue, RememberState, RestoreState, Move, RelMove, Escape,
+ Restore};
private:
OpType Operation;
MCSymbol *Label;
// Move to & from location.
MachineLocation Destination;
MachineLocation Source;
+ std::vector<char> Values;
public:
MCCFIInstruction(OpType Op, MCSymbol *L)
: Operation(Op), Label(L) {
- assert(Op == Remember || Op == Restore);
+ assert(Op == RememberState || Op == RestoreState);
}
MCCFIInstruction(OpType Op, MCSymbol *L, unsigned Register)
: Operation(Op), Label(L), Destination(Register) {
- assert(Op == SameValue);
+ assert(Op == SameValue || Op == Restore);
}
MCCFIInstruction(MCSymbol *L, const MachineLocation &D,
const MachineLocation &S)
@@ -254,16 +292,24 @@ namespace llvm {
: Operation(Op), Label(L), Destination(D), Source(S) {
assert(Op == RelMove);
}
+ MCCFIInstruction(OpType Op, MCSymbol *L, StringRef Vals)
+ : Operation(Op), Label(L), Values(Vals.begin(), Vals.end()) {
+ assert(Op == Escape);
+ }
OpType getOperation() const { return Operation; }
MCSymbol *getLabel() const { return Label; }
const MachineLocation &getDestination() const { return Destination; }
const MachineLocation &getSource() const { return Source; }
+ const StringRef getValues() const {
+ return StringRef(&Values[0], Values.size());
+ }
};
struct MCDwarfFrameInfo {
MCDwarfFrameInfo() : Begin(0), End(0), Personality(0), Lsda(0),
Function(0), Instructions(), PersonalityEncoding(),
- LsdaEncoding(0), CompactUnwindEncoding(0) {}
+ LsdaEncoding(0), CompactUnwindEncoding(0),
+ IsSignalFrame(false) {}
MCSymbol *Begin;
MCSymbol *End;
const MCSymbol *Personality;
@@ -273,6 +319,7 @@ namespace llvm {
unsigned PersonalityEncoding;
unsigned LsdaEncoding;
uint32_t CompactUnwindEncoding;
+ bool IsSignalFrame;
};
class MCDwarfFrameEmitter {
diff --git a/include/llvm/MC/MCELFObjectWriter.h b/include/llvm/MC/MCELFObjectWriter.h
index 3c150dc..f153cb0 100644
--- a/include/llvm/MC/MCELFObjectWriter.h
+++ b/include/llvm/MC/MCELFObjectWriter.h
@@ -10,28 +10,91 @@
#ifndef LLVM_MC_MCELFOBJECTWRITER_H
#define LLVM_MC_MCELFOBJECTWRITER_H
-#include "llvm/MC/MCObjectWriter.h"
+#include "llvm/ADT/Triple.h"
#include "llvm/Support/DataTypes.h"
+#include "llvm/Support/ELF.h"
+#include <vector>
namespace llvm {
+class MCAssembler;
+class MCFixup;
+class MCFragment;
+class MCObjectWriter;
+class MCSymbol;
+class MCValue;
+
+/// @name Relocation Data
+/// @{
+
+struct ELFRelocationEntry {
+ // Make these big enough for both 32-bit and 64-bit
+ uint64_t r_offset;
+ int Index;
+ unsigned Type;
+ const MCSymbol *Symbol;
+ uint64_t r_addend;
+ const MCFixup *Fixup;
+
+ ELFRelocationEntry()
+ : r_offset(0), Index(0), Type(0), Symbol(0), r_addend(0), Fixup(0) {}
+
+ ELFRelocationEntry(uint64_t RelocOffset, int Idx, unsigned RelType,
+ const MCSymbol *Sym, uint64_t Addend, const MCFixup &Fixup)
+ : r_offset(RelocOffset), Index(Idx), Type(RelType), Symbol(Sym),
+ r_addend(Addend), Fixup(&Fixup) {}
+
+ // Support lexicographic sorting.
+ bool operator<(const ELFRelocationEntry &RE) const {
+ return RE.r_offset < r_offset;
+ }
+};
+
class MCELFObjectTargetWriter {
- const Triple::OSType OSType;
+ const uint8_t OSABI;
const uint16_t EMachine;
const unsigned HasRelocationAddend : 1;
const unsigned Is64Bit : 1;
+
protected:
- MCELFObjectTargetWriter(bool Is64Bit_, Triple::OSType OSType_,
+
+ MCELFObjectTargetWriter(bool Is64Bit_, uint8_t OSABI_,
uint16_t EMachine_, bool HasRelocationAddend_);
public:
- virtual ~MCELFObjectTargetWriter();
+ static uint8_t getOSABI(Triple::OSType OSType) {
+ switch (OSType) {
+ case Triple::FreeBSD:
+ return ELF::ELFOSABI_FREEBSD;
+ case Triple::Linux:
+ return ELF::ELFOSABI_LINUX;
+ default:
+ return ELF::ELFOSABI_NONE;
+ }
+ }
+
+ virtual ~MCELFObjectTargetWriter() {}
+
+ virtual unsigned GetRelocType(const MCValue &Target, const MCFixup &Fixup,
+ bool IsPCRel, bool IsRelocWithSymbol,
+ int64_t Addend) const = 0;
+ virtual unsigned getEFlags() const;
+ virtual const MCSymbol *ExplicitRelSym(const MCAssembler &Asm,
+ const MCValue &Target,
+ const MCFragment &F,
+ const MCFixup &Fixup,
+ bool IsPCRel) const;
+ virtual void adjustFixupOffset(const MCFixup &Fixup,
+ uint64_t &RelocOffset);
+
+ virtual void sortRelocs(const MCAssembler &Asm,
+ std::vector<ELFRelocationEntry> &Relocs);
/// @name Accessors
/// @{
- Triple::OSType getOSType() { return OSType; }
+ uint8_t getOSABI() { return OSABI; }
uint16_t getEMachine() { return EMachine; }
bool hasRelocationAddend() { return HasRelocationAddend; }
- bool is64Bit() { return Is64Bit; }
+ bool is64Bit() const { return Is64Bit; }
/// @}
};
diff --git a/include/llvm/MC/MCExpr.h b/include/llvm/MC/MCExpr.h
index 0f28599..ff33641 100644
--- a/include/llvm/MC/MCExpr.h
+++ b/include/llvm/MC/MCExpr.h
@@ -15,7 +15,6 @@
#include "llvm/Support/DataTypes.h"
namespace llvm {
-class MCAsmInfo;
class MCAsmLayout;
class MCAssembler;
class MCContext;
@@ -162,6 +161,7 @@ public:
VK_TPOFF,
VK_DTPOFF,
VK_TLVP, // Mach-O thread local variable relocation
+ VK_SECREL,
// FIXME: We'd really like to use the generic Kinds listed above for these.
VK_ARM_PLT, // ARM-style PLT references. i.e., (PLT) instead of @PLT
VK_ARM_TLSGD, // ditto for TLSGD, GOT, GOTOFF, TPOFF and GOTTPOFF
@@ -169,12 +169,32 @@ public:
VK_ARM_GOTOFF,
VK_ARM_TPOFF,
VK_ARM_GOTTPOFF,
+ VK_ARM_TARGET1,
VK_PPC_TOC,
VK_PPC_DARWIN_HA16, // ha16(symbol)
VK_PPC_DARWIN_LO16, // lo16(symbol)
VK_PPC_GAS_HA16, // symbol@ha
- VK_PPC_GAS_LO16 // symbol@l
+ VK_PPC_GAS_LO16, // symbol@l
+
+ VK_Mips_GPREL,
+ VK_Mips_GOT_CALL,
+ VK_Mips_GOT16,
+ VK_Mips_GOT,
+ VK_Mips_ABS_HI,
+ VK_Mips_ABS_LO,
+ VK_Mips_TLSGD,
+ VK_Mips_TLSLDM,
+ VK_Mips_DTPREL_HI,
+ VK_Mips_DTPREL_LO,
+ VK_Mips_GOTTPREL,
+ VK_Mips_TPREL_HI,
+ VK_Mips_TPREL_LO,
+ VK_Mips_GPOFF_HI,
+ VK_Mips_GPOFF_LO,
+ VK_Mips_GOT_DISP,
+ VK_Mips_GOT_PAGE,
+ VK_Mips_GOT_OFST
};
private:
@@ -185,7 +205,9 @@ private:
const VariantKind Kind;
explicit MCSymbolRefExpr(const MCSymbol *_Symbol, VariantKind _Kind)
- : MCExpr(MCExpr::SymbolRef), Symbol(_Symbol), Kind(_Kind) {}
+ : MCExpr(MCExpr::SymbolRef), Symbol(_Symbol), Kind(_Kind) {
+ assert(Symbol);
+ }
public:
/// @name Construction
diff --git a/include/llvm/MC/MCFixup.h b/include/llvm/MC/MCFixup.h
index 6fde797..16e9eb7 100644
--- a/include/llvm/MC/MCFixup.h
+++ b/include/llvm/MC/MCFixup.h
@@ -11,6 +11,8 @@
#define LLVM_MC_MCFIXUP_H
#include "llvm/Support/DataTypes.h"
+#include "llvm/Support/ErrorHandling.h"
+#include "llvm/Support/SMLoc.h"
#include <cassert>
namespace llvm {
@@ -26,6 +28,14 @@ enum MCFixupKind {
FK_PCRel_2, ///< A two-byte pc relative fixup.
FK_PCRel_4, ///< A four-byte pc relative fixup.
FK_PCRel_8, ///< A eight-byte pc relative fixup.
+ FK_GPRel_1, ///< A one-byte gp relative fixup.
+ FK_GPRel_2, ///< A two-byte gp relative fixup.
+ FK_GPRel_4, ///< A four-byte gp relative fixup.
+ FK_GPRel_8, ///< A eight-byte gp relative fixup.
+ FK_SecRel_1, ///< A one-byte section relative fixup.
+ FK_SecRel_2, ///< A two-byte section relative fixup.
+ FK_SecRel_4, ///< A four-byte section relative fixup.
+ FK_SecRel_8, ///< A eight-byte section relative fixup.
FirstTargetFixupKind = 128,
@@ -61,14 +71,17 @@ class MCFixup {
/// determine how the operand value should be encoded into the instruction.
unsigned Kind;
+ /// The source location which gave rise to the fixup, if any.
+ SMLoc Loc;
public:
static MCFixup Create(uint32_t Offset, const MCExpr *Value,
- MCFixupKind Kind) {
+ MCFixupKind Kind, SMLoc Loc = SMLoc()) {
assert(unsigned(Kind) < MaxTargetFixupKind && "Kind out of range!");
MCFixup FI;
FI.Value = Value;
FI.Offset = Offset;
FI.Kind = unsigned(Kind);
+ FI.Loc = Loc;
return FI;
}
@@ -83,13 +96,15 @@ public:
/// size. It is an error to pass an unsupported size.
static MCFixupKind getKindForSize(unsigned Size, bool isPCRel) {
switch (Size) {
- default: assert(0 && "Invalid generic fixup size!");
+ default: llvm_unreachable("Invalid generic fixup size!");
case 1: return isPCRel ? FK_PCRel_1 : FK_Data_1;
case 2: return isPCRel ? FK_PCRel_2 : FK_Data_2;
case 4: return isPCRel ? FK_PCRel_4 : FK_Data_4;
case 8: return isPCRel ? FK_PCRel_8 : FK_Data_8;
}
}
+
+ SMLoc getLoc() const { return Loc; }
};
} // End llvm namespace
diff --git a/include/llvm/MC/MCInst.h b/include/llvm/MC/MCInst.h
index d384764..397a37d 100644
--- a/include/llvm/MC/MCInst.h
+++ b/include/llvm/MC/MCInst.h
@@ -19,12 +19,14 @@
#include "llvm/ADT/SmallVector.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/Support/DataTypes.h"
+#include "llvm/Support/SMLoc.h"
namespace llvm {
class raw_ostream;
class MCAsmInfo;
class MCInstPrinter;
class MCExpr;
+class MCInst;
/// MCOperand - Instances of this class represent operands of the MCInst class.
/// This is a simple discriminated union.
@@ -34,7 +36,8 @@ class MCOperand {
kRegister, ///< Register operand.
kImmediate, ///< Immediate operand.
kFPImmediate, ///< Floating-point immediate operand.
- kExpr ///< Relocatable immediate operand.
+ kExpr, ///< Relocatable immediate operand.
+ kInst ///< Sub-instruction operand.
};
unsigned char Kind;
@@ -43,6 +46,7 @@ class MCOperand {
int64_t ImmVal;
double FPImmVal;
const MCExpr *ExprVal;
+ const MCInst *InstVal;
};
public:
@@ -53,6 +57,7 @@ public:
bool isImm() const { return Kind == kImmediate; }
bool isFPImm() const { return Kind == kFPImmediate; }
bool isExpr() const { return Kind == kExpr; }
+ bool isInst() const { return Kind == kInst; }
/// getReg - Returns the register number.
unsigned getReg() const {
@@ -94,6 +99,15 @@ public:
ExprVal = Val;
}
+ const MCInst *getInst() const {
+ assert(isInst() && "This is not a sub-instruction");
+ return InstVal;
+ }
+ void setInst(const MCInst *Val) {
+ assert(isInst() && "This is not a sub-instruction");
+ InstVal = Val;
+ }
+
static MCOperand CreateReg(unsigned Reg) {
MCOperand Op;
Op.Kind = kRegister;
@@ -118,24 +132,34 @@ public:
Op.ExprVal = Val;
return Op;
}
+ static MCOperand CreateInst(const MCInst *Val) {
+ MCOperand Op;
+ Op.Kind = kInst;
+ Op.InstVal = Val;
+ return Op;
+ }
void print(raw_ostream &OS, const MCAsmInfo *MAI) const;
void dump() const;
};
+template <> struct isPodLike<MCOperand> { static const bool value = true; };
/// MCInst - Instances of this class represent a single low-level machine
/// instruction.
class MCInst {
unsigned Opcode;
+ SMLoc Loc;
SmallVector<MCOperand, 8> Operands;
public:
MCInst() : Opcode(0) {}
void setOpcode(unsigned Op) { Opcode = Op; }
-
unsigned getOpcode() const { return Opcode; }
+ void setLoc(SMLoc loc) { Loc = loc; }
+ SMLoc getLoc() const { return Loc; }
+
const MCOperand &getOperand(unsigned i) const { return Operands[i]; }
MCOperand &getOperand(unsigned i) { return Operands[i]; }
unsigned getNumOperands() const { return Operands.size(); }
diff --git a/include/llvm/MC/MCInstPrinter.h b/include/llvm/MC/MCInstPrinter.h
index 01ad2d3f..3c4f28b 100644
--- a/include/llvm/MC/MCInstPrinter.h
+++ b/include/llvm/MC/MCInstPrinter.h
@@ -14,6 +14,8 @@ namespace llvm {
class MCInst;
class raw_ostream;
class MCAsmInfo;
+class MCInstrInfo;
+class MCRegisterInfo;
class StringRef;
/// MCInstPrinter - This is an instance of a target assembly language printer
@@ -25,6 +27,8 @@ protected:
/// assembly emission is disable.
raw_ostream *CommentStream;
const MCAsmInfo &MAI;
+ const MCInstrInfo &MII;
+ const MCRegisterInfo &MRI;
/// The current set of available features.
unsigned AvailableFeatures;
@@ -32,8 +36,9 @@ protected:
/// Utility function for printing annotations.
void printAnnotation(raw_ostream &OS, StringRef Annot);
public:
- MCInstPrinter(const MCAsmInfo &mai)
- : CommentStream(0), MAI(mai), AvailableFeatures(0) {}
+ MCInstPrinter(const MCAsmInfo &mai, const MCInstrInfo &mii,
+ const MCRegisterInfo &mri)
+ : CommentStream(0), MAI(mai), MII(mii), MRI(mri), AvailableFeatures(0) {}
virtual ~MCInstPrinter();
@@ -47,7 +52,7 @@ public:
/// getOpcodeName - Return the name of the specified opcode enum (e.g.
/// "MOV32ri") or empty if we can't resolve it.
- virtual StringRef getOpcodeName(unsigned Opcode) const;
+ StringRef getOpcodeName(unsigned Opcode) const;
/// printRegName - Print the assembler register name.
virtual void printRegName(raw_ostream &OS, unsigned RegNo) const;
diff --git a/include/llvm/MC/MCInstrAnalysis.h b/include/llvm/MC/MCInstrAnalysis.h
index 8f3c499..acad633 100644
--- a/include/llvm/MC/MCInstrAnalysis.h
+++ b/include/llvm/MC/MCInstrAnalysis.h
@@ -33,7 +33,7 @@ public:
}
virtual bool isConditionalBranch(const MCInst &Inst) const {
- return Info->get(Inst.getOpcode()).isBranch();
+ return Info->get(Inst.getOpcode()).isConditionalBranch();
}
virtual bool isUnconditionalBranch(const MCInst &Inst) const {
diff --git a/include/llvm/MC/MCInstrDesc.h b/include/llvm/MC/MCInstrDesc.h
index aafa800..186612d 100644
--- a/include/llvm/MC/MCInstrDesc.h
+++ b/include/llvm/MC/MCInstrDesc.h
@@ -58,17 +58,17 @@ public:
/// if the operand is a register. If isLookupPtrRegClass is set, then this is
/// an index that is passed to TargetRegisterInfo::getPointerRegClass(x) to
/// get a dynamic register class.
- short RegClass;
+ int16_t RegClass;
/// Flags - These are flags from the MCOI::OperandFlags enum.
- unsigned short Flags;
+ uint8_t Flags;
+
+ /// OperandType - Information about the type of the operand.
+ uint8_t OperandType;
/// Lower 16 bits are used to specify which constraints are set. The higher 16
/// bits are used to specify the value of constraints (4 bits each).
- unsigned Constraints;
-
- /// OperandType - Information about the type of the operand.
- MCOI::OperandType OperandType;
+ uint32_t Constraints;
/// Currently no other information.
/// isLookupPtrRegClass - Set if this operand is a pointer value and it
@@ -137,11 +137,10 @@ public:
unsigned short NumDefs; // Num of args that are definitions
unsigned short SchedClass; // enum identifying instr sched class
unsigned short Size; // Number of bytes in encoding.
- const char * Name; // Name of the instruction record in td file
unsigned Flags; // Flags identifying machine instr class
uint64_t TSFlags; // Target Specific Flag values
- const unsigned *ImplicitUses; // Registers implicitly read by this instr
- const unsigned *ImplicitDefs; // Registers implicitly defined by this instr
+ const uint16_t *ImplicitUses; // Registers implicitly read by this instr
+ const uint16_t *ImplicitDefs; // Registers implicitly defined by this instr
const MCOperandInfo *OpInfo; // 'NumOperands' entries about operands
/// getOperandConstraint - Returns the value of the specific constraint if
@@ -161,12 +160,6 @@ public:
return Opcode;
}
- /// getName - Return the name of the record in the .td file for this
- /// instruction, for example "ADD8ri".
- const char *getName() const {
- return Name;
- }
-
/// getNumOperands - Return the number of declared MachineOperands for this
/// MachineInstruction. Note that variadic (isVariadic() returns true)
/// instructions may have additional operands at the end of the list, and note
@@ -184,6 +177,10 @@ public:
return NumDefs;
}
+ /// getFlags - Return flags of this instruction.
+ ///
+ unsigned getFlags() const { return Flags; }
+
/// isVariadic - Return true if this instruction can have a variable number of
/// operands. In this case, the variable operands will be after the normal
/// operands but before the implicit definitions and uses (if any are
@@ -198,84 +195,6 @@ public:
return Flags & (1 << MCID::HasOptionalDef);
}
- /// getImplicitUses - Return a list of registers that are potentially
- /// read by any instance of this machine instruction. For example, on X86,
- /// the "adc" instruction adds two register operands and adds the carry bit in
- /// from the flags register. In this case, the instruction is marked as
- /// implicitly reading the flags. Likewise, the variable shift instruction on
- /// X86 is marked as implicitly reading the 'CL' register, which it always
- /// does.
- ///
- /// This method returns null if the instruction has no implicit uses.
- const unsigned *getImplicitUses() const {
- return ImplicitUses;
- }
-
- /// getNumImplicitUses - Return the number of implicit uses this instruction
- /// has.
- unsigned getNumImplicitUses() const {
- if (ImplicitUses == 0) return 0;
- unsigned i = 0;
- for (; ImplicitUses[i]; ++i) /*empty*/;
- return i;
- }
-
- /// getImplicitDefs - Return a list of registers that are potentially
- /// written by any instance of this machine instruction. For example, on X86,
- /// many instructions implicitly set the flags register. In this case, they
- /// are marked as setting the FLAGS. Likewise, many instructions always
- /// deposit their result in a physical register. For example, the X86 divide
- /// instruction always deposits the quotient and remainder in the EAX/EDX
- /// registers. For that instruction, this will return a list containing the
- /// EAX/EDX/EFLAGS registers.
- ///
- /// This method returns null if the instruction has no implicit defs.
- const unsigned *getImplicitDefs() const {
- return ImplicitDefs;
- }
-
- /// getNumImplicitDefs - Return the number of implicit defs this instruction
- /// has.
- unsigned getNumImplicitDefs() const {
- if (ImplicitDefs == 0) return 0;
- unsigned i = 0;
- for (; ImplicitDefs[i]; ++i) /*empty*/;
- return i;
- }
-
- /// hasImplicitUseOfPhysReg - Return true if this instruction implicitly
- /// uses the specified physical register.
- bool hasImplicitUseOfPhysReg(unsigned Reg) const {
- if (const unsigned *ImpUses = ImplicitUses)
- for (; *ImpUses; ++ImpUses)
- if (*ImpUses == Reg) return true;
- return false;
- }
-
- /// hasImplicitDefOfPhysReg - Return true if this instruction implicitly
- /// defines the specified physical register.
- bool hasImplicitDefOfPhysReg(unsigned Reg) const {
- if (const unsigned *ImpDefs = ImplicitDefs)
- for (; *ImpDefs; ++ImpDefs)
- if (*ImpDefs == Reg) return true;
- return false;
- }
-
- /// getSchedClass - Return the scheduling class for this instruction. The
- /// scheduling class is an index into the InstrItineraryData table. This
- /// returns zero if there is no known scheduling information for the
- /// instruction.
- ///
- unsigned getSchedClass() const {
- return SchedClass;
- }
-
- /// getSize - Return the number of bytes in the encoding of this instruction,
- /// or zero if the encoding size cannot be known from the opcode.
- unsigned getSize() const {
- return Size;
- }
-
/// isPseudo - Return true if this is a pseudo instruction that doesn't
/// correspond to a real machine instruction.
///
@@ -298,18 +217,6 @@ public:
return Flags & (1 << MCID::Barrier);
}
- /// findFirstPredOperandIdx() - Find the index of the first operand in the
- /// operand list that is used to represent the predicate. It returns -1 if
- /// none is found.
- int findFirstPredOperandIdx() const {
- if (isPredicable()) {
- for (unsigned i = 0, e = getNumOperands(); i != e; ++i)
- if (OpInfo[i].isPredicate())
- return i;
- }
- return -1;
- }
-
/// isTerminator - Returns true if this instruction part of the terminator for
/// a basic block. Typically this is things like return and branch
/// instructions.
@@ -530,6 +437,97 @@ public:
bool hasExtraDefRegAllocReq() const {
return Flags & (1 << MCID::ExtraDefRegAllocReq);
}
+
+
+ /// getImplicitUses - Return a list of registers that are potentially
+ /// read by any instance of this machine instruction. For example, on X86,
+ /// the "adc" instruction adds two register operands and adds the carry bit in
+ /// from the flags register. In this case, the instruction is marked as
+ /// implicitly reading the flags. Likewise, the variable shift instruction on
+ /// X86 is marked as implicitly reading the 'CL' register, which it always
+ /// does.
+ ///
+ /// This method returns null if the instruction has no implicit uses.
+ const uint16_t *getImplicitUses() const {
+ return ImplicitUses;
+ }
+
+ /// getNumImplicitUses - Return the number of implicit uses this instruction
+ /// has.
+ unsigned getNumImplicitUses() const {
+ if (ImplicitUses == 0) return 0;
+ unsigned i = 0;
+ for (; ImplicitUses[i]; ++i) /*empty*/;
+ return i;
+ }
+
+ /// getImplicitDefs - Return a list of registers that are potentially
+ /// written by any instance of this machine instruction. For example, on X86,
+ /// many instructions implicitly set the flags register. In this case, they
+ /// are marked as setting the FLAGS. Likewise, many instructions always
+ /// deposit their result in a physical register. For example, the X86 divide
+ /// instruction always deposits the quotient and remainder in the EAX/EDX
+ /// registers. For that instruction, this will return a list containing the
+ /// EAX/EDX/EFLAGS registers.
+ ///
+ /// This method returns null if the instruction has no implicit defs.
+ const uint16_t *getImplicitDefs() const {
+ return ImplicitDefs;
+ }
+
+ /// getNumImplicitDefs - Return the number of implicit defs this instruction
+ /// has.
+ unsigned getNumImplicitDefs() const {
+ if (ImplicitDefs == 0) return 0;
+ unsigned i = 0;
+ for (; ImplicitDefs[i]; ++i) /*empty*/;
+ return i;
+ }
+
+ /// hasImplicitUseOfPhysReg - Return true if this instruction implicitly
+ /// uses the specified physical register.
+ bool hasImplicitUseOfPhysReg(unsigned Reg) const {
+ if (const uint16_t *ImpUses = ImplicitUses)
+ for (; *ImpUses; ++ImpUses)
+ if (*ImpUses == Reg) return true;
+ return false;
+ }
+
+ /// hasImplicitDefOfPhysReg - Return true if this instruction implicitly
+ /// defines the specified physical register.
+ bool hasImplicitDefOfPhysReg(unsigned Reg) const {
+ if (const uint16_t *ImpDefs = ImplicitDefs)
+ for (; *ImpDefs; ++ImpDefs)
+ if (*ImpDefs == Reg) return true;
+ return false;
+ }
+
+ /// getSchedClass - Return the scheduling class for this instruction. The
+ /// scheduling class is an index into the InstrItineraryData table. This
+ /// returns zero if there is no known scheduling information for the
+ /// instruction.
+ ///
+ unsigned getSchedClass() const {
+ return SchedClass;
+ }
+
+ /// getSize - Return the number of bytes in the encoding of this instruction,
+ /// or zero if the encoding size cannot be known from the opcode.
+ unsigned getSize() const {
+ return Size;
+ }
+
+ /// findFirstPredOperandIdx() - Find the index of the first operand in the
+ /// operand list that is used to represent the predicate. It returns -1 if
+ /// none is found.
+ int findFirstPredOperandIdx() const {
+ if (isPredicable()) {
+ for (unsigned i = 0, e = getNumOperands(); i != e; ++i)
+ if (OpInfo[i].isPredicate())
+ return i;
+ }
+ return -1;
+ }
};
} // end namespace llvm
diff --git a/include/llvm/MC/MCInstrInfo.h b/include/llvm/MC/MCInstrInfo.h
index a63e5fa..1d3a36c 100644
--- a/include/llvm/MC/MCInstrInfo.h
+++ b/include/llvm/MC/MCInstrInfo.h
@@ -24,14 +24,19 @@ namespace llvm {
/// MCInstrInfo - Interface to description of machine instruction set
///
class MCInstrInfo {
- const MCInstrDesc *Desc; // Raw array to allow static init'n
- unsigned NumOpcodes; // Number of entries in the desc array
+ const MCInstrDesc *Desc; // Raw array to allow static init'n
+ const unsigned *InstrNameIndices; // Array for name indices in InstrNameData
+ const char *InstrNameData; // Instruction name string pool
+ unsigned NumOpcodes; // Number of entries in the desc array
public:
/// InitMCInstrInfo - Initialize MCInstrInfo, called by TableGen
/// auto-generated routines. *DO NOT USE*.
- void InitMCInstrInfo(const MCInstrDesc *D, unsigned NO) {
+ void InitMCInstrInfo(const MCInstrDesc *D, const unsigned *NI, const char *ND,
+ unsigned NO) {
Desc = D;
+ InstrNameIndices = NI;
+ InstrNameData = ND;
NumOpcodes = NO;
}
@@ -44,6 +49,12 @@ public:
assert(Opcode < NumOpcodes && "Invalid opcode!");
return Desc[Opcode];
}
+
+ /// getName - Returns the name for the instructions with the given opcode.
+ const char *getName(unsigned Opcode) const {
+ assert(Opcode < NumOpcodes && "Invalid opcode!");
+ return &InstrNameData[InstrNameIndices[Opcode]];
+ }
};
} // End llvm namespace
diff --git a/include/llvm/MC/MCObjectFileInfo.h b/include/llvm/MC/MCObjectFileInfo.h
index 060d508..aea4b41 100644
--- a/include/llvm/MC/MCObjectFileInfo.h
+++ b/include/llvm/MC/MCObjectFileInfo.h
@@ -14,15 +14,14 @@
#ifndef LLVM_MC_MCBJECTFILEINFO_H
#define LLVM_MC_MCBJECTFILEINFO_H
-#include "llvm/MC/MCCodeGenInfo.h"
-#include "llvm/ADT/StringRef.h"
-#include "llvm/MC/SectionKind.h"
+#include "llvm/Support/CodeGen.h"
namespace llvm {
-class MCContext;
-class MCSection;
-class Triple;
-
+ class MCContext;
+ class MCSection;
+ class StringRef;
+ class Triple;
+
class MCObjectFileInfo {
protected:
/// CommDirectiveSupportsAlignment - True if .comm supports alignment. This
@@ -47,6 +46,9 @@ protected:
unsigned FDEEncoding;
unsigned FDECFIEncoding;
unsigned TTypeEncoding;
+ // Section flags for eh_frame
+ unsigned EHSectionType;
+ unsigned EHSectionFlags;
/// TextSection - Section directive for standard text.
///
@@ -82,13 +84,20 @@ protected:
/// this is the section to emit them into.
const MCSection *CompactUnwindSection;
+ /// DwarfAccelNamesSection, DwarfAccelObjCSection
+ /// If we use the DWARF accelerated hash tables then we want toe emit these
+ /// sections.
+ const MCSection *DwarfAccelNamesSection;
+ const MCSection *DwarfAccelObjCSection;
+ const MCSection *DwarfAccelNamespaceSection;
+ const MCSection *DwarfAccelTypesSection;
+
// Dwarf sections for debug info. If a target supports debug info, these must
// be set.
const MCSection *DwarfAbbrevSection;
const MCSection *DwarfInfoSection;
const MCSection *DwarfLineSection;
const MCSection *DwarfFrameSection;
- const MCSection *DwarfPubNamesSection;
const MCSection *DwarfPubTypesSection;
const MCSection *DwarfDebugInlineSection;
const MCSection *DwarfStrSection;
@@ -102,7 +111,7 @@ protected:
const MCSection *TLSExtraDataSection;
/// TLSDataSection - Section directive for Thread Local data.
- /// ELF and MachO only.
+ /// ELF, MachO and COFF.
const MCSection *TLSDataSection; // Defaults to ".tdata".
/// TLSBSSSection - Section directive for Thread Local uninitialized data.
@@ -156,7 +165,7 @@ protected:
const MCSection *DrectveSection;
const MCSection *PDataSection;
const MCSection *XDataSection;
-
+
public:
void InitMCObjectFileInfo(StringRef TT, Reloc::Model RM, CodeModel::Model CM,
MCContext &ctx);
@@ -181,17 +190,26 @@ public:
const MCSection *getTextSection() const { return TextSection; }
const MCSection *getDataSection() const { return DataSection; }
const MCSection *getBSSSection() const { return BSSSection; }
- const MCSection *getStaticCtorSection() const { return StaticCtorSection; }
- const MCSection *getStaticDtorSection() const { return StaticDtorSection; }
const MCSection *getLSDASection() const { return LSDASection; }
const MCSection *getCompactUnwindSection() const{
return CompactUnwindSection;
}
+ const MCSection *getDwarfAccelNamesSection() const {
+ return DwarfAccelNamesSection;
+ }
+ const MCSection *getDwarfAccelObjCSection() const {
+ return DwarfAccelObjCSection;
+ }
+ const MCSection *getDwarfAccelNamespaceSection() const {
+ return DwarfAccelNamespaceSection;
+ }
+ const MCSection *getDwarfAccelTypesSection() const {
+ return DwarfAccelTypesSection;
+ }
const MCSection *getDwarfAbbrevSection() const { return DwarfAbbrevSection; }
const MCSection *getDwarfInfoSection() const { return DwarfInfoSection; }
const MCSection *getDwarfLineSection() const { return DwarfLineSection; }
const MCSection *getDwarfFrameSection() const { return DwarfFrameSection; }
- const MCSection *getDwarfPubNamesSection() const{return DwarfPubNamesSection;}
const MCSection *getDwarfPubTypesSection() const{return DwarfPubTypesSection;}
const MCSection *getDwarfDebugInlineSection() const {
return DwarfDebugInlineSection;
diff --git a/include/llvm/MC/MCObjectStreamer.h b/include/llvm/MC/MCObjectStreamer.h
index f897e64..a69075d 100644
--- a/include/llvm/MC/MCObjectStreamer.h
+++ b/include/llvm/MC/MCObjectStreamer.h
@@ -34,6 +34,8 @@ class MCObjectStreamer : public MCStreamer {
MCSectionData *CurSectionData;
virtual void EmitInstToData(const MCInst &Inst) = 0;
+ virtual void EmitCFIStartProcImpl(MCDwarfFrameInfo &Frame);
+ virtual void EmitCFIEndProcImpl(MCDwarfFrameInfo &Frame);
protected:
MCObjectStreamer(MCContext &Context, MCAsmBackend &TAB,
@@ -70,14 +72,15 @@ public:
virtual void ChangeSection(const MCSection *Section);
virtual void EmitInstruction(const MCInst &Inst);
virtual void EmitInstToFragment(const MCInst &Inst);
- virtual void EmitValueToOffset(const MCExpr *Offset, unsigned char Value);
+ virtual bool EmitValueToOffset(const MCExpr *Offset, unsigned char Value);
virtual void EmitDwarfAdvanceLineAddr(int64_t LineDelta,
const MCSymbol *LastLabel,
const MCSymbol *Label,
unsigned PointerSize);
virtual void EmitDwarfAdvanceFrameAddr(const MCSymbol *LastLabel,
const MCSymbol *Label);
- virtual void Finish();
+ virtual void EmitGPRel32Value(const MCExpr *Value);
+ virtual void FinishImpl();
/// @}
};
diff --git a/include/llvm/MC/MCObjectWriter.h b/include/llvm/MC/MCObjectWriter.h
index 782d844..6e44e6ce 100644
--- a/include/llvm/MC/MCObjectWriter.h
+++ b/include/llvm/MC/MCObjectWriter.h
@@ -10,7 +10,6 @@
#ifndef LLVM_MC_MCOBJECTWRITER_H
#define LLVM_MC_MCOBJECTWRITER_H
-#include "llvm/ADT/Triple.h"
#include "llvm/Support/raw_ostream.h"
#include "llvm/Support/DataTypes.h"
#include <cassert>
@@ -20,11 +19,9 @@ class MCAsmLayout;
class MCAssembler;
class MCFixup;
class MCFragment;
-class MCSymbol;
class MCSymbolData;
class MCSymbolRefExpr;
class MCValue;
-class raw_ostream;
/// MCObjectWriter - Defines the object file and target independent interfaces
/// used by the assembler backend to write native file format object files.
@@ -188,11 +185,10 @@ 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);
+ static void EncodeULEB128(uint64_t Value, raw_ostream &OS,
+ unsigned Padding = 0);
};
-MCObjectWriter *createWinCOFFObjectWriter(raw_ostream &OS, bool is64Bit);
-
} // End llvm namespace
#endif
diff --git a/include/llvm/MC/MCParser/MCAsmLexer.h b/include/llvm/MC/MCParser/MCAsmLexer.h
index 9bbb755..ac04483 100644
--- a/include/llvm/MC/MCParser/MCAsmLexer.h
+++ b/include/llvm/MC/MCParser/MCAsmLexer.h
@@ -71,6 +71,7 @@ public:
bool isNot(TokenKind K) const { return Kind != K; }
SMLoc getLoc() const;
+ SMLoc getEndLoc() const;
/// getStringContents - Get the contents of a string token (without quotes).
StringRef getStringContents() const {
diff --git a/include/llvm/MC/MCParser/MCAsmParser.h b/include/llvm/MC/MCParser/MCAsmParser.h
index 6ff1753..793c709 100644
--- a/include/llvm/MC/MCParser/MCAsmParser.h
+++ b/include/llvm/MC/MCParser/MCAsmParser.h
@@ -11,6 +11,7 @@
#define LLVM_MC_MCASMPARSER_H
#include "llvm/Support/DataTypes.h"
+#include "llvm/ADT/ArrayRef.h"
namespace llvm {
class AsmToken;
@@ -22,6 +23,7 @@ class MCExpr;
class MCStreamer;
class MCTargetAsmParser;
class SMLoc;
+class SMRange;
class SourceMgr;
class StringRef;
class Twine;
@@ -62,6 +64,9 @@ public:
MCTargetAsmParser &getTargetParser() const { return *TargetParser; }
void setTargetParser(MCTargetAsmParser &P);
+ virtual unsigned getAssemblerDialect() { return 0;}
+ virtual void setAssemblerDialect(unsigned i) { }
+
bool getShowParsedOperands() const { return ShowParsedOperands; }
void setShowParsedOperands(bool Value) { ShowParsedOperands = Value; }
@@ -72,14 +77,16 @@ public:
/// Msg.
///
/// \return The return value is true, if warnings are fatal.
- virtual bool Warning(SMLoc L, const Twine &Msg) = 0;
+ virtual bool Warning(SMLoc L, const Twine &Msg,
+ ArrayRef<SMRange> Ranges = ArrayRef<SMRange>()) = 0;
/// Error - Emit an error at the location \arg L, with the message \arg
/// Msg.
///
/// \return The return value is always true, as an idiomatic convenience to
/// clients.
- virtual bool Error(SMLoc L, const Twine &Msg) = 0;
+ virtual bool Error(SMLoc L, const Twine &Msg,
+ ArrayRef<SMRange> Ranges = ArrayRef<SMRange>()) = 0;
/// Lex - Get the next AsmToken in the stream, possibly handling file
/// inclusion first.
@@ -89,7 +96,8 @@ public:
const AsmToken &getTok();
/// \brief Report an error at the current lexer location.
- bool TokError(const Twine &Msg);
+ bool TokError(const Twine &Msg,
+ ArrayRef<SMRange> Ranges = ArrayRef<SMRange>());
/// ParseIdentifier - Parse an identifier or string (as a quoted identifier)
/// and set \arg Res to the identifier contents.
diff --git a/include/llvm/MC/MCRegisterInfo.h b/include/llvm/MC/MCRegisterInfo.h
index ada5ae8..27acf2f 100644
--- a/include/llvm/MC/MCRegisterInfo.h
+++ b/include/llvm/MC/MCRegisterInfo.h
@@ -17,6 +17,7 @@
#define LLVM_MC_MCREGISTERINFO_H
#include "llvm/ADT/DenseMap.h"
+#include "llvm/Support/ErrorHandling.h"
#include <cassert>
namespace llvm {
@@ -24,28 +25,18 @@ namespace llvm {
/// MCRegisterClass - Base class of TargetRegisterClass.
class MCRegisterClass {
public:
- typedef const unsigned* iterator;
- typedef const unsigned* const_iterator;
-private:
- unsigned ID;
+ typedef const uint16_t* iterator;
+ typedef const uint16_t* const_iterator;
+
const char *Name;
- const unsigned RegSize, Alignment; // Size & Alignment of register in bytes
- const int CopyCost;
+ const iterator RegsBegin;
+ const uint8_t *const RegSet;
+ const uint16_t RegsSize;
+ const uint16_t RegSetSize;
+ const uint16_t ID;
+ const uint16_t RegSize, Alignment; // Size & Alignment of register in bytes
+ const int8_t CopyCost;
const bool Allocatable;
- const iterator RegsBegin, RegsEnd;
- const unsigned char *const RegSet;
- const unsigned RegSetSize;
-public:
- MCRegisterClass(unsigned id, const char *name,
- unsigned RS, unsigned Al, int CC, bool Allocable,
- iterator RB, iterator RE, const unsigned char *Bits,
- unsigned NumBytes)
- : ID(id), Name(name), RegSize(RS), Alignment(Al), CopyCost(CC),
- Allocatable(Allocable), RegsBegin(RB), RegsEnd(RE), RegSet(Bits),
- RegSetSize(NumBytes) {
- for (iterator i = RegsBegin; i != RegsEnd; ++i)
- assert(contains(*i) && "Bit field corrupted.");
- }
/// getID() - Return the register class ID number.
///
@@ -58,11 +49,11 @@ public:
/// begin/end - Return all of the registers in this class.
///
iterator begin() const { return RegsBegin; }
- iterator end() const { return RegsEnd; }
+ iterator end() const { return RegsBegin + RegsSize; }
/// getNumRegs - Return the number of registers in this class.
///
- unsigned getNumRegs() const { return (unsigned)(RegsEnd-RegsBegin); }
+ unsigned getNumRegs() const { return RegsSize; }
/// getRegister - Return the specified register in the class.
///
@@ -115,10 +106,10 @@ public:
/// of AX.
///
struct MCRegisterDesc {
- const char *Name; // Printable name for the reg (for debugging)
- const unsigned *Overlaps; // Overlapping registers, described above
- const unsigned *SubRegs; // Sub-register set, described above
- const unsigned *SuperRegs; // Super-register set, described above
+ 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
};
/// MCRegisterInfo base class - We assume that the target defines a static
@@ -136,50 +127,82 @@ struct MCRegisterDesc {
class MCRegisterInfo {
public:
typedef const MCRegisterClass *regclass_iterator;
+
+ /// DwarfLLVMRegPair - Emitted by tablegen so Dwarf<->LLVM reg mappings can be
+ /// performed with a binary search.
+ struct DwarfLLVMRegPair {
+ unsigned FromReg;
+ unsigned ToReg;
+
+ bool operator<(DwarfLLVMRegPair RHS) const { return FromReg < RHS.FromReg; }
+ };
private:
const MCRegisterDesc *Desc; // Pointer to the descriptor array
unsigned NumRegs; // Number of entries in the array
unsigned RAReg; // Return address register
const MCRegisterClass *Classes; // Pointer to the regclass array
unsigned NumClasses; // Number of entries in the array
- DenseMap<unsigned, int> L2DwarfRegs; // LLVM to Dwarf regs mapping
- DenseMap<unsigned, int> EHL2DwarfRegs; // LLVM to Dwarf regs mapping EH
- DenseMap<unsigned, unsigned> Dwarf2LRegs; // Dwarf to LLVM regs mapping
- DenseMap<unsigned, unsigned> EHDwarf2LRegs; // Dwarf to LLVM regs mapping EH
+ const uint16_t *RegLists; // Pointer to the reglists array
+ const uint16_t *SubRegIndices; // Pointer to the subreg lookup
+ // array.
+ unsigned NumSubRegIndices; // Number of subreg indices.
+
+ unsigned L2DwarfRegsSize;
+ unsigned EHL2DwarfRegsSize;
+ unsigned Dwarf2LRegsSize;
+ unsigned EHDwarf2LRegsSize;
+ const DwarfLLVMRegPair *L2DwarfRegs; // LLVM to Dwarf regs mapping
+ const DwarfLLVMRegPair *EHL2DwarfRegs; // LLVM to Dwarf regs mapping EH
+ const DwarfLLVMRegPair *Dwarf2LRegs; // Dwarf to LLVM regs mapping
+ const DwarfLLVMRegPair *EHDwarf2LRegs; // Dwarf to LLVM regs mapping EH
DenseMap<unsigned, int> L2SEHRegs; // LLVM to SEH regs mapping
public:
/// 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 MCRegisterClass *C, unsigned NC,
+ const uint16_t *RL,
+ const uint16_t *SubIndices,
+ unsigned NumIndices) {
Desc = D;
NumRegs = NR;
RAReg = RA;
Classes = C;
+ RegLists = RL;
NumClasses = NC;
+ SubRegIndices = SubIndices;
+ NumSubRegIndices = NumIndices;
}
- /// mapLLVMRegToDwarfReg - Used to initialize LLVM register to Dwarf
+ /// mapLLVMRegsToDwarfRegs - Used to initialize LLVM register to Dwarf
/// register number mapping. Called by TableGen auto-generated routines.
/// *DO NOT USE*.
- void mapLLVMRegToDwarfReg(unsigned LLVMReg, int DwarfReg, bool isEH) {
- if (isEH)
- EHL2DwarfRegs[LLVMReg] = DwarfReg;
- else
- L2DwarfRegs[LLVMReg] = DwarfReg;
+ void mapLLVMRegsToDwarfRegs(const DwarfLLVMRegPair *Map, unsigned Size,
+ bool isEH) {
+ if (isEH) {
+ EHL2DwarfRegs = Map;
+ EHL2DwarfRegsSize = Size;
+ } else {
+ L2DwarfRegs = Map;
+ L2DwarfRegsSize = Size;
+ }
}
-
- /// mapDwarfRegToLLVMReg - Used to initialize Dwarf register to LLVM
+
+ /// mapDwarfRegsToLLVMRegs - Used to initialize Dwarf register to LLVM
/// register number mapping. Called by TableGen auto-generated routines.
/// *DO NOT USE*.
- void mapDwarfRegToLLVMReg(unsigned DwarfReg, unsigned LLVMReg, bool isEH) {
- if (isEH)
- EHDwarf2LRegs[DwarfReg] = LLVMReg;
- else
- Dwarf2LRegs[DwarfReg] = LLVMReg;
+ void mapDwarfRegsToLLVMRegs(const DwarfLLVMRegPair *Map, unsigned Size,
+ bool isEH) {
+ if (isEH) {
+ EHDwarf2LRegs = Map;
+ EHDwarf2LRegsSize = Size;
+ } else {
+ Dwarf2LRegs = Map;
+ Dwarf2LRegsSize = Size;
+ }
}
-
+
/// mapLLVMRegToSEHReg - Used to initialize LLVM register to SEH register
/// number mapping. By default the SEH register number is just the same
/// as the LLVM register number.
@@ -212,9 +235,9 @@ public:
/// register, or a null list of there are none. The list returned is zero
/// terminated.
///
- const unsigned *getAliasSet(unsigned RegNo) const {
+ const uint16_t *getAliasSet(unsigned RegNo) const {
// The Overlaps set always begins with Reg itself.
- return get(RegNo).Overlaps + 1;
+ return RegLists + get(RegNo).Overlaps + 1;
}
/// getOverlaps - Return a list of registers that overlap Reg, including
@@ -222,8 +245,8 @@ public:
/// list.
/// These are exactly the registers in { x | regsOverlap(x, Reg) }.
///
- const unsigned *getOverlaps(unsigned RegNo) const {
- return get(RegNo).Overlaps;
+ const uint16_t *getOverlaps(unsigned RegNo) const {
+ return RegLists + get(RegNo).Overlaps;
}
/// getSubRegisters - Return the list of registers that are sub-registers of
@@ -231,8 +254,35 @@ public:
/// 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 unsigned *getSubRegisters(unsigned RegNo) const {
- return get(RegNo).SubRegs;
+ 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);
+ }
+
+ /// 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;
+ }
+
+ /// 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
@@ -240,8 +290,8 @@ public:
/// 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 unsigned *getSuperRegisters(unsigned RegNo) const {
- return get(RegNo).SuperRegs;
+ const uint16_t *getSuperRegisters(unsigned RegNo) const {
+ return RegLists + get(RegNo).SuperRegs;
}
/// getName - Return the human-readable symbolic target-specific name for the
@@ -261,22 +311,26 @@ public:
/// parameter allows targets to use different numberings for EH info and
/// debugging info.
int getDwarfRegNum(unsigned RegNum, bool isEH) const {
- const DenseMap<unsigned, int> &M = isEH ? EHL2DwarfRegs : L2DwarfRegs;
- const DenseMap<unsigned, int>::const_iterator I = M.find(RegNum);
- if (I == M.end()) return -1;
- return I->second;
+ 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;
}
/// getLLVMRegNum - Map a dwarf register back to a target register.
///
int getLLVMRegNum(unsigned RegNum, bool isEH) const {
- const DenseMap<unsigned, unsigned> &M = isEH ? EHDwarf2LRegs : Dwarf2LRegs;
- const DenseMap<unsigned, unsigned>::const_iterator I = M.find(RegNum);
- if (I == M.end()) {
- assert(0 && "Invalid RegNum");
- return -1;
- }
- return I->second;
+ 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;
}
/// getSEHRegNum - Map a target register to an equivalent SEH register
@@ -301,7 +355,7 @@ public:
return Classes[i];
}
};
-
+
} // End llvm namespace
#endif
diff --git a/include/llvm/MC/MCSection.h b/include/llvm/MC/MCSection.h
index 5700817..7da6534 100644
--- a/include/llvm/MC/MCSection.h
+++ b/include/llvm/MC/MCSection.h
@@ -14,12 +14,10 @@
#ifndef LLVM_MC_MCSECTION_H
#define LLVM_MC_MCSECTION_H
-#include "llvm/ADT/StringRef.h"
#include "llvm/MC/SectionKind.h"
#include "llvm/Support/Casting.h"
namespace llvm {
- class MCContext;
class MCAsmInfo;
class raw_ostream;
diff --git a/include/llvm/MC/MCSectionCOFF.h b/include/llvm/MC/MCSectionCOFF.h
index b154cf5..7eacde5 100644
--- a/include/llvm/MC/MCSectionCOFF.h
+++ b/include/llvm/MC/MCSectionCOFF.h
@@ -15,8 +15,8 @@
#define LLVM_MC_MCSECTIONCOFF_H
#include "llvm/MC/MCSection.h"
-
#include "llvm/Support/COFF.h"
+#include "llvm/ADT/StringRef.h"
namespace llvm {
diff --git a/include/llvm/MC/MCSectionELF.h b/include/llvm/MC/MCSectionELF.h
index c82de71..7321ca8 100644
--- a/include/llvm/MC/MCSectionELF.h
+++ b/include/llvm/MC/MCSectionELF.h
@@ -16,6 +16,7 @@
#include "llvm/MC/MCSection.h"
#include "llvm/Support/ELF.h"
+#include "llvm/ADT/StringRef.h"
namespace llvm {
diff --git a/include/llvm/MC/MCSectionMachO.h b/include/llvm/MC/MCSectionMachO.h
index bdb17e9..15eb4f4 100644
--- a/include/llvm/MC/MCSectionMachO.h
+++ b/include/llvm/MC/MCSectionMachO.h
@@ -15,6 +15,7 @@
#define LLVM_MC_MCSECTIONMACHO_H
#include "llvm/MC/MCSection.h"
+#include "llvm/ADT/StringRef.h"
namespace llvm {
diff --git a/include/llvm/MC/MCStreamer.h b/include/llvm/MC/MCStreamer.h
index 451efbf..2595600 100644
--- a/include/llvm/MC/MCStreamer.h
+++ b/include/llvm/MC/MCStreamer.h
@@ -23,7 +23,6 @@
namespace llvm {
class MCAsmBackend;
- class MCAsmInfo;
class MCCodeEmitter;
class MCContext;
class MCExpr;
@@ -32,7 +31,6 @@ namespace llvm {
class MCSection;
class MCSymbol;
class StringRef;
- class TargetLoweringObjectFile;
class Twine;
class raw_ostream;
class formatted_raw_ostream;
@@ -94,6 +92,10 @@ namespace llvm {
const MCExpr *ForceExpAbs(const MCExpr* Expr);
+ void RecordProcStart(MCDwarfFrameInfo &Frame);
+ virtual void EmitCFIStartProcImpl(MCDwarfFrameInfo &Frame);
+ void RecordProcEnd(MCDwarfFrameInfo &Frame);
+ virtual void EmitCFIEndProcImpl(MCDwarfFrameInfo &CurFrame);
void EmitFrames(bool usingCFI);
MCWin64EHUnwindInfo *getCurrentW64UnwindInfo(){return CurrentW64UnwindInfo;}
@@ -334,6 +336,11 @@ namespace llvm {
/// EndCOFFSymbolDef - Marks the end of the symbol definition.
virtual void EndCOFFSymbolDef() = 0;
+ /// EmitCOFFSecRel32 - Emits a COFF section relative relocation.
+ ///
+ /// @param Symbol - Symbol the section relative realocation should point to.
+ virtual void EmitCOFFSecRel32(MCSymbol const *Symbol);
+
/// EmitELFSize - Emit an ELF .size directive.
///
/// This corresponds to an assembler statement such as:
@@ -420,7 +427,8 @@ namespace llvm {
/// EmitULEB128Value - Special case of EmitULEB128Value that avoids the
/// client having to pass in a MCExpr for constant integers.
- void EmitULEB128IntValue(uint64_t Value, unsigned AddrSpace = 0);
+ void EmitULEB128IntValue(uint64_t Value, unsigned AddrSpace = 0,
+ unsigned Padding = 0);
/// EmitSLEB128Value - Special case of EmitSLEB128Value that avoids the
/// client having to pass in a MCExpr for constant integers.
@@ -431,6 +439,13 @@ namespace llvm {
void EmitSymbolValue(const MCSymbol *Sym, unsigned Size,
unsigned AddrSpace = 0);
+ /// EmitGPRel64Value - Emit the expression @p Value into the output as a
+ /// gprel64 (64-bit GP relative) value.
+ ///
+ /// This is used to implement assembler directives such as .gpdword on
+ /// targets that support them.
+ virtual void EmitGPRel64Value(const MCExpr *Value);
+
/// EmitGPRel32Value - Emit the expression @p Value into the output as a
/// gprel32 (32-bit GP relative) value.
///
@@ -493,7 +508,8 @@ namespace llvm {
/// @param Offset - The offset to reach. This may be an expression, but the
/// expression must be associated with the current section.
/// @param Value - The value to use when filling bytes.
- virtual void EmitValueToOffset(const MCExpr *Offset,
+ /// @return false on success, true if the offset was invalid.
+ virtual bool EmitValueToOffset(const MCExpr *Offset,
unsigned char Value = 0) = 0;
/// @}
@@ -505,7 +521,8 @@ namespace llvm {
/// EmitDwarfFileDirective - Associate a filename with a specified logical
/// file number. This implements the DWARF2 '.file 4 "foo.c"' assembler
/// directive.
- virtual bool EmitDwarfFileDirective(unsigned FileNo,StringRef Filename);
+ virtual bool EmitDwarfFileDirective(unsigned FileNo, StringRef Directory,
+ StringRef Filename);
/// EmitDwarfLocDirective - This implements the DWARF2
// '.loc fileno lineno ...' assembler directive.
@@ -529,8 +546,8 @@ namespace llvm {
virtual void EmitCompactUnwindEncoding(uint32_t CompactUnwindEncoding);
virtual void EmitCFISections(bool EH, bool Debug);
- virtual void EmitCFIStartProc();
- virtual void EmitCFIEndProc();
+ void EmitCFIStartProc();
+ void EmitCFIEndProc();
virtual void EmitCFIDefCfa(int64_t Register, int64_t Offset);
virtual void EmitCFIDefCfaOffset(int64_t Offset);
virtual void EmitCFIDefCfaRegister(int64_t Register);
@@ -540,8 +557,11 @@ namespace llvm {
virtual void EmitCFIRememberState();
virtual void EmitCFIRestoreState();
virtual void EmitCFISameValue(int64_t Register);
+ virtual void EmitCFIRestore(int64_t Register);
virtual void EmitCFIRelOffset(int64_t Register, int64_t Offset);
virtual void EmitCFIAdjustCfaOffset(int64_t Adjustment);
+ virtual void EmitCFIEscape(StringRef Values);
+ virtual void EmitCFISignalFrame();
virtual void EmitWin64EHStartProc(const MCSymbol *Symbol);
virtual void EmitWin64EHEndProc();
@@ -581,8 +601,10 @@ namespace llvm {
virtual void EmitRegSave(const SmallVectorImpl<unsigned> &RegList,
bool isVector);
+ /// FinishImpl - Streamer specific finalization.
+ virtual void FinishImpl() = 0;
/// Finish - Finish emission of machine code.
- virtual void Finish() = 0;
+ void Finish();
};
/// createNullStreamer - Create a dummy machine code streamer, which does
@@ -613,6 +635,7 @@ namespace llvm {
bool isVerboseAsm,
bool useLoc,
bool useCFI,
+ bool useDwarfDirectory,
MCInstPrinter *InstPrint = 0,
MCCodeEmitter *CE = 0,
MCAsmBackend *TAB = 0,
@@ -638,14 +661,8 @@ namespace llvm {
/// createELFStreamer - Create a machine code streamer which will generate
/// ELF format object files.
MCStreamer *createELFStreamer(MCContext &Ctx, MCAsmBackend &TAB,
- raw_ostream &OS, MCCodeEmitter *CE,
- bool RelaxAll, bool NoExecStack);
-
- /// createLoggingStreamer - Create a machine code streamer which just logs the
- /// API calls and then dispatches to another streamer.
- ///
- /// The new streamer takes ownership of the \arg Child.
- MCStreamer *createLoggingStreamer(MCStreamer *Child, raw_ostream &OS);
+ raw_ostream &OS, MCCodeEmitter *CE,
+ bool RelaxAll, bool NoExecStack);
/// createPureStreamer - Create a machine code streamer which will generate
/// "pure" MC object files, for use with MC-JIT and testing tools.
diff --git a/include/llvm/MC/MCWinCOFFObjectWriter.h b/include/llvm/MC/MCWinCOFFObjectWriter.h
new file mode 100644
index 0000000..7a0b1ff
--- /dev/null
+++ b/include/llvm/MC/MCWinCOFFObjectWriter.h
@@ -0,0 +1,36 @@
+//===-- llvm/MC/MCWinCOFFObjectWriter.h - Win COFF Object Writer *- C++ -*-===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_MC_MCWINCOFFOBJECTWRITER_H
+#define LLVM_MC_MCWINCOFFOBJECTWRITER_H
+
+namespace llvm {
+ class MCWinCOFFObjectTargetWriter {
+ const unsigned Machine;
+
+ protected:
+ MCWinCOFFObjectTargetWriter(unsigned Machine_);
+
+ public:
+ virtual ~MCWinCOFFObjectTargetWriter() {}
+
+ unsigned getMachine() const { return Machine; }
+ virtual unsigned getRelocType(unsigned FixupKind) const = 0;
+ };
+
+ /// \brief Construct a new Win COFF writer instance.
+ ///
+ /// \param MOTW - The target specific WinCOFF writer subclass.
+ /// \param OS - The stream to write to.
+ /// \returns The constructed object writer.
+ MCObjectWriter *createWinCOFFObjectWriter(MCWinCOFFObjectTargetWriter *MOTW,
+ raw_ostream &OS);
+} // End llvm namespace
+
+#endif
OpenPOWER on IntegriCloud