MC: Add default value for AddrSpace argument to EmitValue.
[oota-llvm.git] / include / llvm / MC / MCAssembler.h
1 //===- MCAssembler.h - Object File Generation -------------------*- 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 #ifndef LLVM_MC_MCASSEMBLER_H
11 #define LLVM_MC_MCASSEMBLER_H
12
13 #include "llvm/ADT/DenseMap.h"
14 #include "llvm/ADT/SmallString.h"
15 #include "llvm/ADT/ilist.h"
16 #include "llvm/ADT/ilist_node.h"
17 #include "llvm/Support/Casting.h"
18 #include "llvm/MC/MCFixup.h"
19 #include "llvm/MC/MCInst.h"
20 #include "llvm/System/DataTypes.h"
21 #include <vector> // FIXME: Shouldn't be needed.
22
23 namespace llvm {
24 class raw_ostream;
25 class MCAsmLayout;
26 class MCAssembler;
27 class MCContext;
28 class MCCodeEmitter;
29 class MCExpr;
30 class MCFragment;
31 class MCObjectWriter;
32 class MCSection;
33 class MCSectionData;
34 class MCSymbol;
35 class MCSymbolData;
36 class MCValue;
37 class TargetAsmBackend;
38
39 class MCFragment : public ilist_node<MCFragment> {
40   friend class MCAsmLayout;
41
42   MCFragment(const MCFragment&);     // DO NOT IMPLEMENT
43   void operator=(const MCFragment&); // DO NOT IMPLEMENT
44
45 public:
46   enum FragmentType {
47     FT_Align,
48     FT_Data,
49     FT_Fill,
50     FT_Inst,
51     FT_Org
52   };
53
54 private:
55   FragmentType Kind;
56
57   /// Parent - The data for the section this fragment is in.
58   MCSectionData *Parent;
59
60   /// Atom - The atom this fragment is in, as represented by it's defining
61   /// symbol. Atom's are only used by backends which set
62   /// \see MCAsmBackend::hasReliableSymbolDifference().
63   MCSymbolData *Atom;
64
65   /// @name Assembler Backend Data
66   /// @{
67   //
68   // FIXME: This could all be kept private to the assembler implementation.
69
70   /// Offset - The offset of this fragment in its section. This is ~0 until
71   /// initialized.
72   uint64_t Offset;
73
74   /// EffectiveSize - The compute size of this section. This is ~0 until
75   /// initialized.
76   uint64_t EffectiveSize;
77
78   /// LayoutOrder - The global layout order of this fragment. This is the index
79   /// across all fragments in the file, not just within the section.
80   unsigned LayoutOrder;
81
82   /// @}
83
84 protected:
85   MCFragment(FragmentType _Kind, MCSectionData *_Parent = 0);
86
87 public:
88   // Only for sentinel.
89   MCFragment();
90   virtual ~MCFragment();
91
92   FragmentType getKind() const { return Kind; }
93
94   MCSectionData *getParent() const { return Parent; }
95   void setParent(MCSectionData *Value) { Parent = Value; }
96
97   MCSymbolData *getAtom() const { return Atom; }
98   void setAtom(MCSymbolData *Value) { Atom = Value; }
99
100   unsigned getLayoutOrder() const { return LayoutOrder; }
101   void setLayoutOrder(unsigned Value) { LayoutOrder = Value; }
102
103   static bool classof(const MCFragment *O) { return true; }
104
105   void dump();
106 };
107
108 class MCDataFragment : public MCFragment {
109   SmallString<32> Contents;
110
111   /// Fixups - The list of fixups in this fragment.
112   std::vector<MCFixup> Fixups;
113
114 public:
115   typedef std::vector<MCFixup>::const_iterator const_fixup_iterator;
116   typedef std::vector<MCFixup>::iterator fixup_iterator;
117
118 public:
119   MCDataFragment(MCSectionData *SD = 0) : MCFragment(FT_Data, SD) {}
120
121   /// @name Accessors
122   /// @{
123
124   SmallString<32> &getContents() { return Contents; }
125   const SmallString<32> &getContents() const { return Contents; }
126
127   /// @}
128   /// @name Fixup Access
129   /// @{
130
131   void addFixup(MCFixup Fixup) {
132     // Enforce invariant that fixups are in offset order.
133     assert((Fixups.empty() || Fixup.getOffset() > Fixups.back().getOffset()) &&
134            "Fixups must be added in order!");
135     Fixups.push_back(Fixup);
136   }
137
138   std::vector<MCFixup> &getFixups() { return Fixups; }
139   const std::vector<MCFixup> &getFixups() const { return Fixups; }
140
141   fixup_iterator fixup_begin() { return Fixups.begin(); }
142   const_fixup_iterator fixup_begin() const { return Fixups.begin(); }
143
144   fixup_iterator fixup_end() {return Fixups.end();}
145   const_fixup_iterator fixup_end() const {return Fixups.end();}
146
147   size_t fixup_size() const { return Fixups.size(); }
148
149   /// @}
150
151   static bool classof(const MCFragment *F) {
152     return F->getKind() == MCFragment::FT_Data;
153   }
154   static bool classof(const MCDataFragment *) { return true; }
155 };
156
157 // FIXME: This current incarnation of MCInstFragment doesn't make much sense, as
158 // it is almost entirely a duplicate of MCDataFragment. If we decide to stick
159 // with this approach (as opposed to making MCInstFragment a very light weight
160 // object with just the MCInst and a code size, then we should just change
161 // MCDataFragment to have an optional MCInst at its end.
162 class MCInstFragment : public MCFragment {
163   /// Inst - The instruction this is a fragment for.
164   MCInst Inst;
165
166   /// InstSize - The size of the currently encoded instruction.
167   SmallString<8> Code;
168
169   /// Fixups - The list of fixups in this fragment.
170   SmallVector<MCFixup, 1> Fixups;
171
172 public:
173   typedef SmallVectorImpl<MCFixup>::const_iterator const_fixup_iterator;
174   typedef SmallVectorImpl<MCFixup>::iterator fixup_iterator;
175
176 public:
177   MCInstFragment(MCInst _Inst, MCSectionData *SD = 0)
178     : MCFragment(FT_Inst, SD), Inst(_Inst) {
179   }
180
181   /// @name Accessors
182   /// @{
183
184   SmallVectorImpl<char> &getCode() { return Code; }
185   const SmallVectorImpl<char> &getCode() const { return Code; }
186
187   unsigned getInstSize() const { return Code.size(); }
188
189   MCInst &getInst() { return Inst; }
190   const MCInst &getInst() const { return Inst; }
191
192   void setInst(MCInst Value) { Inst = Value; }
193
194   /// @}
195   /// @name Fixup Access
196   /// @{
197
198   SmallVectorImpl<MCFixup> &getFixups() { return Fixups; }
199   const SmallVectorImpl<MCFixup> &getFixups() const { return Fixups; }
200
201   fixup_iterator fixup_begin() { return Fixups.begin(); }
202   const_fixup_iterator fixup_begin() const { return Fixups.begin(); }
203
204   fixup_iterator fixup_end() {return Fixups.end();}
205   const_fixup_iterator fixup_end() const {return Fixups.end();}
206
207   size_t fixup_size() const { return Fixups.size(); }
208
209   /// @}
210
211   static bool classof(const MCFragment *F) {
212     return F->getKind() == MCFragment::FT_Inst;
213   }
214   static bool classof(const MCInstFragment *) { return true; }
215 };
216
217 class MCAlignFragment : public MCFragment {
218   /// Alignment - The alignment to ensure, in bytes.
219   unsigned Alignment;
220
221   /// Value - Value to use for filling padding bytes.
222   int64_t Value;
223
224   /// ValueSize - The size of the integer (in bytes) of \arg Value.
225   unsigned ValueSize;
226
227   /// MaxBytesToEmit - The maximum number of bytes to emit; if the alignment
228   /// cannot be satisfied in this width then this fragment is ignored.
229   unsigned MaxBytesToEmit;
230
231   /// EmitNops - Flag to indicate that (optimal) NOPs should be emitted instead
232   /// of using the provided value. The exact interpretation of this flag is
233   /// target dependent.
234   bool EmitNops : 1;
235
236   /// OnlyAlignAddress - Flag to indicate that this align is only used to adjust
237   /// the address space size of a section and that it should not be included as
238   /// part of the section size. This flag can only be used on the last fragment
239   /// in a section.
240   bool OnlyAlignAddress : 1;
241
242 public:
243   MCAlignFragment(unsigned _Alignment, int64_t _Value, unsigned _ValueSize,
244                   unsigned _MaxBytesToEmit, MCSectionData *SD = 0)
245     : MCFragment(FT_Align, SD), Alignment(_Alignment),
246       Value(_Value),ValueSize(_ValueSize),
247       MaxBytesToEmit(_MaxBytesToEmit), EmitNops(false),
248       OnlyAlignAddress(false) {}
249
250   /// @name Accessors
251   /// @{
252
253   unsigned getAlignment() const { return Alignment; }
254
255   int64_t getValue() const { return Value; }
256
257   unsigned getValueSize() const { return ValueSize; }
258
259   unsigned getMaxBytesToEmit() const { return MaxBytesToEmit; }
260
261   bool hasEmitNops() const { return EmitNops; }
262   void setEmitNops(bool Value) { EmitNops = Value; }
263
264   bool hasOnlyAlignAddress() const { return OnlyAlignAddress; }
265   void setOnlyAlignAddress(bool Value) { OnlyAlignAddress = Value; }
266
267   /// @}
268
269   static bool classof(const MCFragment *F) {
270     return F->getKind() == MCFragment::FT_Align;
271   }
272   static bool classof(const MCAlignFragment *) { return true; }
273 };
274
275 class MCFillFragment : public MCFragment {
276   /// Value - Value to use for filling bytes.
277   int64_t Value;
278
279   /// ValueSize - The size (in bytes) of \arg Value to use when filling, or 0 if
280   /// this is a virtual fill fragment.
281   unsigned ValueSize;
282
283   /// Size - The number of bytes to insert.
284   uint64_t Size;
285
286 public:
287   MCFillFragment(int64_t _Value, unsigned _ValueSize, uint64_t _Size,
288                  MCSectionData *SD = 0)
289     : MCFragment(FT_Fill, SD),
290       Value(_Value), ValueSize(_ValueSize), Size(_Size) {
291     assert((!ValueSize || (Size % ValueSize) == 0) &&
292            "Fill size must be a multiple of the value size!");
293   }
294
295   /// @name Accessors
296   /// @{
297
298   int64_t getValue() const { return Value; }
299
300   unsigned getValueSize() const { return ValueSize; }
301
302   uint64_t getSize() const { return Size; }
303
304   /// @}
305
306   static bool classof(const MCFragment *F) {
307     return F->getKind() == MCFragment::FT_Fill;
308   }
309   static bool classof(const MCFillFragment *) { return true; }
310 };
311
312 class MCOrgFragment : public MCFragment {
313   /// Offset - The offset this fragment should start at.
314   const MCExpr *Offset;
315
316   /// Value - Value to use for filling bytes.
317   int8_t Value;
318
319 public:
320   MCOrgFragment(const MCExpr &_Offset, int8_t _Value, MCSectionData *SD = 0)
321     : MCFragment(FT_Org, SD),
322       Offset(&_Offset), Value(_Value) {}
323
324   /// @name Accessors
325   /// @{
326
327   const MCExpr &getOffset() const { return *Offset; }
328
329   uint8_t getValue() const { return Value; }
330
331   /// @}
332
333   static bool classof(const MCFragment *F) {
334     return F->getKind() == MCFragment::FT_Org;
335   }
336   static bool classof(const MCOrgFragment *) { return true; }
337 };
338
339 // FIXME: Should this be a separate class, or just merged into MCSection? Since
340 // we anticipate the fast path being through an MCAssembler, the only reason to
341 // keep it out is for API abstraction.
342 class MCSectionData : public ilist_node<MCSectionData> {
343   friend class MCAsmLayout;
344
345   MCSectionData(const MCSectionData&);  // DO NOT IMPLEMENT
346   void operator=(const MCSectionData&); // DO NOT IMPLEMENT
347
348 public:
349   typedef iplist<MCFragment> FragmentListType;
350
351   typedef FragmentListType::const_iterator const_iterator;
352   typedef FragmentListType::iterator iterator;
353
354   typedef FragmentListType::const_reverse_iterator const_reverse_iterator;
355   typedef FragmentListType::reverse_iterator reverse_iterator;
356
357 private:
358   FragmentListType Fragments;
359   const MCSection *Section;
360
361   /// Ordinal - The section index in the assemblers section list.
362   unsigned Ordinal;
363
364   /// LayoutOrder - The index of this section in the layout order.
365   unsigned LayoutOrder;
366
367   /// Alignment - The maximum alignment seen in this section.
368   unsigned Alignment;
369
370   /// @name Assembler Backend Data
371   /// @{
372   //
373   // FIXME: This could all be kept private to the assembler implementation.
374
375   /// Address - The computed address of this section. This is ~0 until
376   /// initialized.
377   uint64_t Address;
378
379   /// HasInstructions - Whether this section has had instructions emitted into
380   /// it.
381   unsigned HasInstructions : 1;
382
383   /// @}
384
385 public:
386   // Only for use as sentinel.
387   MCSectionData();
388   MCSectionData(const MCSection &Section, MCAssembler *A = 0);
389
390   const MCSection &getSection() const { return *Section; }
391
392   unsigned getAlignment() const { return Alignment; }
393   void setAlignment(unsigned Value) { Alignment = Value; }
394
395   bool hasInstructions() const { return HasInstructions; }
396   void setHasInstructions(bool Value) { HasInstructions = Value; }
397
398   unsigned getOrdinal() const { return Ordinal; }
399   void setOrdinal(unsigned Value) { Ordinal = Value; }
400
401   unsigned getLayoutOrder() const { return LayoutOrder; }
402   void setLayoutOrder(unsigned Value) { LayoutOrder = Value; }
403
404   /// @name Fragment Access
405   /// @{
406
407   const FragmentListType &getFragmentList() const { return Fragments; }
408   FragmentListType &getFragmentList() { return Fragments; }
409
410   iterator begin() { return Fragments.begin(); }
411   const_iterator begin() const { return Fragments.begin(); }
412
413   iterator end() { return Fragments.end(); }
414   const_iterator end() const { return Fragments.end(); }
415
416   reverse_iterator rbegin() { return Fragments.rbegin(); }
417   const_reverse_iterator rbegin() const { return Fragments.rbegin(); }
418
419   reverse_iterator rend() { return Fragments.rend(); }
420   const_reverse_iterator rend() const { return Fragments.rend(); }
421
422   size_t size() const { return Fragments.size(); }
423
424   bool empty() const { return Fragments.empty(); }
425
426   void dump();
427
428   /// @}
429 };
430
431 // FIXME: Same concerns as with SectionData.
432 class MCSymbolData : public ilist_node<MCSymbolData> {
433 public:
434   const MCSymbol *Symbol;
435
436   /// Fragment - The fragment this symbol's value is relative to, if any.
437   MCFragment *Fragment;
438
439   /// Offset - The offset to apply to the fragment address to form this symbol's
440   /// value.
441   uint64_t Offset;
442
443   /// IsExternal - True if this symbol is visible outside this translation
444   /// unit.
445   unsigned IsExternal : 1;
446
447   /// IsPrivateExtern - True if this symbol is private extern.
448   unsigned IsPrivateExtern : 1;
449
450   /// CommonSize - The size of the symbol, if it is 'common', or 0.
451   //
452   // FIXME: Pack this in with other fields? We could put it in offset, since a
453   // common symbol can never get a definition.
454   uint64_t CommonSize;
455
456   /// CommonAlign - The alignment of the symbol, if it is 'common'.
457   //
458   // FIXME: Pack this in with other fields?
459   unsigned CommonAlign;
460
461   /// Flags - The Flags field is used by object file implementations to store
462   /// additional per symbol information which is not easily classified.
463   uint32_t Flags;
464
465   /// Index - Index field, for use by the object file implementation.
466   uint64_t Index;
467
468 public:
469   // Only for use as sentinel.
470   MCSymbolData();
471   MCSymbolData(const MCSymbol &_Symbol, MCFragment *_Fragment, uint64_t _Offset,
472                MCAssembler *A = 0);
473
474   /// @name Accessors
475   /// @{
476
477   const MCSymbol &getSymbol() const { return *Symbol; }
478
479   MCFragment *getFragment() const { return Fragment; }
480   void setFragment(MCFragment *Value) { Fragment = Value; }
481
482   uint64_t getOffset() const { return Offset; }
483   void setOffset(uint64_t Value) { Offset = Value; }
484
485   /// @}
486   /// @name Symbol Attributes
487   /// @{
488
489   bool isExternal() const { return IsExternal; }
490   void setExternal(bool Value) { IsExternal = Value; }
491
492   bool isPrivateExtern() const { return IsPrivateExtern; }
493   void setPrivateExtern(bool Value) { IsPrivateExtern = Value; }
494
495   /// isCommon - Is this a 'common' symbol.
496   bool isCommon() const { return CommonSize != 0; }
497
498   /// setCommon - Mark this symbol as being 'common'.
499   ///
500   /// \param Size - The size of the symbol.
501   /// \param Align - The alignment of the symbol.
502   void setCommon(uint64_t Size, unsigned Align) {
503     CommonSize = Size;
504     CommonAlign = Align;
505   }
506
507   /// getCommonSize - Return the size of a 'common' symbol.
508   uint64_t getCommonSize() const {
509     assert(isCommon() && "Not a 'common' symbol!");
510     return CommonSize;
511   }
512
513   /// getCommonAlignment - Return the alignment of a 'common' symbol.
514   unsigned getCommonAlignment() const {
515     assert(isCommon() && "Not a 'common' symbol!");
516     return CommonAlign;
517   }
518
519   /// getFlags - Get the (implementation defined) symbol flags.
520   uint32_t getFlags() const { return Flags; }
521
522   /// setFlags - Set the (implementation defined) symbol flags.
523   void setFlags(uint32_t Value) { Flags = Value; }
524
525   /// modifyFlags - Modify the flags via a mask
526   void modifyFlags(uint32_t Value, uint32_t Mask) {
527     Flags = (Flags & ~Mask) | Value;
528   }
529
530   /// getIndex - Get the (implementation defined) index.
531   uint64_t getIndex() const { return Index; }
532
533   /// setIndex - Set the (implementation defined) index.
534   void setIndex(uint64_t Value) { Index = Value; }
535
536   /// @}
537
538   void dump();
539 };
540
541 // FIXME: This really doesn't belong here. See comments below.
542 struct IndirectSymbolData {
543   MCSymbol *Symbol;
544   MCSectionData *SectionData;
545 };
546
547 class MCAssembler {
548   friend class MCAsmLayout;
549
550 public:
551   typedef iplist<MCSectionData> SectionDataListType;
552   typedef iplist<MCSymbolData> SymbolDataListType;
553
554   typedef SectionDataListType::const_iterator const_iterator;
555   typedef SectionDataListType::iterator iterator;
556
557   typedef SymbolDataListType::const_iterator const_symbol_iterator;
558   typedef SymbolDataListType::iterator symbol_iterator;
559
560   typedef std::vector<IndirectSymbolData>::const_iterator
561     const_indirect_symbol_iterator;
562   typedef std::vector<IndirectSymbolData>::iterator indirect_symbol_iterator;
563
564 private:
565   MCAssembler(const MCAssembler&);    // DO NOT IMPLEMENT
566   void operator=(const MCAssembler&); // DO NOT IMPLEMENT
567
568   MCContext &Context;
569
570   TargetAsmBackend &Backend;
571
572   MCCodeEmitter &Emitter;
573
574   raw_ostream &OS;
575
576   iplist<MCSectionData> Sections;
577
578   iplist<MCSymbolData> Symbols;
579
580   /// The map of sections to their associated assembler backend data.
581   //
582   // FIXME: Avoid this indirection?
583   DenseMap<const MCSection*, MCSectionData*> SectionMap;
584
585   /// The map of symbols to their associated assembler backend data.
586   //
587   // FIXME: Avoid this indirection?
588   DenseMap<const MCSymbol*, MCSymbolData*> SymbolMap;
589
590   std::vector<IndirectSymbolData> IndirectSymbols;
591
592   unsigned RelaxAll : 1;
593   unsigned SubsectionsViaSymbols : 1;
594
595 private:
596   /// Evaluate a fixup to a relocatable expression and the value which should be
597   /// placed into the fixup.
598   ///
599   /// \param Layout The layout to use for evaluation.
600   /// \param Fixup The fixup to evaluate.
601   /// \param DF The fragment the fixup is inside.
602   /// \param Target [out] On return, the relocatable expression the fixup
603   /// evaluates to.
604   /// \param Value [out] On return, the value of the fixup as currently layed
605   /// out.
606   /// \return Whether the fixup value was fully resolved. This is true if the
607   /// \arg Value result is fixed, otherwise the value may change due to
608   /// relocation.
609   bool EvaluateFixup(const MCAsmLayout &Layout,
610                      const MCFixup &Fixup, const MCFragment *DF,
611                      MCValue &Target, uint64_t &Value) const;
612
613   /// Check whether a fixup can be satisfied, or whether it needs to be relaxed
614   /// (increased in size, in order to hold its value correctly).
615   bool FixupNeedsRelaxation(const MCFixup &Fixup, const MCFragment *DF,
616                             const MCAsmLayout &Layout) const;
617
618   /// Check whether the given fragment needs relaxation.
619   bool FragmentNeedsRelaxation(const MCInstFragment *IF,
620                                const MCAsmLayout &Layout) const;
621
622   /// Compute the effective fragment size assuming it is layed out at the given
623   /// \arg SectionAddress and \arg FragmentOffset.
624   uint64_t ComputeFragmentSize(MCAsmLayout &Layout, const MCFragment &F,
625                                uint64_t SectionAddress,
626                                uint64_t FragmentOffset) const;
627
628   /// LayoutOnce - Perform one layout iteration and return true if any offsets
629   /// were adjusted.
630   bool LayoutOnce(MCAsmLayout &Layout);
631
632   /// FinishLayout - Finalize a layout, including fragment lowering.
633   void FinishLayout(MCAsmLayout &Layout);
634
635 public:
636   /// Find the symbol which defines the atom containing the given symbol, or
637   /// null if there is no such symbol.
638   const MCSymbolData *getAtom(const MCAsmLayout &Layout,
639                               const MCSymbolData *Symbol) const;
640
641   /// Check whether a particular symbol is visible to the linker and is required
642   /// in the symbol table, or whether it can be discarded by the assembler. This
643   /// also effects whether the assembler treats the label as potentially
644   /// defining a separate atom.
645   bool isSymbolLinkerVisible(const MCSymbol &SD) const;
646
647   /// Emit the section contents using the given object writer.
648   //
649   // FIXME: Should MCAssembler always have a reference to the object writer?
650   void WriteSectionData(const MCSectionData *Section, const MCAsmLayout &Layout,
651                         MCObjectWriter *OW) const;
652
653 public:
654   /// Construct a new assembler instance.
655   ///
656   /// \arg OS - The stream to output to.
657   //
658   // FIXME: How are we going to parameterize this? Two obvious options are stay
659   // concrete and require clients to pass in a target like object. The other
660   // option is to make this abstract, and have targets provide concrete
661   // implementations as we do with AsmParser.
662   MCAssembler(MCContext &_Context, TargetAsmBackend &_Backend,
663               MCCodeEmitter &_Emitter, raw_ostream &OS);
664   ~MCAssembler();
665
666   MCContext &getContext() const { return Context; }
667
668   TargetAsmBackend &getBackend() const { return Backend; }
669
670   MCCodeEmitter &getEmitter() const { return Emitter; }
671
672   /// Finish - Do final processing and write the object to the output stream.
673   /// \arg Writer is used for custom object writer (as the MCJIT does),
674   /// if not specified it is automatically created from backend.
675   void Finish(MCObjectWriter *Writer = 0);
676
677   // FIXME: This does not belong here.
678   bool getSubsectionsViaSymbols() const {
679     return SubsectionsViaSymbols;
680   }
681   void setSubsectionsViaSymbols(bool Value) {
682     SubsectionsViaSymbols = Value;
683   }
684
685   bool getRelaxAll() const { return RelaxAll; }
686   void setRelaxAll(bool Value) { RelaxAll = Value; }
687
688   /// @name Section List Access
689   /// @{
690
691   const SectionDataListType &getSectionList() const { return Sections; }
692   SectionDataListType &getSectionList() { return Sections; }
693
694   iterator begin() { return Sections.begin(); }
695   const_iterator begin() const { return Sections.begin(); }
696
697   iterator end() { return Sections.end(); }
698   const_iterator end() const { return Sections.end(); }
699
700   size_t size() const { return Sections.size(); }
701
702   /// @}
703   /// @name Symbol List Access
704   /// @{
705
706   const SymbolDataListType &getSymbolList() const { return Symbols; }
707   SymbolDataListType &getSymbolList() { return Symbols; }
708
709   symbol_iterator symbol_begin() { return Symbols.begin(); }
710   const_symbol_iterator symbol_begin() const { return Symbols.begin(); }
711
712   symbol_iterator symbol_end() { return Symbols.end(); }
713   const_symbol_iterator symbol_end() const { return Symbols.end(); }
714
715   size_t symbol_size() const { return Symbols.size(); }
716
717   /// @}
718   /// @name Indirect Symbol List Access
719   /// @{
720
721   // FIXME: This is a total hack, this should not be here. Once things are
722   // factored so that the streamer has direct access to the .o writer, it can
723   // disappear.
724   std::vector<IndirectSymbolData> &getIndirectSymbols() {
725     return IndirectSymbols;
726   }
727
728   indirect_symbol_iterator indirect_symbol_begin() {
729     return IndirectSymbols.begin();
730   }
731   const_indirect_symbol_iterator indirect_symbol_begin() const {
732     return IndirectSymbols.begin();
733   }
734
735   indirect_symbol_iterator indirect_symbol_end() {
736     return IndirectSymbols.end();
737   }
738   const_indirect_symbol_iterator indirect_symbol_end() const {
739     return IndirectSymbols.end();
740   }
741
742   size_t indirect_symbol_size() const { return IndirectSymbols.size(); }
743
744   /// @}
745   /// @name Backend Data Access
746   /// @{
747
748   MCSectionData &getSectionData(const MCSection &Section) const {
749     MCSectionData *Entry = SectionMap.lookup(&Section);
750     assert(Entry && "Missing section data!");
751     return *Entry;
752   }
753
754   MCSectionData &getOrCreateSectionData(const MCSection &Section,
755                                         bool *Created = 0) {
756     MCSectionData *&Entry = SectionMap[&Section];
757
758     if (Created) *Created = !Entry;
759     if (!Entry)
760       Entry = new MCSectionData(Section, this);
761
762     return *Entry;
763   }
764
765   MCSymbolData &getSymbolData(const MCSymbol &Symbol) const {
766     MCSymbolData *Entry = SymbolMap.lookup(&Symbol);
767     assert(Entry && "Missing symbol data!");
768     return *Entry;
769   }
770
771   MCSymbolData &getOrCreateSymbolData(const MCSymbol &Symbol,
772                                       bool *Created = 0) {
773     MCSymbolData *&Entry = SymbolMap[&Symbol];
774
775     if (Created) *Created = !Entry;
776     if (!Entry)
777       Entry = new MCSymbolData(Symbol, 0, 0, this);
778
779     return *Entry;
780   }
781
782   /// @}
783
784   void dump();
785 };
786
787 } // end namespace llvm
788
789 #endif