5fd67b25b2a6c87579269ad2ed523b1fff3528ca
[oota-llvm.git] / lib / MC / MCAssembler.cpp
1 //===- lib/MC/MCAssembler.cpp - Assembler Backend Implementation ----------===//
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 #define DEBUG_TYPE "assembler"
11 #include "llvm/MC/MCAssembler.h"
12 #include "llvm/MC/MCSectionMachO.h"
13 #include "llvm/Target/TargetMachOWriterInfo.h"
14 #include "llvm/ADT/DenseMap.h"
15 #include "llvm/ADT/SmallString.h"
16 #include "llvm/ADT/Statistic.h"
17 #include "llvm/ADT/StringMap.h"
18 #include "llvm/ADT/Twine.h"
19 #include "llvm/Support/ErrorHandling.h"
20 #include "llvm/Support/raw_ostream.h"
21 #include <vector>
22 using namespace llvm;
23
24 class MachObjectWriter;
25
26 STATISTIC(EmittedFragments, "Number of emitted assembler fragments");
27
28 static void WriteFileData(raw_ostream &OS, const MCSectionData &SD,
29                           MachObjectWriter &MOW);
30
31 class MachObjectWriter {
32   // See <mach-o/loader.h>.
33   enum {
34     Header_Magic32 = 0xFEEDFACE,
35     Header_Magic64 = 0xFEEDFACF
36   };
37   
38   static const unsigned Header32Size = 28;
39   static const unsigned Header64Size = 32;
40   static const unsigned SegmentLoadCommand32Size = 56;
41   static const unsigned Section32Size = 68;
42   static const unsigned SymtabLoadCommandSize = 24;
43   static const unsigned DysymtabLoadCommandSize = 80;
44   static const unsigned Nlist32Size = 12;
45   static const unsigned RelocationInfoSize = 8;
46
47   enum HeaderFileType {
48     HFT_Object = 0x1
49   };
50
51   enum HeaderFlags {
52     HF_SubsectionsViaSymbols = 0x2000
53   };
54
55   enum LoadCommandType {
56     LCT_Segment = 0x1,
57     LCT_Symtab = 0x2,
58     LCT_Dysymtab = 0xb
59   };
60
61   // See <mach-o/nlist.h>.
62   enum SymbolTypeType {
63     STT_Undefined = 0x00,
64     STT_Absolute  = 0x02,
65     STT_Section   = 0x0e
66   };
67
68   enum SymbolTypeFlags {
69     // If any of these bits are set, then the entry is a stab entry number (see
70     // <mach-o/stab.h>. Otherwise the other masks apply.
71     STF_StabsEntryMask = 0xe0,
72
73     STF_TypeMask       = 0x0e,
74     STF_External       = 0x01,
75     STF_PrivateExtern  = 0x10
76   };
77
78   /// IndirectSymbolFlags - Flags for encoding special values in the indirect
79   /// symbol entry.
80   enum IndirectSymbolFlags {
81     ISF_Local    = 0x80000000,
82     ISF_Absolute = 0x40000000
83   };
84
85   /// RelocationFlags - Special flags for addresses.
86   enum RelocationFlags {
87     RF_Scattered = 0x80000000
88   };
89
90   enum RelocationInfoType {
91     RIT_Vanilla             = 0,
92     RIT_Pair                = 1,
93     RIT_Difference          = 2,
94     RIT_PreboundLazyPointer = 3,
95     RIT_LocalDifference     = 4
96   };
97
98   /// MachSymbolData - Helper struct for containing some precomputed information
99   /// on symbols.
100   struct MachSymbolData {
101     MCSymbolData *SymbolData;
102     uint64_t StringIndex;
103     uint8_t SectionIndex;
104
105     // Support lexicographic sorting.
106     bool operator<(const MachSymbolData &RHS) const {
107       const std::string &Name = SymbolData->getSymbol().getName();
108       return Name < RHS.SymbolData->getSymbol().getName();
109     }
110   };
111
112   raw_ostream &OS;
113   bool IsLSB;
114
115 public:
116   MachObjectWriter(raw_ostream &_OS, bool _IsLSB = true) 
117     : OS(_OS), IsLSB(_IsLSB) {
118   }
119
120   /// @name Helper Methods
121   /// @{
122
123   void Write8(uint8_t Value) {
124     OS << char(Value);
125   }
126
127   void Write16(uint16_t Value) {
128     if (IsLSB) {
129       Write8(uint8_t(Value >> 0));
130       Write8(uint8_t(Value >> 8));
131     } else {
132       Write8(uint8_t(Value >> 8));
133       Write8(uint8_t(Value >> 0));
134     }
135   }
136
137   void Write32(uint32_t Value) {
138     if (IsLSB) {
139       Write16(uint16_t(Value >> 0));
140       Write16(uint16_t(Value >> 16));
141     } else {
142       Write16(uint16_t(Value >> 16));
143       Write16(uint16_t(Value >> 0));
144     }
145   }
146
147   void Write64(uint64_t Value) {
148     if (IsLSB) {
149       Write32(uint32_t(Value >> 0));
150       Write32(uint32_t(Value >> 32));
151     } else {
152       Write32(uint32_t(Value >> 32));
153       Write32(uint32_t(Value >> 0));
154     }
155   }
156
157   void WriteZeros(unsigned N) {
158     const char Zeros[16] = { 0 };
159     
160     for (unsigned i = 0, e = N / 16; i != e; ++i)
161       OS << StringRef(Zeros, 16);
162     
163     OS << StringRef(Zeros, N % 16);
164   }
165
166   void WriteString(const StringRef &Str, unsigned ZeroFillSize = 0) {
167     OS << Str;
168     if (ZeroFillSize)
169       WriteZeros(ZeroFillSize - Str.size());
170   }
171
172   /// @}
173   
174   void WriteHeader32(unsigned NumLoadCommands, unsigned LoadCommandsSize,
175                      bool SubsectionsViaSymbols) {
176     uint32_t Flags = 0;
177
178     if (SubsectionsViaSymbols)
179       Flags |= HF_SubsectionsViaSymbols;
180
181     // struct mach_header (28 bytes)
182
183     uint64_t Start = OS.tell();
184     (void) Start;
185
186     Write32(Header_Magic32);
187
188     // FIXME: Support cputype.
189     Write32(TargetMachOWriterInfo::HDR_CPU_TYPE_I386);
190     // FIXME: Support cpusubtype.
191     Write32(TargetMachOWriterInfo::HDR_CPU_SUBTYPE_I386_ALL);
192     Write32(HFT_Object);
193     Write32(NumLoadCommands);    // Object files have a single load command, the
194                                  // segment.
195     Write32(LoadCommandsSize);
196     Write32(Flags);
197
198     assert(OS.tell() - Start == Header32Size);
199   }
200
201   /// WriteSegmentLoadCommand32 - Write a 32-bit segment load command.
202   ///
203   /// \arg NumSections - The number of sections in this segment.
204   /// \arg SectionDataSize - The total size of the sections.
205   void WriteSegmentLoadCommand32(unsigned NumSections,
206                                  uint64_t SectionDataStartOffset,
207                                  uint64_t SectionDataSize) {
208     // struct segment_command (56 bytes)
209
210     uint64_t Start = OS.tell();
211     (void) Start;
212
213     Write32(LCT_Segment);
214     Write32(SegmentLoadCommand32Size + NumSections * Section32Size);
215
216     WriteString("", 16);
217     Write32(0); // vmaddr
218     Write32(SectionDataSize); // vmsize
219     Write32(SectionDataStartOffset); // file offset
220     Write32(SectionDataSize); // file size
221     Write32(0x7); // maxprot
222     Write32(0x7); // initprot
223     Write32(NumSections);
224     Write32(0); // flags
225
226     assert(OS.tell() - Start == SegmentLoadCommand32Size);
227   }
228
229   void WriteSection32(const MCSectionData &SD, uint64_t FileOffset,
230                       uint64_t RelocationsStart, unsigned NumRelocations) {
231     // struct section (68 bytes)
232
233     uint64_t Start = OS.tell();
234     (void) Start;
235
236     // FIXME: cast<> support!
237     const MCSectionMachO &Section =
238       static_cast<const MCSectionMachO&>(SD.getSection());
239     WriteString(Section.getSectionName(), 16);
240     WriteString(Section.getSegmentName(), 16);
241     Write32(SD.getAddress()); // address
242     Write32(SD.getSize()); // size
243     Write32(FileOffset);
244
245     assert(isPowerOf2_32(SD.getAlignment()) && "Invalid alignment!");
246     Write32(Log2_32(SD.getAlignment()));
247     Write32(NumRelocations ? RelocationsStart : 0);
248     Write32(NumRelocations);
249     Write32(Section.getTypeAndAttributes());
250     Write32(0); // reserved1
251     Write32(Section.getStubSize()); // reserved2
252
253     assert(OS.tell() - Start == Section32Size);
254   }
255
256   void WriteSymtabLoadCommand(uint32_t SymbolOffset, uint32_t NumSymbols,
257                               uint32_t StringTableOffset,
258                               uint32_t StringTableSize) {
259     // struct symtab_command (24 bytes)
260
261     uint64_t Start = OS.tell();
262     (void) Start;
263
264     Write32(LCT_Symtab);
265     Write32(SymtabLoadCommandSize);
266     Write32(SymbolOffset);
267     Write32(NumSymbols);
268     Write32(StringTableOffset);
269     Write32(StringTableSize);
270
271     assert(OS.tell() - Start == SymtabLoadCommandSize);
272   }
273
274   void WriteDysymtabLoadCommand(uint32_t FirstLocalSymbol,
275                                 uint32_t NumLocalSymbols,
276                                 uint32_t FirstExternalSymbol,
277                                 uint32_t NumExternalSymbols,
278                                 uint32_t FirstUndefinedSymbol,
279                                 uint32_t NumUndefinedSymbols,
280                                 uint32_t IndirectSymbolOffset,
281                                 uint32_t NumIndirectSymbols) {
282     // struct dysymtab_command (80 bytes)
283
284     uint64_t Start = OS.tell();
285     (void) Start;
286
287     Write32(LCT_Dysymtab);
288     Write32(DysymtabLoadCommandSize);
289     Write32(FirstLocalSymbol);
290     Write32(NumLocalSymbols);
291     Write32(FirstExternalSymbol);
292     Write32(NumExternalSymbols);
293     Write32(FirstUndefinedSymbol);
294     Write32(NumUndefinedSymbols);
295     Write32(0); // tocoff
296     Write32(0); // ntoc
297     Write32(0); // modtaboff
298     Write32(0); // nmodtab
299     Write32(0); // extrefsymoff
300     Write32(0); // nextrefsyms
301     Write32(IndirectSymbolOffset);
302     Write32(NumIndirectSymbols);
303     Write32(0); // extreloff
304     Write32(0); // nextrel
305     Write32(0); // locreloff
306     Write32(0); // nlocrel
307
308     assert(OS.tell() - Start == DysymtabLoadCommandSize);
309   }
310
311   void WriteNlist32(MachSymbolData &MSD) {
312     MCSymbolData &Data = *MSD.SymbolData;
313     MCSymbol &Symbol = Data.getSymbol();
314     uint8_t Type = 0;
315
316     // Set the N_TYPE bits. See <mach-o/nlist.h>.
317     //
318     // FIXME: Are the prebound or indirect fields possible here?
319     if (Symbol.isUndefined())
320       Type = STT_Undefined;
321     else if (Symbol.isAbsolute())
322       Type = STT_Absolute;
323     else
324       Type = STT_Section;
325
326     // FIXME: Set STAB bits.
327
328     if (Data.isPrivateExtern())
329       Type |= STF_PrivateExtern;
330
331     // Set external bit.
332     if (Data.isExternal() || Symbol.isUndefined())
333       Type |= STF_External;
334
335     // struct nlist (12 bytes)
336
337     Write32(MSD.StringIndex);
338     Write8(Type);
339     Write8(MSD.SectionIndex);
340     
341     // The Mach-O streamer uses the lowest 16-bits of the flags for the 'desc'
342     // value.
343     Write16(Data.getFlags() & 0xFFFF);
344
345     // Write the symbol address.
346     uint32_t Address = 0;
347     if (Symbol.isDefined()) {
348       if (Symbol.isAbsolute()) {
349         llvm_unreachable("FIXME: Not yet implemented!");
350       } else {
351         Address = Data.getFragment()->getAddress() + Data.getOffset();
352       }
353     }
354     Write32(Address);
355   }
356
357   struct MachRelocationEntry {
358     uint32_t Word0;
359     uint32_t Word1;
360   };
361   void ComputeScatteredRelocationInfo(MCAssembler &Asm,
362                                       MCSectionData::Fixup &Fixup,
363                              DenseMap<const MCSymbol*,MCSymbolData*> &SymbolMap,
364                                      std::vector<MachRelocationEntry> &Relocs) {
365     uint32_t Address = Fixup.Fragment->getOffset() + Fixup.Offset;
366     unsigned IsPCRel = 0;
367     unsigned Type = RIT_Vanilla;
368
369     // See <reloc.h>.
370
371     const MCSymbol *A = Fixup.Value.getSymA();
372     MCSymbolData *SD = SymbolMap.lookup(A);
373     uint32_t Value = SD->getFragment()->getAddress() + SD->getOffset();
374     uint32_t Value2 = 0;
375
376     if (const MCSymbol *B = Fixup.Value.getSymB()) {
377       Type = RIT_LocalDifference;
378
379       MCSymbolData *SD = SymbolMap.lookup(B);
380       Value2 = SD->getFragment()->getAddress() + SD->getOffset();
381     }
382
383     unsigned Log2Size = Log2_32(Fixup.Size);
384     assert((1U << Log2Size) == Fixup.Size && "Invalid fixup size!");
385
386     // The value which goes in the fixup is current value of the expression.
387     Fixup.FixedValue = Value - Value2 + Fixup.Value.getConstant();
388
389     MachRelocationEntry MRE;
390     MRE.Word0 = ((Address   <<  0) |
391                  (Type      << 24) |
392                  (Log2Size  << 28) |
393                  (IsPCRel   << 30) |
394                  RF_Scattered);
395     MRE.Word1 = Value;
396     Relocs.push_back(MRE);
397
398     if (Type == RIT_LocalDifference) {
399       Type = RIT_Pair;
400
401       MachRelocationEntry MRE;
402       MRE.Word0 = ((0         <<  0) |
403                    (Type      << 24) |
404                    (Log2Size  << 28) |
405                    (0   << 30) |
406                    RF_Scattered);
407       MRE.Word1 = Value2;
408       Relocs.push_back(MRE);
409     }
410   }
411
412   void ComputeRelocationInfo(MCAssembler &Asm,
413                              MCSectionData::Fixup &Fixup,
414                              DenseMap<const MCSymbol*,MCSymbolData*> &SymbolMap,
415                              std::vector<MachRelocationEntry> &Relocs) {
416     // If this is a local symbol plus an offset or a difference, then we need a
417     // scattered relocation entry.
418     if (Fixup.Value.getSymB()) // a - b
419       return ComputeScatteredRelocationInfo(Asm, Fixup, SymbolMap, Relocs);
420     if (Fixup.Value.getSymA() && Fixup.Value.getConstant())
421       if (!Fixup.Value.getSymA()->isUndefined())
422         return ComputeScatteredRelocationInfo(Asm, Fixup, SymbolMap, Relocs);
423         
424     // See <reloc.h>.
425     uint32_t Address = Fixup.Fragment->getOffset() + Fixup.Offset;
426     uint32_t Value = 0;
427     unsigned Index = 0;
428     unsigned IsPCRel = 0;
429     unsigned IsExtern = 0;
430     unsigned Type = 0;
431
432     if (Fixup.Value.isAbsolute()) { // constant
433       // SymbolNum of 0 indicates the absolute section.
434       Type = RIT_Vanilla;
435       Value = 0;
436       llvm_unreachable("FIXME: Not yet implemented!");
437     } else {
438       const MCSymbol *Symbol = Fixup.Value.getSymA();
439       MCSymbolData *SD = SymbolMap.lookup(Symbol);
440       
441       if (Symbol->isUndefined()) {
442         IsExtern = 1;
443         Index = SD->getIndex();
444         Value = 0;
445       } else {
446         // The index is the section ordinal.
447         //
448         // FIXME: O(N)
449         Index = 1;
450         for (MCAssembler::iterator it = Asm.begin(),
451                ie = Asm.end(); it != ie; ++it, ++Index)
452           if (&*it == SD->getFragment()->getParent())
453             break;
454         Value = SD->getFragment()->getAddress() + SD->getOffset();
455       }
456
457       Type = RIT_Vanilla;
458     }
459
460     // The value which goes in the fixup is current value of the expression.
461     Fixup.FixedValue = Value + Fixup.Value.getConstant();
462
463     unsigned Log2Size = Log2_32(Fixup.Size);
464     assert((1U << Log2Size) == Fixup.Size && "Invalid fixup size!");
465
466     // struct relocation_info (8 bytes)
467     MachRelocationEntry MRE;
468     MRE.Word0 = Address;
469     MRE.Word1 = ((Index     <<  0) |
470                  (IsPCRel   << 24) |
471                  (Log2Size  << 25) |
472                  (IsExtern  << 27) |
473                  (Type      << 28));
474     Relocs.push_back(MRE);
475   }
476   
477   void BindIndirectSymbols(MCAssembler &Asm,
478                            DenseMap<const MCSymbol*,MCSymbolData*> &SymbolMap) {
479     // This is the point where 'as' creates actual symbols for indirect symbols
480     // (in the following two passes). It would be easier for us to do this
481     // sooner when we see the attribute, but that makes getting the order in the
482     // symbol table much more complicated than it is worth.
483     //
484     // FIXME: Revisit this when the dust settles.
485
486     // Bind non lazy symbol pointers first.
487     for (MCAssembler::indirect_symbol_iterator it = Asm.indirect_symbol_begin(),
488            ie = Asm.indirect_symbol_end(); it != ie; ++it) {
489       // FIXME: cast<> support!
490       const MCSectionMachO &Section =
491         static_cast<const MCSectionMachO&>(it->SectionData->getSection());
492
493       unsigned Type =
494         Section.getTypeAndAttributes() & MCSectionMachO::SECTION_TYPE;
495       if (Type != MCSectionMachO::S_NON_LAZY_SYMBOL_POINTERS)
496         continue;
497
498       MCSymbolData *&Entry = SymbolMap[it->Symbol];
499       if (!Entry)
500         Entry = new MCSymbolData(*it->Symbol, 0, 0, &Asm);
501     }
502
503     // Then lazy symbol pointers and symbol stubs.
504     for (MCAssembler::indirect_symbol_iterator it = Asm.indirect_symbol_begin(),
505            ie = Asm.indirect_symbol_end(); it != ie; ++it) {
506       // FIXME: cast<> support!
507       const MCSectionMachO &Section =
508         static_cast<const MCSectionMachO&>(it->SectionData->getSection());
509
510       unsigned Type =
511         Section.getTypeAndAttributes() & MCSectionMachO::SECTION_TYPE;
512       if (Type != MCSectionMachO::S_LAZY_SYMBOL_POINTERS &&
513           Type != MCSectionMachO::S_SYMBOL_STUBS)
514         continue;
515
516       MCSymbolData *&Entry = SymbolMap[it->Symbol];
517       if (!Entry) {
518         Entry = new MCSymbolData(*it->Symbol, 0, 0, &Asm);
519
520         // Set the symbol type to undefined lazy, but only on construction.
521         //
522         // FIXME: Do not hardcode.
523         Entry->setFlags(Entry->getFlags() | 0x0001);
524       }
525     }
526   }
527
528   /// ComputeSymbolTable - Compute the symbol table data
529   ///
530   /// \param StringTable [out] - The string table data.
531   /// \param StringIndexMap [out] - Map from symbol names to offsets in the
532   /// string table.
533   void ComputeSymbolTable(MCAssembler &Asm, SmallString<256> &StringTable,
534                           std::vector<MachSymbolData> &LocalSymbolData,
535                           std::vector<MachSymbolData> &ExternalSymbolData,
536                           std::vector<MachSymbolData> &UndefinedSymbolData) {
537     // Build section lookup table.
538     DenseMap<const MCSection*, uint8_t> SectionIndexMap;
539     unsigned Index = 1;
540     for (MCAssembler::iterator it = Asm.begin(),
541            ie = Asm.end(); it != ie; ++it, ++Index)
542       SectionIndexMap[&it->getSection()] = Index;
543     assert(Index <= 256 && "Too many sections!");
544
545     // Index 0 is always the empty string.
546     StringMap<uint64_t> StringIndexMap;
547     StringTable += '\x00';
548
549     // Build the symbol arrays and the string table, but only for non-local
550     // symbols.
551     //
552     // The particular order that we collect the symbols and create the string
553     // table, then sort the symbols is chosen to match 'as'. Even though it
554     // doesn't matter for correctness, this is important for letting us diff .o
555     // files.
556     for (MCAssembler::symbol_iterator it = Asm.symbol_begin(),
557            ie = Asm.symbol_end(); it != ie; ++it) {
558       MCSymbol &Symbol = it->getSymbol();
559
560       // Ignore assembler temporaries.
561       if (it->getSymbol().isTemporary())
562         continue;
563
564       if (!it->isExternal() && !Symbol.isUndefined())
565         continue;
566
567       uint64_t &Entry = StringIndexMap[Symbol.getName()];
568       if (!Entry) {
569         Entry = StringTable.size();
570         StringTable += Symbol.getName();
571         StringTable += '\x00';
572       }
573
574       MachSymbolData MSD;
575       MSD.SymbolData = it;
576       MSD.StringIndex = Entry;
577
578       if (Symbol.isUndefined()) {
579         MSD.SectionIndex = 0;
580         UndefinedSymbolData.push_back(MSD);
581       } else if (Symbol.isAbsolute()) {
582         MSD.SectionIndex = 0;
583         ExternalSymbolData.push_back(MSD);
584       } else {
585         MSD.SectionIndex = SectionIndexMap.lookup(&Symbol.getSection());
586         assert(MSD.SectionIndex && "Invalid section index!");
587         ExternalSymbolData.push_back(MSD);
588       }
589     }
590
591     // Now add the data for local symbols.
592     for (MCAssembler::symbol_iterator it = Asm.symbol_begin(),
593            ie = Asm.symbol_end(); it != ie; ++it) {
594       MCSymbol &Symbol = it->getSymbol();
595
596       // Ignore assembler temporaries.
597       if (it->getSymbol().isTemporary())
598         continue;
599
600       if (it->isExternal() || Symbol.isUndefined())
601         continue;
602
603       uint64_t &Entry = StringIndexMap[Symbol.getName()];
604       if (!Entry) {
605         Entry = StringTable.size();
606         StringTable += Symbol.getName();
607         StringTable += '\x00';
608       }
609
610       MachSymbolData MSD;
611       MSD.SymbolData = it;
612       MSD.StringIndex = Entry;
613
614       if (Symbol.isAbsolute()) {
615         MSD.SectionIndex = 0;
616         LocalSymbolData.push_back(MSD);
617       } else {
618         MSD.SectionIndex = SectionIndexMap.lookup(&Symbol.getSection());
619         assert(MSD.SectionIndex && "Invalid section index!");
620         LocalSymbolData.push_back(MSD);
621       }
622     }
623
624     // External and undefined symbols are required to be in lexicographic order.
625     std::sort(ExternalSymbolData.begin(), ExternalSymbolData.end());
626     std::sort(UndefinedSymbolData.begin(), UndefinedSymbolData.end());
627
628     // Set the symbol indices.
629     Index = 0;
630     for (unsigned i = 0, e = LocalSymbolData.size(); i != e; ++i)
631       LocalSymbolData[i].SymbolData->setIndex(Index++);
632     for (unsigned i = 0, e = ExternalSymbolData.size(); i != e; ++i)
633       ExternalSymbolData[i].SymbolData->setIndex(Index++);
634     for (unsigned i = 0, e = UndefinedSymbolData.size(); i != e; ++i)
635       UndefinedSymbolData[i].SymbolData->setIndex(Index++);
636
637     // The string table is padded to a multiple of 4.
638     //
639     // FIXME: Check to see if this varies per arch.
640     while (StringTable.size() % 4)
641       StringTable += '\x00';
642   }
643
644   void WriteObject(MCAssembler &Asm) {
645     unsigned NumSections = Asm.size();
646
647     // Compute the symbol -> symbol data map.
648     //
649     // FIXME: This should not be here.
650     DenseMap<const MCSymbol*, MCSymbolData *> SymbolMap;
651     for (MCAssembler::symbol_iterator it = Asm.symbol_begin(),
652            ie = Asm.symbol_end(); it != ie; ++it)
653       SymbolMap[&it->getSymbol()] = it;
654
655     // Create symbol data for any indirect symbols.
656     BindIndirectSymbols(Asm, SymbolMap);
657
658     // Compute symbol table information.
659     SmallString<256> StringTable;
660     std::vector<MachSymbolData> LocalSymbolData;
661     std::vector<MachSymbolData> ExternalSymbolData;
662     std::vector<MachSymbolData> UndefinedSymbolData;
663     unsigned NumSymbols = Asm.symbol_size();
664
665     // No symbol table command is written if there are no symbols.
666     if (NumSymbols)
667       ComputeSymbolTable(Asm, StringTable, LocalSymbolData, ExternalSymbolData,
668                          UndefinedSymbolData);
669   
670     // The section data starts after the header, the segment load command (and
671     // section headers) and the symbol table.
672     unsigned NumLoadCommands = 1;
673     uint64_t LoadCommandsSize =
674       SegmentLoadCommand32Size + NumSections * Section32Size;
675
676     // Add the symbol table load command sizes, if used.
677     if (NumSymbols) {
678       NumLoadCommands += 2;
679       LoadCommandsSize += SymtabLoadCommandSize + DysymtabLoadCommandSize;
680     }
681
682     uint64_t SectionDataStart = Header32Size + LoadCommandsSize;
683     uint64_t SectionDataEnd = SectionDataStart;
684     uint64_t SectionDataSize = 0;
685     if (!Asm.getSectionList().empty()) {
686       MCSectionData &SD = Asm.getSectionList().back();
687       SectionDataSize = SD.getAddress() + SD.getSize();
688       SectionDataEnd = SectionDataStart + SD.getAddress() + SD.getFileSize();
689     }
690
691     // Write the prolog, starting with the header and load command...
692     WriteHeader32(NumLoadCommands, LoadCommandsSize,
693                   Asm.getSubsectionsViaSymbols());
694     WriteSegmentLoadCommand32(NumSections, SectionDataStart, SectionDataSize);
695   
696     // ... and then the section headers.
697     // 
698     // We also compute the section relocations while we do this. Note that
699     // compute relocation info will also update the fixup to have the correct
700     // value; this will be overwrite the appropriate data in the fragment when
701     // it is written.
702     std::vector<MachRelocationEntry> RelocInfos;
703     uint64_t RelocTableEnd = SectionDataEnd;
704     for (MCAssembler::iterator it = Asm.begin(), ie = Asm.end(); it != ie;
705          ++it) {
706       MCSectionData &SD = *it;
707
708       // The assembler writes relocations in the reverse order they were seen.
709       //
710       // FIXME: It is probably more complicated than this.
711       unsigned NumRelocsStart = RelocInfos.size();
712       for (unsigned i = 0, e = SD.fixup_size(); i != e; ++i)
713         ComputeRelocationInfo(Asm, SD.getFixups()[e - i - 1], SymbolMap,
714                               RelocInfos);
715
716       unsigned NumRelocs = RelocInfos.size() - NumRelocsStart;
717       uint64_t SectionStart = SectionDataStart + SD.getAddress();
718       WriteSection32(SD, SectionStart, RelocTableEnd, NumRelocs);
719       RelocTableEnd += NumRelocs * RelocationInfoSize;
720     }
721     
722     // Write the symbol table load command, if used.
723     if (NumSymbols) {
724       unsigned FirstLocalSymbol = 0;
725       unsigned NumLocalSymbols = LocalSymbolData.size();
726       unsigned FirstExternalSymbol = FirstLocalSymbol + NumLocalSymbols;
727       unsigned NumExternalSymbols = ExternalSymbolData.size();
728       unsigned FirstUndefinedSymbol = FirstExternalSymbol + NumExternalSymbols;
729       unsigned NumUndefinedSymbols = UndefinedSymbolData.size();
730       unsigned NumIndirectSymbols = Asm.indirect_symbol_size();
731       unsigned NumSymTabSymbols =
732         NumLocalSymbols + NumExternalSymbols + NumUndefinedSymbols;
733       uint64_t IndirectSymbolSize = NumIndirectSymbols * 4;
734       uint64_t IndirectSymbolOffset = 0;
735
736       // If used, the indirect symbols are written after the section data.
737       if (NumIndirectSymbols)
738         IndirectSymbolOffset = RelocTableEnd;
739
740       // The symbol table is written after the indirect symbol data.
741       uint64_t SymbolTableOffset = RelocTableEnd + IndirectSymbolSize;
742
743       // The string table is written after symbol table.
744       uint64_t StringTableOffset =
745         SymbolTableOffset + NumSymTabSymbols * Nlist32Size;
746       WriteSymtabLoadCommand(SymbolTableOffset, NumSymTabSymbols,
747                              StringTableOffset, StringTable.size());
748
749       WriteDysymtabLoadCommand(FirstLocalSymbol, NumLocalSymbols,
750                                FirstExternalSymbol, NumExternalSymbols,
751                                FirstUndefinedSymbol, NumUndefinedSymbols,
752                                IndirectSymbolOffset, NumIndirectSymbols);
753     }
754
755     // Write the actual section data.
756     for (MCAssembler::iterator it = Asm.begin(), ie = Asm.end(); it != ie; ++it)
757       WriteFileData(OS, *it, *this);
758
759     // Write the relocation entries.
760     for (unsigned i = 0, e = RelocInfos.size(); i != e; ++i) {
761       Write32(RelocInfos[i].Word0);
762       Write32(RelocInfos[i].Word1);
763     }
764
765     // Write the symbol table data, if used.
766     if (NumSymbols) {
767       // Write the indirect symbol entries.
768       for (MCAssembler::indirect_symbol_iterator
769              it = Asm.indirect_symbol_begin(),
770              ie = Asm.indirect_symbol_end(); it != ie; ++it) {
771         // Indirect symbols in the non lazy symbol pointer section have some
772         // special handling.
773         const MCSectionMachO &Section =
774           static_cast<const MCSectionMachO&>(it->SectionData->getSection());
775         unsigned Type =
776           Section.getTypeAndAttributes() & MCSectionMachO::SECTION_TYPE;
777         if (Type == MCSectionMachO::S_NON_LAZY_SYMBOL_POINTERS) {
778           // If this symbol is defined and internal, mark it as such.
779           if (it->Symbol->isDefined() &&
780               !SymbolMap.lookup(it->Symbol)->isExternal()) {
781             uint32_t Flags = ISF_Local;
782             if (it->Symbol->isAbsolute())
783               Flags |= ISF_Absolute;
784             Write32(Flags);
785             continue;
786           }
787         }
788
789         Write32(SymbolMap[it->Symbol]->getIndex());
790       }
791
792       // FIXME: Check that offsets match computed ones.
793
794       // Write the symbol table entries.
795       for (unsigned i = 0, e = LocalSymbolData.size(); i != e; ++i)
796         WriteNlist32(LocalSymbolData[i]);
797       for (unsigned i = 0, e = ExternalSymbolData.size(); i != e; ++i)
798         WriteNlist32(ExternalSymbolData[i]);
799       for (unsigned i = 0, e = UndefinedSymbolData.size(); i != e; ++i)
800         WriteNlist32(UndefinedSymbolData[i]);
801
802       // Write the string table.
803       OS << StringTable.str();
804     }
805   }
806 };
807
808 /* *** */
809
810 MCFragment::MCFragment() : Kind(FragmentType(~0)) {
811 }
812
813 MCFragment::MCFragment(FragmentType _Kind, MCSectionData *_Parent)
814   : Kind(_Kind),
815     Parent(_Parent),
816     FileSize(~UINT64_C(0))
817 {
818   if (Parent)
819     Parent->getFragmentList().push_back(this);
820 }
821
822 MCFragment::~MCFragment() {
823 }
824
825 uint64_t MCFragment::getAddress() const {
826   assert(getParent() && "Missing Section!");
827   return getParent()->getAddress() + Offset;
828 }
829
830 /* *** */
831
832 MCSectionData::MCSectionData() : Section(0) {}
833
834 MCSectionData::MCSectionData(const MCSection &_Section, MCAssembler *A)
835   : Section(&_Section),
836     Alignment(1),
837     Address(~UINT64_C(0)),
838     Size(~UINT64_C(0)),
839     FileSize(~UINT64_C(0)),
840     LastFixupLookup(~0)
841 {
842   if (A)
843     A->getSectionList().push_back(this);
844 }
845
846 const MCSectionData::Fixup *
847 MCSectionData::LookupFixup(const MCFragment *Fragment, uint64_t Offset) const {
848   // Use a one level cache to turn the common case of accessing the fixups in
849   // order into O(1) instead of O(N).
850   unsigned i = LastFixupLookup, Count = Fixups.size(), End = Fixups.size();
851   if (i >= End)
852     i = 0;
853   while (Count--) {
854     const Fixup &F = Fixups[i];
855     if (F.Fragment == Fragment && F.Offset == Offset) {
856       LastFixupLookup = i;
857       return &F;
858     }
859
860     ++i;
861     if (i == End)
862       i = 0;
863   }
864
865   return 0;
866 }
867                                                        
868 /* *** */
869
870 MCSymbolData::MCSymbolData() : Symbol(*(MCSymbol*)0) {}
871
872 MCSymbolData::MCSymbolData(MCSymbol &_Symbol, MCFragment *_Fragment,
873                            uint64_t _Offset, MCAssembler *A)
874   : Symbol(_Symbol), Fragment(_Fragment), Offset(_Offset),
875     IsExternal(false), IsPrivateExtern(false), Flags(0), Index(0)
876 {
877   if (A)
878     A->getSymbolList().push_back(this);
879 }
880
881 /* *** */
882
883 MCAssembler::MCAssembler(raw_ostream &_OS)
884   : OS(_OS),
885     SubsectionsViaSymbols(false)
886 {
887 }
888
889 MCAssembler::~MCAssembler() {
890 }
891
892 void MCAssembler::LayoutSection(MCSectionData &SD, unsigned NextAlign) {
893   uint64_t Address = SD.getAddress();
894
895   for (MCSectionData::iterator it = SD.begin(), ie = SD.end(); it != ie; ++it) {
896     MCFragment &F = *it;
897
898     F.setOffset(Address - SD.getAddress());
899
900     // Evaluate fragment size.
901     switch (F.getKind()) {
902     case MCFragment::FT_Align: {
903       MCAlignFragment &AF = cast<MCAlignFragment>(F);
904       
905       uint64_t Size = RoundUpToAlignment(Address, AF.getAlignment()) - Address;
906       if (Size > AF.getMaxBytesToEmit())
907         AF.setFileSize(0);
908       else
909         AF.setFileSize(Size);
910       break;
911     }
912
913     case MCFragment::FT_Data:
914       F.setFileSize(F.getMaxFileSize());
915       break;
916
917     case MCFragment::FT_Fill: {
918       MCFillFragment &FF = cast<MCFillFragment>(F);
919
920       F.setFileSize(F.getMaxFileSize());
921
922       // If the fill value is constant, thats it.
923       if (FF.getValue().isAbsolute())
924         break;
925
926       // Otherwise, add fixups for the values.
927       for (uint64_t i = 0, e = FF.getCount(); i != e; ++i) {
928         MCSectionData::Fixup Fix(F, i * FF.getValueSize(),
929                                  FF.getValue(),FF.getValueSize());
930         SD.getFixups().push_back(Fix);
931       }
932       break;
933     }
934
935     case MCFragment::FT_Org: {
936       MCOrgFragment &OF = cast<MCOrgFragment>(F);
937
938       if (!OF.getOffset().isAbsolute())
939         llvm_unreachable("FIXME: Not yet implemented!");
940       uint64_t OrgOffset = OF.getOffset().getConstant();
941       uint64_t Offset = Address - SD.getAddress();
942
943       // FIXME: We need a way to communicate this error.
944       if (OrgOffset < Offset)
945         llvm_report_error("invalid .org offset '" + Twine(OrgOffset) + 
946                           "' (at offset '" + Twine(Offset) + "'");
947         
948       F.setFileSize(OrgOffset - Offset);
949       break;
950     }      
951     }
952
953     Address += F.getFileSize();
954   }
955
956   // Set the section sizes.
957   SD.setSize(Address - SD.getAddress());
958   SD.setFileSize(RoundUpToAlignment(Address, NextAlign) - SD.getAddress());
959 }
960
961 /// WriteFileData - Write the \arg F data to the output file.
962 static void WriteFileData(raw_ostream &OS, const MCFragment &F,
963                           MachObjectWriter &MOW) {
964   uint64_t Start = OS.tell();
965   (void) Start;
966     
967   ++EmittedFragments;
968
969   // FIXME: Embed in fragments instead?
970   switch (F.getKind()) {
971   case MCFragment::FT_Align: {
972     MCAlignFragment &AF = cast<MCAlignFragment>(F);
973     uint64_t Count = AF.getFileSize() / AF.getValueSize();
974
975     // FIXME: This error shouldn't actually occur (the front end should emit
976     // multiple .align directives to enforce the semantics it wants), but is
977     // severe enough that we want to report it. How to handle this?
978     if (Count * AF.getValueSize() != AF.getFileSize())
979       llvm_report_error("undefined .align directive, value size '" + 
980                         Twine(AF.getValueSize()) + 
981                         "' is not a divisor of padding size '" +
982                         Twine(AF.getFileSize()) + "'");
983
984     for (uint64_t i = 0; i != Count; ++i) {
985       switch (AF.getValueSize()) {
986       default:
987         assert(0 && "Invalid size!");
988       case 1: MOW.Write8 (uint8_t (AF.getValue())); break;
989       case 2: MOW.Write16(uint16_t(AF.getValue())); break;
990       case 4: MOW.Write32(uint32_t(AF.getValue())); break;
991       case 8: MOW.Write64(uint64_t(AF.getValue())); break;
992       }
993     }
994     break;
995   }
996
997   case MCFragment::FT_Data:
998     OS << cast<MCDataFragment>(F).getContents().str();
999     break;
1000
1001   case MCFragment::FT_Fill: {
1002     MCFillFragment &FF = cast<MCFillFragment>(F);
1003
1004     int64_t Value = 0;
1005     if (!FF.getValue().isAbsolute())
1006       Value = FF.getValue().getConstant();
1007     for (uint64_t i = 0, e = FF.getCount(); i != e; ++i) {
1008       if (!FF.getValue().isAbsolute()) {
1009         // Find the fixup.
1010         //
1011         // FIXME: Find a better way to write in the fixes.
1012         const MCSectionData::Fixup *Fixup =
1013           F.getParent()->LookupFixup(&F, i * FF.getValueSize());
1014         assert(Fixup && "Missing fixup for fill value!");
1015         Value = Fixup->FixedValue;
1016       }
1017
1018       switch (FF.getValueSize()) {
1019       default:
1020         assert(0 && "Invalid size!");
1021       case 1: MOW.Write8 (uint8_t (Value)); break;
1022       case 2: MOW.Write16(uint16_t(Value)); break;
1023       case 4: MOW.Write32(uint32_t(Value)); break;
1024       case 8: MOW.Write64(uint64_t(Value)); break;
1025       }
1026     }
1027     break;
1028   }
1029     
1030   case MCFragment::FT_Org: {
1031     MCOrgFragment &OF = cast<MCOrgFragment>(F);
1032
1033     for (uint64_t i = 0, e = OF.getFileSize(); i != e; ++i)
1034       MOW.Write8(uint8_t(OF.getValue()));
1035
1036     break;
1037   }
1038   }
1039
1040   assert(OS.tell() - Start == F.getFileSize());
1041 }
1042
1043 /// WriteFileData - Write the \arg SD data to the output file.
1044 static void WriteFileData(raw_ostream &OS, const MCSectionData &SD,
1045                           MachObjectWriter &MOW) {
1046   uint64_t Start = OS.tell();
1047   (void) Start;
1048       
1049   for (MCSectionData::const_iterator it = SD.begin(),
1050          ie = SD.end(); it != ie; ++it)
1051     WriteFileData(OS, *it, MOW);
1052
1053   // Add section padding.
1054   assert(SD.getFileSize() >= SD.getSize() && "Invalid section sizes!");
1055   MOW.WriteZeros(SD.getFileSize() - SD.getSize());
1056
1057   assert(OS.tell() - Start == SD.getFileSize());
1058 }
1059
1060 void MCAssembler::Finish() {
1061   // Layout the sections and fragments.
1062   uint64_t Address = 0;
1063   for (iterator it = begin(), ie = end(); it != ie;) {
1064     MCSectionData &SD = *it;
1065
1066     // Select the amount of padding alignment we need, based on either the next
1067     // sections alignment or the default alignment.
1068     //
1069     // FIXME: This should probably match the native word size.
1070     unsigned NextAlign = 4;
1071     ++it;
1072     if (it != ie)
1073       NextAlign = it->getAlignment();
1074
1075     // Layout the section fragments and its size.
1076     SD.setAddress(Address);
1077     LayoutSection(SD, NextAlign);
1078     Address += SD.getFileSize();
1079   }
1080
1081   // Write the object file.
1082   MachObjectWriter MOW(OS);
1083   MOW.WriteObject(*this);
1084
1085   OS.flush();
1086 }