Use a consistent argument order in TargetLoweringObjectFile.
[oota-llvm.git] / lib / CodeGen / AsmPrinter / DwarfUnit.h
index ed44a10cf3b1bccd362169c3d29dcfe81f907e30..61a50a79364873b4a4f368c08052d38815bb41c9 100644 (file)
@@ -22,6 +22,7 @@
 #include "llvm/ADT/StringMap.h"
 #include "llvm/DebugInfo.h"
 #include "llvm/MC/MCExpr.h"
+#include "llvm/MC/MCSection.h"
 
 namespace llvm {
 
@@ -59,13 +60,13 @@ public:
 //===----------------------------------------------------------------------===//
 /// 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;
+  DICompileUnit CUNode;
 
   /// Unit debug information entry.
   const OwningPtr<DIE> UnitDie;
@@ -117,6 +118,9 @@ protected:
   /// corresponds to the MDNode mapped with the subprogram DIE.
   DenseMap<DIE *, const MDNode *> ContainingTypeMap;
 
+  // List of ranges for a given compile unit.
+  SmallVector<RangeSpan, 1> CURanges;
+
   // List of range lists for a given compile unit, separate from the ranges for
   // the CU itself.
   SmallVector<RangeSpanList, 1> CURangeLists;
@@ -127,16 +131,95 @@ protected:
   // DIEIntegerOne - A preallocated DIEValue because 1 is used frequently.
   DIEInteger *DIEIntegerOne;
 
-  Unit(unsigned UID, DIE *D, DICompileUnit CU, AsmPrinter *A, DwarfDebug *DW,
-       DwarfFile *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;
+
+  /// Skeleton unit associated with this unit.
+  DwarfUnit *Skeleton;
+
+  DwarfUnit(unsigned UID, DIE *D, DICompileUnit CU, AsmPrinter *A,
+            DwarfDebug *DW, DwarfFile *DWU);
 
 public:
-  virtual ~Unit();
+  virtual ~DwarfUnit();
+
+  /// Set the skeleton unit associated with this unit.
+  void setSkeleton(DwarfUnit *Skel) { Skeleton = Skel; }
+
+  /// Get the skeleton unit associated with this unit.
+  DwarfUnit *getSkeleton() const { return Skeleton; }
+
+  /// 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;
+  }
+
+  /// If there's a skeleton then return the section symbol for the skeleton
+  /// unit, otherwise return the section symbol for this unit.
+  MCSymbol *getLocalSectionSym() const {
+    if (Skeleton)
+      return Skeleton->getSectionSym();
+    return getSectionSym();
+  }
+
+  MCSymbol *getSectionSym() const {
+    assert(Section);
+    return SectionSym;
+  }
+
+  /// If there's a skeleton then return the begin label for the skeleton unit,
+  /// otherwise return the local label for this unit.
+  MCSymbol *getLocalLabelBegin() const {
+    if (Skeleton)
+      return Skeleton->getLabelBegin();
+    return getLabelBegin();
+  }
+
+  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; }
+  uint16_t getLanguage() const { return CUNode.getLanguage(); }
+  DICompileUnit getCUNode() const { return CUNode; }
   DIE *getUnitDie() const { return UnitDie.get(); }
   const StringMap<const DIE *> &getGlobalNames() const { return GlobalNames; }
   const StringMap<const DIE *> &getGlobalTypes() const { return GlobalTypes; }
@@ -161,6 +244,13 @@ public:
   /// hasContent - Return true if this compile unit has something to write out.
   bool hasContent() const { return !UnitDie->getChildren().empty(); }
 
+  /// addRange - Add an address range to the list of ranges for this unit.
+  void addRange(RangeSpan Range) { CURanges.push_back(Range); }
+
+  /// getRanges - Get the list of ranges for this unit.
+  const SmallVectorImpl<RangeSpan> &getRanges() const { return CURanges; }
+  SmallVectorImpl<RangeSpan> &getRanges() { return CURanges; }
+
   /// addRangeList - Add an address range list to the list of range lists.
   void addRangeList(RangeSpanList Ranges) { CURangeLists.push_back(Ranges); }
 
@@ -264,6 +354,8 @@ public:
   /// addDIEEntry - Add a DIE attribute data and value.
   void addDIEEntry(DIE *Die, dwarf::Attribute Attribute, DIEEntry *Entry);
 
+  void addDIETypeSignature(DIE *Die, const DwarfTypeUnit &Type);
+
   /// addBlock - Add block data.
   void addBlock(DIE *Die, dwarf::Attribute Attribute, DIEBlock *Block);
 
@@ -358,14 +450,15 @@ public:
 
   /// Compute the size of a header for this unit, not including the initial
   /// length field.
-  unsigned getHeaderSize() const {
+  virtual unsigned getHeaderSize() const {
     return sizeof(int16_t) + // DWARF version number
            sizeof(int32_t) + // Offset Into Abbrev. Section
            sizeof(int8_t);   // Pointer Size (in bytes)
   }
 
   /// Emit the header for this unit, not including the initial length field.
-  void emitHeader(const MCSection *ASection, const MCSymbol *ASectionSym);
+  virtual void emitHeader(const MCSection *ASection,
+                          const MCSymbol *ASectionSym) const;
 
 protected:
   /// getOrCreateStaticMemberDIE - Create new static data member DIE.
@@ -440,10 +533,13 @@ private:
   void updateAcceleratorTables(DIScope Context, DIType Ty, const DIE *TyDIE);
 };
 
-class CompileUnit : public Unit {
+class DwarfCompileUnit : public DwarfUnit {
+  unsigned statementListIndex;
+
 public:
-  CompileUnit(unsigned UID, DIE *D, DICompileUnit Node, AsmPrinter *A,
-              DwarfDebug *DW, DwarfFile *DWU);
+  DwarfCompileUnit(unsigned UID, DIE *D, DICompileUnit Node, AsmPrinter *A,
+                   DwarfDebug *DW, DwarfFile *DWU);
+  virtual ~DwarfCompileUnit() LLVM_OVERRIDE;
 
   /// createGlobalVariableDIE - create global variable DIE.
   void createGlobalVariableDIE(DIGlobalVariable GV);
@@ -452,18 +548,40 @@ public:
   /// either DW_FORM_addr or DW_FORM_GNU_addr_index.
   void addLabelAddress(DIE *Die, dwarf::Attribute Attribute, MCSymbol *Label);
 
-  uint16_t getLanguage() const { return getNode().getLanguage(); }
+  void setStatementListIndex(unsigned statementListIndex) {
+    this->statementListIndex = statementListIndex;
+  }
+
+  void initStatementList(DIE *D) const {
+    DIE *UD = getUnitDie();
+    D->addValue(dwarf::DW_AT_stmt_list,
+                UD->getAbbrev().getData()[statementListIndex].getForm(),
+                UD->getValues()[statementListIndex]);
+  }
 };
 
-class TypeUnit : public Unit {
+class DwarfTypeUnit : public DwarfUnit {
 private:
-  uint16_t Language;
+  uint64_t TypeSignature;
+  const DIE *Ty;
 
 public:
-  TypeUnit(unsigned UID, DIE *D, uint16_t Language, AsmPrinter *A,
-           DwarfDebug *DW, DwarfFile *DWU);
+  DwarfTypeUnit(unsigned UID, DIE *D, DICompileUnit CUNode, AsmPrinter *A,
+                DwarfDebug *DW, DwarfFile *DWU);
+  virtual ~DwarfTypeUnit() LLVM_OVERRIDE;
+
+  void setTypeSignature(uint64_t Signature) { TypeSignature = Signature; }
+  uint64_t getTypeSignature() const { return TypeSignature; }
+  void setType(const DIE *Ty) { this->Ty = Ty; }
 
-  uint16_t getLanguage() const { return Language; }
+  /// Emit the header for this unit, not including the initial length field.
+  void emitHeader(const MCSection *ASection, const MCSymbol *ASectionSym) const
+      LLVM_OVERRIDE;
+  unsigned getHeaderSize() const LLVM_OVERRIDE {
+    return DwarfUnit::getHeaderSize() + sizeof(uint64_t) + // Type Signature
+           sizeof(uint32_t);                               // Type DIE Offset
+  }
+  void initSection(const MCSection *Section);
 };
 } // end llvm namespace
 #endif