• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //===--- lib/CodeGen/DIE.h - DWARF Info Entries -----------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // Data structures for DWARF info entries.
11 //
12 //===----------------------------------------------------------------------===//
13 
14 #ifndef LLVM_LIB_CODEGEN_ASMPRINTER_DIE_H
15 #define LLVM_LIB_CODEGEN_ASMPRINTER_DIE_H
16 
17 #include "llvm/ADT/FoldingSet.h"
18 #include "llvm/ADT/PointerIntPair.h"
19 #include "llvm/ADT/STLExtras.h"
20 #include "llvm/ADT/SmallVector.h"
21 #include "llvm/CodeGen/DwarfStringPoolEntry.h"
22 #include "llvm/Support/Dwarf.h"
23 
24 namespace llvm {
25 class AsmPrinter;
26 class MCExpr;
27 class MCSymbol;
28 class raw_ostream;
29 class DwarfTypeUnit;
30 
31 //===--------------------------------------------------------------------===//
32 /// DIEAbbrevData - Dwarf abbreviation data, describes one attribute of a
33 /// Dwarf abbreviation.
34 class DIEAbbrevData {
35   /// Attribute - Dwarf attribute code.
36   ///
37   dwarf::Attribute Attribute;
38 
39   /// Form - Dwarf form code.
40   ///
41   dwarf::Form Form;
42 
43 public:
DIEAbbrevData(dwarf::Attribute A,dwarf::Form F)44   DIEAbbrevData(dwarf::Attribute A, dwarf::Form F) : Attribute(A), Form(F) {}
45 
46   // Accessors.
getAttribute()47   dwarf::Attribute getAttribute() const { return Attribute; }
getForm()48   dwarf::Form getForm() const { return Form; }
49 
50   /// Profile - Used to gather unique data for the abbreviation folding set.
51   ///
52   void Profile(FoldingSetNodeID &ID) const;
53 };
54 
55 //===--------------------------------------------------------------------===//
56 /// DIEAbbrev - Dwarf abbreviation, describes the organization of a debug
57 /// information object.
58 class DIEAbbrev : public FoldingSetNode {
59   /// Unique number for node.
60   ///
61   unsigned Number;
62 
63   /// Tag - Dwarf tag code.
64   ///
65   dwarf::Tag Tag;
66 
67   /// Children - Whether or not this node has children.
68   ///
69   // This cheats a bit in all of the uses since the values in the standard
70   // are 0 and 1 for no children and children respectively.
71   bool Children;
72 
73   /// Data - Raw data bytes for abbreviation.
74   ///
75   SmallVector<DIEAbbrevData, 12> Data;
76 
77 public:
DIEAbbrev(dwarf::Tag T,bool C)78   DIEAbbrev(dwarf::Tag T, bool C) : Tag(T), Children(C), Data() {}
79 
80   // Accessors.
getTag()81   dwarf::Tag getTag() const { return Tag; }
getNumber()82   unsigned getNumber() const { return Number; }
hasChildren()83   bool hasChildren() const { return Children; }
getData()84   const SmallVectorImpl<DIEAbbrevData> &getData() const { return Data; }
setChildrenFlag(bool hasChild)85   void setChildrenFlag(bool hasChild) { Children = hasChild; }
setNumber(unsigned N)86   void setNumber(unsigned N) { Number = N; }
87 
88   /// AddAttribute - Adds another set of attribute information to the
89   /// abbreviation.
AddAttribute(dwarf::Attribute Attribute,dwarf::Form Form)90   void AddAttribute(dwarf::Attribute Attribute, dwarf::Form Form) {
91     Data.push_back(DIEAbbrevData(Attribute, Form));
92   }
93 
94   /// Profile - Used to gather unique data for the abbreviation folding set.
95   ///
96   void Profile(FoldingSetNodeID &ID) const;
97 
98   /// Emit - Print the abbreviation using the specified asm printer.
99   ///
100   void Emit(const AsmPrinter *AP) const;
101 
102   void print(raw_ostream &O);
103   void dump();
104 };
105 
106 //===--------------------------------------------------------------------===//
107 /// DIEInteger - An integer value DIE.
108 ///
109 class DIEInteger {
110   uint64_t Integer;
111 
112 public:
DIEInteger(uint64_t I)113   explicit DIEInteger(uint64_t I) : Integer(I) {}
114 
115   /// BestForm - Choose the best form for integer.
116   ///
BestForm(bool IsSigned,uint64_t Int)117   static dwarf::Form BestForm(bool IsSigned, uint64_t Int) {
118     if (IsSigned) {
119       const int64_t SignedInt = Int;
120       if ((char)Int == SignedInt)
121         return dwarf::DW_FORM_data1;
122       if ((short)Int == SignedInt)
123         return dwarf::DW_FORM_data2;
124       if ((int)Int == SignedInt)
125         return dwarf::DW_FORM_data4;
126     } else {
127       if ((unsigned char)Int == Int)
128         return dwarf::DW_FORM_data1;
129       if ((unsigned short)Int == Int)
130         return dwarf::DW_FORM_data2;
131       if ((unsigned int)Int == Int)
132         return dwarf::DW_FORM_data4;
133     }
134     return dwarf::DW_FORM_data8;
135   }
136 
getValue()137   uint64_t getValue() const { return Integer; }
setValue(uint64_t Val)138   void setValue(uint64_t Val) { Integer = Val; }
139 
140   void EmitValue(const AsmPrinter *AP, dwarf::Form Form) const;
141   unsigned SizeOf(const AsmPrinter *AP, dwarf::Form Form) const;
142 
143   void print(raw_ostream &O) const;
144 };
145 
146 //===--------------------------------------------------------------------===//
147 /// DIEExpr - An expression DIE.
148 //
149 class DIEExpr {
150   const MCExpr *Expr;
151 
152 public:
DIEExpr(const MCExpr * E)153   explicit DIEExpr(const MCExpr *E) : Expr(E) {}
154 
155   /// getValue - Get MCExpr.
156   ///
getValue()157   const MCExpr *getValue() const { return Expr; }
158 
159   void EmitValue(const AsmPrinter *AP, dwarf::Form Form) const;
160   unsigned SizeOf(const AsmPrinter *AP, dwarf::Form Form) const;
161 
162   void print(raw_ostream &O) const;
163 };
164 
165 //===--------------------------------------------------------------------===//
166 /// DIELabel - A label DIE.
167 //
168 class DIELabel {
169   const MCSymbol *Label;
170 
171 public:
DIELabel(const MCSymbol * L)172   explicit DIELabel(const MCSymbol *L) : Label(L) {}
173 
174   /// getValue - Get MCSymbol.
175   ///
getValue()176   const MCSymbol *getValue() const { return Label; }
177 
178   void EmitValue(const AsmPrinter *AP, dwarf::Form Form) const;
179   unsigned SizeOf(const AsmPrinter *AP, dwarf::Form Form) const;
180 
181   void print(raw_ostream &O) const;
182 };
183 
184 //===--------------------------------------------------------------------===//
185 /// DIEDelta - A simple label difference DIE.
186 ///
187 class DIEDelta {
188   const MCSymbol *LabelHi;
189   const MCSymbol *LabelLo;
190 
191 public:
DIEDelta(const MCSymbol * Hi,const MCSymbol * Lo)192   DIEDelta(const MCSymbol *Hi, const MCSymbol *Lo) : LabelHi(Hi), LabelLo(Lo) {}
193 
194   void EmitValue(const AsmPrinter *AP, dwarf::Form Form) const;
195   unsigned SizeOf(const AsmPrinter *AP, dwarf::Form Form) const;
196 
197   void print(raw_ostream &O) const;
198 };
199 
200 //===--------------------------------------------------------------------===//
201 /// DIEString - A container for string values.
202 ///
203 class DIEString {
204   DwarfStringPoolEntryRef S;
205 
206 public:
DIEString(DwarfStringPoolEntryRef S)207   DIEString(DwarfStringPoolEntryRef S) : S(S) {}
208 
209   /// getString - Grab the string out of the object.
getString()210   StringRef getString() const { return S.getString(); }
211 
212   void EmitValue(const AsmPrinter *AP, dwarf::Form Form) const;
213   unsigned SizeOf(const AsmPrinter *AP, dwarf::Form Form) const;
214 
215   void print(raw_ostream &O) const;
216 };
217 
218 //===--------------------------------------------------------------------===//
219 /// DIEEntry - A pointer to another debug information entry.  An instance of
220 /// this class can also be used as a proxy for a debug information entry not
221 /// yet defined (ie. types.)
222 class DIE;
223 class DIEEntry {
224   DIE *Entry;
225 
226   DIEEntry() = delete;
227 
228 public:
DIEEntry(DIE & E)229   explicit DIEEntry(DIE &E) : Entry(&E) {}
230 
getEntry()231   DIE &getEntry() const { return *Entry; }
232 
233   /// Returns size of a ref_addr entry.
234   static unsigned getRefAddrSize(const AsmPrinter *AP);
235 
236   void EmitValue(const AsmPrinter *AP, dwarf::Form Form) const;
SizeOf(const AsmPrinter * AP,dwarf::Form Form)237   unsigned SizeOf(const AsmPrinter *AP, dwarf::Form Form) const {
238     return Form == dwarf::DW_FORM_ref_addr ? getRefAddrSize(AP)
239                                            : sizeof(int32_t);
240   }
241 
242   void print(raw_ostream &O) const;
243 };
244 
245 //===--------------------------------------------------------------------===//
246 /// DIELocList - Represents a pointer to a location list in the debug_loc
247 /// section.
248 //
249 class DIELocList {
250   // Index into the .debug_loc vector.
251   size_t Index;
252 
253 public:
DIELocList(size_t I)254   DIELocList(size_t I) : Index(I) {}
255 
256   /// getValue - Grab the current index out.
getValue()257   size_t getValue() const { return Index; }
258 
259   void EmitValue(const AsmPrinter *AP, dwarf::Form Form) const;
260   unsigned SizeOf(const AsmPrinter *AP, dwarf::Form Form) const;
261 
262   void print(raw_ostream &O) const;
263 };
264 
265 //===--------------------------------------------------------------------===//
266 /// DIEValue - A debug information entry value. Some of these roughly correlate
267 /// to DWARF attribute classes.
268 ///
269 class DIEBlock;
270 class DIELoc;
271 class DIEValue {
272 public:
273   enum Type {
274     isNone,
275 #define HANDLE_DIEVALUE(T) is##T,
276 #include "llvm/CodeGen/DIEValue.def"
277   };
278 
279 private:
280   /// Ty - Type of data stored in the value.
281   ///
282   Type Ty = isNone;
283   dwarf::Attribute Attribute = (dwarf::Attribute)0;
284   dwarf::Form Form = (dwarf::Form)0;
285 
286   /// Storage for the value.
287   ///
288   /// All values that aren't standard layout (or are larger than 8 bytes)
289   /// should be stored by reference instead of by value.
290   typedef AlignedCharArrayUnion<DIEInteger, DIEString, DIEExpr, DIELabel,
291                                 DIEDelta *, DIEEntry, DIEBlock *, DIELoc *,
292                                 DIELocList>
293       ValTy;
294   static_assert(sizeof(ValTy) <= sizeof(uint64_t) ||
295                     sizeof(ValTy) <= sizeof(void *),
296                 "Expected all large types to be stored via pointer");
297 
298   /// Underlying stored value.
299   ValTy Val;
300 
construct(T V)301   template <class T> void construct(T V) {
302     static_assert(std::is_standard_layout<T>::value ||
303                       std::is_pointer<T>::value,
304                   "Expected standard layout or pointer");
305     new (reinterpret_cast<void *>(Val.buffer)) T(V);
306   }
307 
get()308   template <class T> T *get() { return reinterpret_cast<T *>(Val.buffer); }
get()309   template <class T> const T *get() const {
310     return reinterpret_cast<const T *>(Val.buffer);
311   }
destruct()312   template <class T> void destruct() { get<T>()->~T(); }
313 
314   /// Destroy the underlying value.
315   ///
316   /// This should get optimized down to a no-op.  We could skip it if we could
317   /// add a static assert on \a std::is_trivially_copyable(), but we currently
318   /// support versions of GCC that don't understand that.
destroyVal()319   void destroyVal() {
320     switch (Ty) {
321     case isNone:
322       return;
323 #define HANDLE_DIEVALUE_SMALL(T)                                               \
324   case is##T:                                                                  \
325     destruct<DIE##T>();
326     return;
327 #define HANDLE_DIEVALUE_LARGE(T)                                               \
328   case is##T:                                                                  \
329     destruct<const DIE##T *>();
330     return;
331 #include "llvm/CodeGen/DIEValue.def"
332     }
333   }
334 
335   /// Copy the underlying value.
336   ///
337   /// This should get optimized down to a simple copy.  We need to actually
338   /// construct the value, rather than calling memcpy, to satisfy strict
339   /// aliasing rules.
copyVal(const DIEValue & X)340   void copyVal(const DIEValue &X) {
341     switch (Ty) {
342     case isNone:
343       return;
344 #define HANDLE_DIEVALUE_SMALL(T)                                               \
345   case is##T:                                                                  \
346     construct<DIE##T>(*X.get<DIE##T>());                                       \
347     return;
348 #define HANDLE_DIEVALUE_LARGE(T)                                               \
349   case is##T:                                                                  \
350     construct<const DIE##T *>(*X.get<const DIE##T *>());                       \
351     return;
352 #include "llvm/CodeGen/DIEValue.def"
353     }
354   }
355 
356 public:
357   DIEValue() = default;
DIEValue(const DIEValue & X)358   DIEValue(const DIEValue &X) : Ty(X.Ty), Attribute(X.Attribute), Form(X.Form) {
359     copyVal(X);
360   }
361   DIEValue &operator=(const DIEValue &X) {
362     destroyVal();
363     Ty = X.Ty;
364     Attribute = X.Attribute;
365     Form = X.Form;
366     copyVal(X);
367     return *this;
368   }
~DIEValue()369   ~DIEValue() { destroyVal(); }
370 
371 #define HANDLE_DIEVALUE_SMALL(T)                                               \
372   DIEValue(dwarf::Attribute Attribute, dwarf::Form Form, const DIE##T &V)      \
373       : Ty(is##T), Attribute(Attribute), Form(Form) {                          \
374     construct<DIE##T>(V);                                                      \
375   }
376 #define HANDLE_DIEVALUE_LARGE(T)                                               \
377   DIEValue(dwarf::Attribute Attribute, dwarf::Form Form, const DIE##T *V)      \
378       : Ty(is##T), Attribute(Attribute), Form(Form) {                          \
379     assert(V && "Expected valid value");                                       \
380     construct<const DIE##T *>(V);                                              \
381   }
382 #include "llvm/CodeGen/DIEValue.def"
383 
384   // Accessors
getType()385   Type getType() const { return Ty; }
getAttribute()386   dwarf::Attribute getAttribute() const { return Attribute; }
getForm()387   dwarf::Form getForm() const { return Form; }
388   explicit operator bool() const { return Ty; }
389 
390 #define HANDLE_DIEVALUE_SMALL(T)                                               \
391   const DIE##T &getDIE##T() const {                                            \
392     assert(getType() == is##T && "Expected " #T);                              \
393     return *get<DIE##T>();                                                     \
394   }
395 #define HANDLE_DIEVALUE_LARGE(T)                                               \
396   const DIE##T &getDIE##T() const {                                            \
397     assert(getType() == is##T && "Expected " #T);                              \
398     return **get<const DIE##T *>();                                            \
399   }
400 #include "llvm/CodeGen/DIEValue.def"
401 
402   /// EmitValue - Emit value via the Dwarf writer.
403   ///
404   void EmitValue(const AsmPrinter *AP) const;
405 
406   /// SizeOf - Return the size of a value in bytes.
407   ///
408   unsigned SizeOf(const AsmPrinter *AP) const;
409 
410   void print(raw_ostream &O) const;
411   void dump() const;
412 };
413 
414 struct IntrusiveBackListNode {
415   PointerIntPair<IntrusiveBackListNode *, 1> Next;
IntrusiveBackListNodeIntrusiveBackListNode416   IntrusiveBackListNode() : Next(this, true) {}
417 
getNextIntrusiveBackListNode418   IntrusiveBackListNode *getNext() const {
419     return Next.getInt() ? nullptr : Next.getPointer();
420   }
421 };
422 
423 struct IntrusiveBackListBase {
424   typedef IntrusiveBackListNode Node;
425   Node *Last = nullptr;
426 
emptyIntrusiveBackListBase427   bool empty() const { return !Last; }
push_backIntrusiveBackListBase428   void push_back(Node &N) {
429     assert(N.Next.getPointer() == &N && "Expected unlinked node");
430     assert(N.Next.getInt() == true && "Expected unlinked node");
431 
432     if (Last) {
433       N.Next = Last->Next;
434       Last->Next.setPointerAndInt(&N, false);
435     }
436     Last = &N;
437   }
438 };
439 
440 template <class T> class IntrusiveBackList : IntrusiveBackListBase {
441 public:
442   using IntrusiveBackListBase::empty;
push_back(T & N)443   void push_back(T &N) { IntrusiveBackListBase::push_back(N); }
back()444   T &back() { return *static_cast<T *>(Last); }
back()445   const T &back() const { return *static_cast<T *>(Last); }
446 
447   class const_iterator;
448   class iterator
449       : public iterator_facade_base<iterator, std::forward_iterator_tag, T> {
450     friend class const_iterator;
451     Node *N = nullptr;
452 
453   public:
454     iterator() = default;
iterator(T * N)455     explicit iterator(T *N) : N(N) {}
456 
457     iterator &operator++() {
458       N = N->getNext();
459       return *this;
460     }
461 
462     explicit operator bool() const { return N; }
463     T &operator*() const { return *static_cast<T *>(N); }
464 
465     bool operator==(const iterator &X) const { return N == X.N; }
466     bool operator!=(const iterator &X) const { return N != X.N; }
467   };
468 
469   class const_iterator
470       : public iterator_facade_base<const_iterator, std::forward_iterator_tag,
471                                     const T> {
472     const Node *N = nullptr;
473 
474   public:
475     const_iterator() = default;
476     // Placate MSVC by explicitly scoping 'iterator'.
const_iterator(typename IntrusiveBackList<T>::iterator X)477     const_iterator(typename IntrusiveBackList<T>::iterator X) : N(X.N) {}
const_iterator(const T * N)478     explicit const_iterator(const T *N) : N(N) {}
479 
480     const_iterator &operator++() {
481       N = N->getNext();
482       return *this;
483     }
484 
485     explicit operator bool() const { return N; }
486     const T &operator*() const { return *static_cast<const T *>(N); }
487 
488     bool operator==(const const_iterator &X) const { return N == X.N; }
489     bool operator!=(const const_iterator &X) const { return N != X.N; }
490   };
491 
begin()492   iterator begin() {
493     return Last ? iterator(static_cast<T *>(Last->Next.getPointer())) : end();
494   }
begin()495   const_iterator begin() const {
496     return const_cast<IntrusiveBackList *>(this)->begin();
497   }
end()498   iterator end() { return iterator(); }
end()499   const_iterator end() const { return const_iterator(); }
500 
toIterator(T & N)501   static iterator toIterator(T &N) { return iterator(&N); }
toIterator(const T & N)502   static const_iterator toIterator(const T &N) { return const_iterator(&N); }
503 };
504 
505 /// A list of DIE values.
506 ///
507 /// This is a singly-linked list, but instead of reversing the order of
508 /// insertion, we keep a pointer to the back of the list so we can push in
509 /// order.
510 ///
511 /// There are two main reasons to choose a linked list over a customized
512 /// vector-like data structure.
513 ///
514 ///  1. For teardown efficiency, we want DIEs to be BumpPtrAllocated.  Using a
515 ///     linked list here makes this way easier to accomplish.
516 ///  2. Carrying an extra pointer per \a DIEValue isn't expensive.  45% of DIEs
517 ///     have 2 or fewer values, and 90% have 5 or fewer.  A vector would be
518 ///     over-allocated by 50% on average anyway, the same cost as the
519 ///     linked-list node.
520 class DIEValueList {
521   struct Node : IntrusiveBackListNode {
522     DIEValue V;
NodeNode523     explicit Node(DIEValue V) : V(V) {}
524   };
525 
526   typedef IntrusiveBackList<Node> ListTy;
527   ListTy List;
528 
529 public:
530   class const_value_iterator;
531   class value_iterator
532       : public iterator_adaptor_base<value_iterator, ListTy::iterator,
533                                      std::forward_iterator_tag, DIEValue> {
534     friend class const_value_iterator;
535     typedef iterator_adaptor_base<value_iterator, ListTy::iterator,
536                                   std::forward_iterator_tag,
537                                   DIEValue> iterator_adaptor;
538 
539   public:
540     value_iterator() = default;
value_iterator(ListTy::iterator X)541     explicit value_iterator(ListTy::iterator X) : iterator_adaptor(X) {}
542 
543     explicit operator bool() const { return bool(wrapped()); }
544     DIEValue &operator*() const { return wrapped()->V; }
545   };
546 
547   class const_value_iterator : public iterator_adaptor_base<
548                                    const_value_iterator, ListTy::const_iterator,
549                                    std::forward_iterator_tag, const DIEValue> {
550     typedef iterator_adaptor_base<const_value_iterator, ListTy::const_iterator,
551                                   std::forward_iterator_tag,
552                                   const DIEValue> iterator_adaptor;
553 
554   public:
555     const_value_iterator() = default;
const_value_iterator(DIEValueList::value_iterator X)556     const_value_iterator(DIEValueList::value_iterator X)
557         : iterator_adaptor(X.wrapped()) {}
const_value_iterator(ListTy::const_iterator X)558     explicit const_value_iterator(ListTy::const_iterator X)
559         : iterator_adaptor(X) {}
560 
561     explicit operator bool() const { return bool(wrapped()); }
562     const DIEValue &operator*() const { return wrapped()->V; }
563   };
564 
565   typedef iterator_range<value_iterator> value_range;
566   typedef iterator_range<const_value_iterator> const_value_range;
567 
addValue(BumpPtrAllocator & Alloc,const DIEValue & V)568   value_iterator addValue(BumpPtrAllocator &Alloc, const DIEValue &V) {
569     List.push_back(*new (Alloc) Node(V));
570     return value_iterator(ListTy::toIterator(List.back()));
571   }
572   template <class T>
addValue(BumpPtrAllocator & Alloc,dwarf::Attribute Attribute,dwarf::Form Form,T && Value)573   value_iterator addValue(BumpPtrAllocator &Alloc, dwarf::Attribute Attribute,
574                     dwarf::Form Form, T &&Value) {
575     return addValue(Alloc, DIEValue(Attribute, Form, std::forward<T>(Value)));
576   }
577 
values()578   value_range values() {
579     return llvm::make_range(value_iterator(List.begin()),
580                             value_iterator(List.end()));
581   }
values()582   const_value_range values() const {
583     return llvm::make_range(const_value_iterator(List.begin()),
584                             const_value_iterator(List.end()));
585   }
586 };
587 
588 //===--------------------------------------------------------------------===//
589 /// DIE - A structured debug information entry.  Has an abbreviation which
590 /// describes its organization.
591 class DIE : IntrusiveBackListNode, public DIEValueList {
592   friend class IntrusiveBackList<DIE>;
593 
594   /// Offset - Offset in debug info section.
595   ///
596   unsigned Offset;
597 
598   /// Size - Size of instance + children.
599   ///
600   unsigned Size;
601 
602   unsigned AbbrevNumber = ~0u;
603 
604   /// Tag - Dwarf tag code.
605   ///
606   dwarf::Tag Tag = (dwarf::Tag)0;
607 
608   /// Children DIEs.
609   IntrusiveBackList<DIE> Children;
610 
611   DIE *Parent = nullptr;
612 
613   DIE() = delete;
DIE(dwarf::Tag Tag)614   explicit DIE(dwarf::Tag Tag) : Offset(0), Size(0), Tag(Tag) {}
615 
616 public:
get(BumpPtrAllocator & Alloc,dwarf::Tag Tag)617   static DIE *get(BumpPtrAllocator &Alloc, dwarf::Tag Tag) {
618     return new (Alloc) DIE(Tag);
619   }
620 
621   // Accessors.
getAbbrevNumber()622   unsigned getAbbrevNumber() const { return AbbrevNumber; }
getTag()623   dwarf::Tag getTag() const { return Tag; }
getOffset()624   unsigned getOffset() const { return Offset; }
getSize()625   unsigned getSize() const { return Size; }
hasChildren()626   bool hasChildren() const { return !Children.empty(); }
627 
628   typedef IntrusiveBackList<DIE>::iterator child_iterator;
629   typedef IntrusiveBackList<DIE>::const_iterator const_child_iterator;
630   typedef iterator_range<child_iterator> child_range;
631   typedef iterator_range<const_child_iterator> const_child_range;
632 
children()633   child_range children() {
634     return llvm::make_range(Children.begin(), Children.end());
635   }
children()636   const_child_range children() const {
637     return llvm::make_range(Children.begin(), Children.end());
638   }
639 
getParent()640   DIE *getParent() const { return Parent; }
641 
642   /// Generate the abbreviation for this DIE.
643   ///
644   /// Calculate the abbreviation for this, which should be uniqued and
645   /// eventually used to call \a setAbbrevNumber().
646   DIEAbbrev generateAbbrev() const;
647 
648   /// Set the abbreviation number for this DIE.
setAbbrevNumber(unsigned I)649   void setAbbrevNumber(unsigned I) { AbbrevNumber = I; }
650 
651   /// Climb up the parent chain to get the compile or type unit DIE this DIE
652   /// belongs to.
653   const DIE *getUnit() const;
654   /// Similar to getUnit, returns null when DIE is not added to an
655   /// owner yet.
656   const DIE *getUnitOrNull() const;
setOffset(unsigned O)657   void setOffset(unsigned O) { Offset = O; }
setSize(unsigned S)658   void setSize(unsigned S) { Size = S; }
659 
660   /// Add a child to the DIE.
addChild(DIE * Child)661   DIE &addChild(DIE *Child) {
662     assert(!Child->getParent() && "Child should be orphaned");
663     Child->Parent = this;
664     Children.push_back(*Child);
665     return Children.back();
666   }
667 
668   /// Find a value in the DIE with the attribute given.
669   ///
670   /// Returns a default-constructed DIEValue (where \a DIEValue::getType()
671   /// gives \a DIEValue::isNone) if no such attribute exists.
672   DIEValue findAttribute(dwarf::Attribute Attribute) const;
673 
674   void print(raw_ostream &O, unsigned IndentCount = 0) const;
675   void dump();
676 };
677 
678 //===--------------------------------------------------------------------===//
679 /// DIELoc - Represents an expression location.
680 //
681 class DIELoc : public DIEValueList {
682   mutable unsigned Size; // Size in bytes excluding size header.
683 
684 public:
DIELoc()685   DIELoc() : Size(0) {}
686 
687   /// ComputeSize - Calculate the size of the location expression.
688   ///
689   unsigned ComputeSize(const AsmPrinter *AP) const;
690 
691   /// BestForm - Choose the best form for data.
692   ///
BestForm(unsigned DwarfVersion)693   dwarf::Form BestForm(unsigned DwarfVersion) const {
694     if (DwarfVersion > 3)
695       return dwarf::DW_FORM_exprloc;
696     // Pre-DWARF4 location expressions were blocks and not exprloc.
697     if ((unsigned char)Size == Size)
698       return dwarf::DW_FORM_block1;
699     if ((unsigned short)Size == Size)
700       return dwarf::DW_FORM_block2;
701     if ((unsigned int)Size == Size)
702       return dwarf::DW_FORM_block4;
703     return dwarf::DW_FORM_block;
704   }
705 
706   void EmitValue(const AsmPrinter *AP, dwarf::Form Form) const;
707   unsigned SizeOf(const AsmPrinter *AP, dwarf::Form Form) const;
708 
709   void print(raw_ostream &O) const;
710 };
711 
712 //===--------------------------------------------------------------------===//
713 /// DIEBlock - Represents a block of values.
714 //
715 class DIEBlock : public DIEValueList {
716   mutable unsigned Size; // Size in bytes excluding size header.
717 
718 public:
DIEBlock()719   DIEBlock() : Size(0) {}
720 
721   /// ComputeSize - Calculate the size of the location expression.
722   ///
723   unsigned ComputeSize(const AsmPrinter *AP) const;
724 
725   /// BestForm - Choose the best form for data.
726   ///
BestForm()727   dwarf::Form BestForm() const {
728     if ((unsigned char)Size == Size)
729       return dwarf::DW_FORM_block1;
730     if ((unsigned short)Size == Size)
731       return dwarf::DW_FORM_block2;
732     if ((unsigned int)Size == Size)
733       return dwarf::DW_FORM_block4;
734     return dwarf::DW_FORM_block;
735   }
736 
737   void EmitValue(const AsmPrinter *AP, dwarf::Form Form) const;
738   unsigned SizeOf(const AsmPrinter *AP, dwarf::Form Form) const;
739 
740   void print(raw_ostream &O) const;
741 };
742 
743 } // end llvm namespace
744 
745 #endif
746