#include "llvm/ADT/StringMap.h"
#include "llvm/DebugInfo.h"
#include "llvm/MC/MCExpr.h"
+#include "llvm/MC/MCSection.h"
namespace llvm {
class ConstantFP;
class DbgVariable;
+// Data structure to hold a range for range lists.
+class RangeSpan {
+public:
+ RangeSpan(MCSymbol *S, MCSymbol *E) : Start(S), End(E) {}
+ const MCSymbol *getStart() const { return Start; }
+ const MCSymbol *getEnd() const { return End; }
+
+private:
+ const MCSymbol *Start, *End;
+};
+
+class RangeSpanList {
+private:
+ // Index for locating within the debug_range section this particular span.
+ MCSymbol *RangeSym;
+ // List of ranges.
+ SmallVector<RangeSpan, 2> Ranges;
+
+public:
+ RangeSpanList(MCSymbol *Sym) : RangeSym(Sym) {}
+ MCSymbol *getSym() const { return RangeSym; }
+ const SmallVectorImpl<RangeSpan> &getRanges() const { return Ranges; }
+ void addRange(RangeSpan Range) { Ranges.push_back(Range); }
+};
+
//===----------------------------------------------------------------------===//
/// Unit - This dwarf writer support class manages information associated
/// with a source file.
-class Unit {
+class DwarfUnit {
protected:
/// UniqueID - a numeric ID unique among all CUs in the module
unsigned UniqueID;
/// Node - MDNode for the compile unit.
DICompileUnit Node;
- /// CUDie - Compile unit debug information entry.
- const OwningPtr<DIE> CUDie;
+ /// Unit debug information entry.
+ const OwningPtr<DIE> UnitDie;
- /// Offset of the CUDie from beginning of debug info section.
+ /// Offset of the UnitDie from beginning of debug info section.
unsigned DebugInfoOffset;
/// Asm - Target of Dwarf emission.
// Holders for some common dwarf information.
DwarfDebug *DD;
- DwarfUnits *DU;
+ DwarfFile *DU;
- /// IndexTyDie - An anonymous type for index type. Owned by CUDie.
+ /// IndexTyDie - An anonymous type for index type. Owned by UnitDie.
DIE *IndexTyDie;
/// MDNodeToDieMap - Tracks the mapping of unit level debug information
/// corresponds to the MDNode mapped with the subprogram DIE.
DenseMap<DIE *, const MDNode *> ContainingTypeMap;
+ // List of range lists for a given compile unit, separate from the ranges for
+ // the CU itself.
+ SmallVector<RangeSpanList, 1> CURangeLists;
+
// DIEValueAllocator - All DIEValues are allocated through this allocator.
BumpPtrAllocator DIEValueAllocator;
// DIEIntegerOne - A preallocated DIEValue because 1 is used frequently.
DIEInteger *DIEIntegerOne;
- Unit(unsigned UID, DIE *D, DICompileUnit CU, AsmPrinter *A, DwarfDebug *DW,
- DwarfUnits *DWU);
+ /// The section this unit will be emitted in.
+ const MCSection *Section;
+
+ /// A label at the start of the non-dwo section related to this unit.
+ MCSymbol *SectionSym;
+
+ /// The start of the unit within its section.
+ MCSymbol *LabelBegin;
+
+ /// The end of the unit within its section.
+ MCSymbol *LabelEnd;
+
+ /// The label for the start of the range sets for the elements of this unit.
+ MCSymbol *LabelRange;
+
+ DwarfUnit(unsigned UID, DIE *D, DICompileUnit CU, AsmPrinter *A,
+ DwarfDebug *DW, DwarfFile *DWU);
public:
- virtual ~Unit();
+ virtual ~DwarfUnit();
+
+ /// Pass in the SectionSym even though we could recreate it in every compile
+ /// unit (type units will have actually distinct symbols once they're in
+ /// comdat sections).
+ void initSection(const MCSection *Section, MCSymbol *SectionSym) {
+ assert(!this->Section);
+ this->Section = Section;
+ this->SectionSym = SectionSym;
+ this->LabelBegin =
+ Asm->GetTempSymbol(Section->getLabelBeginName(), getUniqueID());
+ this->LabelEnd =
+ Asm->GetTempSymbol(Section->getLabelEndName(), getUniqueID());
+ this->LabelRange = Asm->GetTempSymbol("gnu_ranges", getUniqueID());
+ }
+
+ const MCSection *getSection() const {
+ assert(Section);
+ return Section;
+ }
+
+ MCSymbol *getSectionSym() const {
+ assert(Section);
+ return SectionSym;
+ }
+
+ MCSymbol *getLabelBegin() const {
+ assert(Section);
+ return LabelBegin;
+ }
+
+ MCSymbol *getLabelEnd() const {
+ assert(Section);
+ return LabelEnd;
+ }
+
+ MCSymbol *getLabelRange() const {
+ assert(Section);
+ return LabelRange;
+ }
// Accessors.
unsigned getUniqueID() const { return UniqueID; }
virtual uint16_t getLanguage() const = 0;
DICompileUnit getNode() const { return Node; }
- DIE *getCUDie() const { return CUDie.get(); }
+ DIE *getUnitDie() const { return UnitDie.get(); }
const StringMap<const DIE *> &getGlobalNames() const { return GlobalNames; }
const StringMap<const DIE *> &getGlobalTypes() const { return GlobalTypes; }
void setDebugInfoOffset(unsigned DbgInfoOff) { DebugInfoOffset = DbgInfoOff; }
/// hasContent - Return true if this compile unit has something to write out.
- bool hasContent() const { return !CUDie->getChildren().empty(); }
+ bool hasContent() const { return !UnitDie->getChildren().empty(); }
+
+ /// addRangeList - Add an address range list to the list of range lists.
+ void addRangeList(RangeSpanList Ranges) { CURangeLists.push_back(Ranges); }
+
+ /// getRangeLists - Get the vector of range lists.
+ const SmallVectorImpl<RangeSpanList> &getRangeLists() const {
+ return CURangeLists;
+ }
+ SmallVectorImpl<RangeSpanList> &getRangeLists() { return CURangeLists; }
/// getParentContextString - Get a string containing the language specific
/// context for a global name.
/// addDie - Adds or interns the DIE to the compile unit.
///
- void addDie(DIE *Buffer) { CUDie->addChild(Buffer); }
+ void addDie(DIE *Buffer) { UnitDie->addChild(Buffer); }
/// addFlag - Add a flag that is true to the DIE.
void addFlag(DIE *Die, dwarf::Attribute Attribute);
void updateAcceleratorTables(DIScope Context, DIType Ty, const DIE *TyDIE);
};
-class CompileUnit : public Unit {
+class DwarfCompileUnit : public DwarfUnit {
public:
- CompileUnit(unsigned UID, DIE *D, DICompileUnit Node, AsmPrinter *A,
- DwarfDebug *DW, DwarfUnits *DWU);
+ DwarfCompileUnit(unsigned UID, DIE *D, DICompileUnit Node, AsmPrinter *A,
+ DwarfDebug *DW, DwarfFile *DWU);
/// createGlobalVariableDIE - create global variable DIE.
void createGlobalVariableDIE(DIGlobalVariable GV);
uint16_t getLanguage() const { return getNode().getLanguage(); }
};
-class TypeUnit : public Unit {
+class DwarfTypeUnit : public DwarfUnit {
private:
uint16_t Language;
public:
- TypeUnit(unsigned UID, DIE *D, uint16_t Language, AsmPrinter *A,
- DwarfDebug *DW, DwarfUnits *DWU);
+ DwarfTypeUnit(unsigned UID, DIE *D, uint16_t Language, AsmPrinter *A,
+ DwarfDebug *DW, DwarfFile *DWU);
uint16_t getLanguage() const { return Language; }
};