MCMachOStreamer.cpp revision 821e3334ed3390d931f497300e6a5f1dc21bcfb3
1fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar//===- lib/MC/MCMachOStreamer.cpp - Mach-O Object Output ------------===// 2fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar// 3fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar// The LLVM Compiler Infrastructure 4fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar// 5fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar// This file is distributed under the University of Illinois Open Source 6fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar// License. See LICENSE.TXT for details. 7fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar// 8fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar//===----------------------------------------------------------------------===// 9fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 10fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar#include "llvm/MC/MCStreamer.h" 11fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 12fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar#include "llvm/MC/MCAssembler.h" 13fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar#include "llvm/MC/MCContext.h" 144fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar#include "llvm/MC/MCCodeEmitter.h" 158c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar#include "llvm/MC/MCExpr.h" 164fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar#include "llvm/MC/MCInst.h" 17fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar#include "llvm/MC/MCSection.h" 18fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar#include "llvm/MC/MCSymbol.h" 19821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar#include "llvm/MC/MCValue.h" 20fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar#include "llvm/Support/ErrorHandling.h" 214fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar#include "llvm/Support/raw_ostream.h" 22fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarusing namespace llvm; 23fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 24fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarnamespace { 25fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 26fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarclass MCMachOStreamer : public MCStreamer { 276aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar /// SymbolFlags - We store the value for the 'desc' symbol field in the lowest 286aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar /// 16 bits of the implementation defined flags. 296aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar enum SymbolFlags { // See <mach-o/nlist.h>. 306aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_DescFlagsMask = 0xFFFF, 316aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar 326aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // Reference type flags. 336aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_ReferenceTypeMask = 0x0007, 346aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_ReferenceTypeUndefinedNonLazy = 0x0000, 356aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_ReferenceTypeUndefinedLazy = 0x0001, 366aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_ReferenceTypeDefined = 0x0002, 376aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_ReferenceTypePrivateDefined = 0x0003, 386aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_ReferenceTypePrivateUndefinedNonLazy = 0x0004, 396aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_ReferenceTypePrivateUndefinedLazy = 0x0005, 406aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar 416aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // Other 'desc' flags. 426aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_NoDeadStrip = 0x0020, 436aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_WeakReference = 0x0040, 446aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SF_WeakDefinition = 0x0080 456aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar }; 466aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar 476aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbarprivate: 48fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar MCAssembler Assembler; 49fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 504fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar MCCodeEmitter *Emitter; 514fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar 52fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar MCSectionData *CurSectionData; 53fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 54fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar DenseMap<const MCSection*, MCSectionData*> SectionMap; 55f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar 56f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar DenseMap<const MCSymbol*, MCSymbolData*> SymbolMap; 57f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar 58f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbarprivate: 59f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar MCFragment *getCurrentFragment() const { 60f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar assert(CurSectionData && "No current section!"); 61f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar 62f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar if (!CurSectionData->empty()) 63f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar return &CurSectionData->getFragmentList().back(); 64f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar 65f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar return 0; 66f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar } 67f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar 680f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar MCSectionData &getSectionData(const MCSection &Section) { 690f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar MCSectionData *&Entry = SectionMap[&Section]; 700f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar 710f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar if (!Entry) 720f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar Entry = new MCSectionData(Section, &Assembler); 730f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar 740f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar return *Entry; 750f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar } 760f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar 77cb579b3338fe8d9e4424b138f597a4696cb89de3Daniel Dunbar MCSymbolData &getSymbolData(const MCSymbol &Symbol) { 78f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar MCSymbolData *&Entry = SymbolMap[&Symbol]; 79f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar 80f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar if (!Entry) 81f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar Entry = new MCSymbolData(Symbol, 0, 0, &Assembler); 82f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar 83f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar return *Entry; 84f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar } 85fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 86fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarpublic: 874fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar MCMachOStreamer(MCContext &Context, raw_ostream &_OS, MCCodeEmitter *_Emitter) 88a03a368acca1c5ea7eb7de7a4164cbd22308c82fDaniel Dunbar : MCStreamer(Context), Assembler(Context, _OS), Emitter(_Emitter), 894fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar CurSectionData(0) {} 90fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar ~MCMachOStreamer() {} 91fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 928c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar const MCExpr *AddValueSymbols(const MCExpr *Value) { 938c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar switch (Value->getKind()) { 948c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar case MCExpr::Constant: 958c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar break; 968c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar 978c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar case MCExpr::Binary: { 988c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar const MCBinaryExpr *BE = cast<MCBinaryExpr>(Value); 998c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar AddValueSymbols(BE->getLHS()); 1008c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar AddValueSymbols(BE->getRHS()); 1018c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar break; 1028c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar } 1038c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar 1048c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar case MCExpr::SymbolRef: 1058c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar getSymbolData(cast<MCSymbolRefExpr>(Value)->getSymbol()); 1068c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar break; 1078c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar 1088c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar case MCExpr::Unary: 1098c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar AddValueSymbols(cast<MCUnaryExpr>(Value)->getSubExpr()); 1108c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar break; 1118c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar } 1128c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar 1138c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar return Value; 1148c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar } 1158c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar 116fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar /// @name MCStreamer Interface 117fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar /// @{ 118fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 119fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar virtual void SwitchSection(const MCSection *Section); 120fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 121fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar virtual void EmitLabel(MCSymbol *Symbol); 122fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 123fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar virtual void EmitAssemblerFlag(AssemblerFlag Flag); 124fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 125821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar virtual void EmitAssignment(MCSymbol *Symbol, const MCExpr *Value); 126fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 127fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar virtual void EmitSymbolAttribute(MCSymbol *Symbol, SymbolAttr Attribute); 128fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 129fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar virtual void EmitSymbolDesc(MCSymbol *Symbol, unsigned DescValue); 130fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 131fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar virtual void EmitCommonSymbol(MCSymbol *Symbol, unsigned Size, 1327092c7e1dcf9d05741b400dd54bbd7d3419773b2Daniel Dunbar unsigned ByteAlignment); 133fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 1348751b94ffbd9c49df8949a37f78d6bd0be87b256Daniel Dunbar virtual void EmitZerofill(const MCSection *Section, MCSymbol *Symbol = 0, 1357092c7e1dcf9d05741b400dd54bbd7d3419773b2Daniel Dunbar unsigned Size = 0, unsigned ByteAlignment = 0); 136fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 137fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar virtual void EmitBytes(const StringRef &Data); 138fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 139821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar virtual void EmitValue(const MCExpr *Value, unsigned Size); 140fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 141fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar virtual void EmitValueToAlignment(unsigned ByteAlignment, int64_t Value = 0, 142fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar unsigned ValueSize = 1, 143fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar unsigned MaxBytesToEmit = 0); 144fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 145821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar virtual void EmitValueToOffset(const MCExpr *Offset, 146fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar unsigned char Value = 0); 147fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 148fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar virtual void EmitInstruction(const MCInst &Inst); 149fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 150fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar virtual void Finish(); 151fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 152fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar /// @} 153fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar}; 154fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 155fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} // end anonymous namespace. 156fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 157fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarvoid MCMachOStreamer::SwitchSection(const MCSection *Section) { 158fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar assert(Section && "Cannot switch to a null section!"); 159cda7f78233b889772e1454a1246130c576681bb8Chris Lattner 160cda7f78233b889772e1454a1246130c576681bb8Chris Lattner // If already in this section, then this is a noop. 161cda7f78233b889772e1454a1246130c576681bb8Chris Lattner if (Section == CurSection) return; 162fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 1630f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar CurSection = Section; 1640f5fa6955199cc7e0964524d73c8a9820d8f78c1Daniel Dunbar CurSectionData = &getSectionData(*Section); 165fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 166fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 167fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarvoid MCMachOStreamer::EmitLabel(MCSymbol *Symbol) { 1688906ff1b9dfde28f1ff00706643ca10843b26e01Daniel Dunbar assert(Symbol->isUndefined() && "Cannot define a symbol twice!"); 169fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 1705e835967dd5dda294d0ef3392f4c1d4a2260f532Daniel Dunbar // FIXME: We should also use offsets into Fill fragments. 171f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar MCDataFragment *F = dyn_cast_or_null<MCDataFragment>(getCurrentFragment()); 172f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar if (!F) 173f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar F = new MCDataFragment(CurSectionData); 174fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 175f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar MCSymbolData &SD = getSymbolData(*Symbol); 176f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar assert(!SD.getFragment() && "Unexpected fragment on symbol data!"); 177f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar SD.setFragment(F); 178f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar SD.setOffset(F->getContents().size()); 1796aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar 1806aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // This causes the reference type and weak reference flags to be cleared. 1816aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SD.setFlags(SD.getFlags() & ~(SF_WeakReference | SF_ReferenceTypeMask)); 182f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar 1838906ff1b9dfde28f1ff00706643ca10843b26e01Daniel Dunbar Symbol->setSection(*CurSection); 184fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 185fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 186fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarvoid MCMachOStreamer::EmitAssemblerFlag(AssemblerFlag Flag) { 1876009db486e7fba448ccb28dff676c012efade8f0Daniel Dunbar switch (Flag) { 1886009db486e7fba448ccb28dff676c012efade8f0Daniel Dunbar case SubsectionsViaSymbols: 1896009db486e7fba448ccb28dff676c012efade8f0Daniel Dunbar Assembler.setSubsectionsViaSymbols(true); 1908c3eaf46a1fb69004723ce78aaa82965d6474175Daniel Dunbar return; 1916009db486e7fba448ccb28dff676c012efade8f0Daniel Dunbar } 1928c3eaf46a1fb69004723ce78aaa82965d6474175Daniel Dunbar 1938c3eaf46a1fb69004723ce78aaa82965d6474175Daniel Dunbar assert(0 && "invalid assembler flag!"); 194fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 195fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 196821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbarvoid MCMachOStreamer::EmitAssignment(MCSymbol *Symbol, const MCExpr *Value) { 1978906ff1b9dfde28f1ff00706643ca10843b26e01Daniel Dunbar // Only absolute symbols can be redefined. 1988906ff1b9dfde28f1ff00706643ca10843b26e01Daniel Dunbar assert((Symbol->isUndefined() || Symbol->isAbsolute()) && 1998906ff1b9dfde28f1ff00706643ca10843b26e01Daniel Dunbar "Cannot define a symbol twice!"); 200fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 201fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar llvm_unreachable("FIXME: Not yet implemented!"); 202fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 203fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 204fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarvoid MCMachOStreamer::EmitSymbolAttribute(MCSymbol *Symbol, 205fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar SymbolAttr Attribute) { 2060c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar // Indirect symbols are handled differently, to match how 'as' handles 2070c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar // them. This makes writing matching .o files easier. 2080c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar if (Attribute == MCStreamer::IndirectSymbol) { 209ad7c3d55932f949e6bd428232999088a53f54a4fDaniel Dunbar // Note that we intentionally cannot use the symbol data here; this is 210ad7c3d55932f949e6bd428232999088a53f54a4fDaniel Dunbar // important for matching the string table that 'as' generates. 2110c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar IndirectSymbolData ISD; 2120c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar ISD.Symbol = Symbol; 2130c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar ISD.SectionData = CurSectionData; 2140c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar Assembler.getIndirectSymbols().push_back(ISD); 2150c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar return; 2160c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar } 2170c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar 2186aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // Adding a symbol attribute always introduces the symbol, note that an 2196aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // important side effect of calling getSymbolData here is to register the 2206aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // symbol with the assembler. 2216aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar MCSymbolData &SD = getSymbolData(*Symbol); 2226aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar 2236aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // The implementation of symbol attributes is designed to match 'as', but it 2246aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // leaves much to desired. It doesn't really make sense to arbitrarily add and 2256aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // remove flags, but 'as' allows this (in particular, see .desc). 2266aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // 2276aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // In the future it might be worth trying to make these operations more well 2286aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // defined. 2293edd9bb7a3da8526eb2f4a5dae2962a987d3d566Daniel Dunbar switch (Attribute) { 2300c7761b3f98fee270d73f5b9c440fe15e82af263Daniel Dunbar case MCStreamer::IndirectSymbol: 2316aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar case MCStreamer::Hidden: 2326aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar case MCStreamer::Internal: 2336aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar case MCStreamer::Protected: 2346aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar case MCStreamer::Weak: 2356aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar assert(0 && "Invalid symbol attribute for Mach-O!"); 2366aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar break; 2373edd9bb7a3da8526eb2f4a5dae2962a987d3d566Daniel Dunbar 2383edd9bb7a3da8526eb2f4a5dae2962a987d3d566Daniel Dunbar case MCStreamer::Global: 2398f4d146c340c9423271ebd7bb3fd32b880000bc9Daniel Dunbar SD.setExternal(true); 2403edd9bb7a3da8526eb2f4a5dae2962a987d3d566Daniel Dunbar break; 2416aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar 2426aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar case MCStreamer::LazyReference: 2436aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // FIXME: This requires -dynamic. 2446aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SD.setFlags(SD.getFlags() | SF_NoDeadStrip); 2456aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar if (Symbol->isUndefined()) 2466aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SD.setFlags(SD.getFlags() | SF_ReferenceTypeUndefinedLazy); 2476aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar break; 2486aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar 2496aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // Since .reference sets the no dead strip bit, it is equivalent to 2506aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // .no_dead_strip in practice. 2516aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar case MCStreamer::Reference: 2526aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar case MCStreamer::NoDeadStrip: 2536aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SD.setFlags(SD.getFlags() | SF_NoDeadStrip); 2546aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar break; 2556aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar 2566aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar case MCStreamer::PrivateExtern: 2576aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SD.setExternal(true); 2586aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SD.setPrivateExtern(true); 2596aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar break; 2606aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar 2616aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar case MCStreamer::WeakReference: 2626aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // FIXME: This requires -dynamic. 2636aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar if (Symbol->isUndefined()) 2646aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SD.setFlags(SD.getFlags() | SF_WeakReference); 2656aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar break; 2666aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar 2676aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar case MCStreamer::WeakDefinition: 2686aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // FIXME: 'as' enforces that this is defined and global. The manual claims 2696aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // it has to be in a coalesced section, but this isn't enforced. 2706aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar SD.setFlags(SD.getFlags() | SF_WeakDefinition); 2716aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar break; 2723edd9bb7a3da8526eb2f4a5dae2962a987d3d566Daniel Dunbar } 273fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 274fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 275fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarvoid MCMachOStreamer::EmitSymbolDesc(MCSymbol *Symbol, unsigned DescValue) { 2766aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar // Encode the 'desc' value into the lowest implementation defined bits. 2776aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar assert(DescValue == (DescValue & SF_DescFlagsMask) && 2786aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar "Invalid .desc value!"); 2796aff2fbd56d4bc2d6029f7c9bd49a97f6dc01213Daniel Dunbar getSymbolData(*Symbol).setFlags(DescValue & SF_DescFlagsMask); 280fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 281fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 282fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarvoid MCMachOStreamer::EmitCommonSymbol(MCSymbol *Symbol, unsigned Size, 2837092c7e1dcf9d05741b400dd54bbd7d3419773b2Daniel Dunbar unsigned ByteAlignment) { 2848f4d146c340c9423271ebd7bb3fd32b880000bc9Daniel Dunbar // FIXME: Darwin 'as' does appear to allow redef of a .comm by itself. 2858f4d146c340c9423271ebd7bb3fd32b880000bc9Daniel Dunbar assert(Symbol->isUndefined() && "Cannot define a symbol twice!"); 2868f4d146c340c9423271ebd7bb3fd32b880000bc9Daniel Dunbar 2878f4d146c340c9423271ebd7bb3fd32b880000bc9Daniel Dunbar MCSymbolData &SD = getSymbolData(*Symbol); 2888f4d146c340c9423271ebd7bb3fd32b880000bc9Daniel Dunbar SD.setExternal(true); 2897092c7e1dcf9d05741b400dd54bbd7d3419773b2Daniel Dunbar SD.setCommon(Size, ByteAlignment); 290fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 291fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 2928751b94ffbd9c49df8949a37f78d6bd0be87b256Daniel Dunbarvoid MCMachOStreamer::EmitZerofill(const MCSection *Section, MCSymbol *Symbol, 2937092c7e1dcf9d05741b400dd54bbd7d3419773b2Daniel Dunbar unsigned Size, unsigned ByteAlignment) { 294d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar MCSectionData &SectData = getSectionData(*Section); 295d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar 296d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar // The symbol may not be present, which only creates the section. 297d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar if (!Symbol) 298d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar return; 299d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar 300d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar // FIXME: Assert that this section has the zerofill type. 301d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar 302d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar assert(Symbol->isUndefined() && "Cannot define a symbol twice!"); 303d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar 304d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar MCSymbolData &SD = getSymbolData(*Symbol); 305d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar 3067092c7e1dcf9d05741b400dd54bbd7d3419773b2Daniel Dunbar MCFragment *F = new MCZeroFillFragment(Size, ByteAlignment, &SectData); 307d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar SD.setFragment(F); 308d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar 309d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar Symbol->setSection(*Section); 310d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar 311d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar // Update the maximum alignment on the zero fill section if necessary. 312d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar if (ByteAlignment > SectData.getAlignment()) 313d5a8e98ef627a35284c9b5989664514f8f163968Daniel Dunbar SectData.setAlignment(ByteAlignment); 314fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 315fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 316fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarvoid MCMachOStreamer::EmitBytes(const StringRef &Data) { 317f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar MCDataFragment *DF = dyn_cast_or_null<MCDataFragment>(getCurrentFragment()); 318f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar if (!DF) 319f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar DF = new MCDataFragment(CurSectionData); 3200705fbf52fcaade0c6b9d5d33bec163ee4c2daf4Daniel Dunbar DF->getContents().append(Data.begin(), Data.end()); 321fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 322fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 323821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbarvoid MCMachOStreamer::EmitValue(const MCExpr *Value, unsigned Size) { 324821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar MCValue RelocValue; 325821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar 326821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar if (!AddValueSymbols(Value)->EvaluateAsRelocatable(getContext(), RelocValue)) 327821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar return llvm_report_error("expected relocatable expression"); 328821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar 329821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar new MCFillFragment(RelocValue, Size, 1, CurSectionData); 330fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 331fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 332fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarvoid MCMachOStreamer::EmitValueToAlignment(unsigned ByteAlignment, 333fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar int64_t Value, unsigned ValueSize, 334fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar unsigned MaxBytesToEmit) { 335d6f761e0eb610936a6b8495360b62696dcd85164Daniel Dunbar if (MaxBytesToEmit == 0) 336d6f761e0eb610936a6b8495360b62696dcd85164Daniel Dunbar MaxBytesToEmit = ByteAlignment; 3370705fbf52fcaade0c6b9d5d33bec163ee4c2daf4Daniel Dunbar new MCAlignFragment(ByteAlignment, Value, ValueSize, MaxBytesToEmit, 3380705fbf52fcaade0c6b9d5d33bec163ee4c2daf4Daniel Dunbar CurSectionData); 3390705fbf52fcaade0c6b9d5d33bec163ee4c2daf4Daniel Dunbar 340f3d2ef0c9712381a105118336975adcfbf733db0Daniel Dunbar // Update the maximum alignment on the current section if necessary. 3410705fbf52fcaade0c6b9d5d33bec163ee4c2daf4Daniel Dunbar if (ByteAlignment > CurSectionData->getAlignment()) 3420705fbf52fcaade0c6b9d5d33bec163ee4c2daf4Daniel Dunbar CurSectionData->setAlignment(ByteAlignment); 343fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 344fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 345821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbarvoid MCMachOStreamer::EmitValueToOffset(const MCExpr *Offset, 346fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar unsigned char Value) { 347821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar MCValue RelocOffset; 348821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar 349821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar if (!AddValueSymbols(Offset)->EvaluateAsRelocatable(getContext(), 350821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar RelocOffset)) 351821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar return llvm_report_error("expected relocatable expression"); 352821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar 353821e3334ed3390d931f497300e6a5f1dc21bcfb3Daniel Dunbar new MCOrgFragment(RelocOffset, Value, CurSectionData); 354fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 355fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 356fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarvoid MCMachOStreamer::EmitInstruction(const MCInst &Inst) { 3574fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar // Scan for values. 3584fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar for (unsigned i = 0; i != Inst.getNumOperands(); ++i) 3598c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar if (Inst.getOperand(i).isExpr()) 3608c2eebe4074ef218b30d94358f6b2e45c079605cDaniel Dunbar AddValueSymbols(Inst.getOperand(i).getExpr()); 3614fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar 3624fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar if (!Emitter) 3634fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar llvm_unreachable("no code emitter available!"); 3644fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar 3654fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar // FIXME: Relocations! 3664fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar SmallString<256> Code; 3674fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar raw_svector_ostream VecOS(Code); 3684fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar Emitter->EncodeInstruction(Inst, VecOS); 3694fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar EmitBytes(VecOS.str()); 370fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 371fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 372fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbarvoid MCMachOStreamer::Finish() { 373fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar Assembler.Finish(); 374fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 375fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar 3764fac74950a1ff08b995b366bfb84369c1507faefDaniel DunbarMCStreamer *llvm::createMachOStreamer(MCContext &Context, raw_ostream &OS, 3774fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar MCCodeEmitter *CE) { 3784fac74950a1ff08b995b366bfb84369c1507faefDaniel Dunbar return new MCMachOStreamer(Context, OS, CE); 379fb4a6b397665df011348ade24a8e38d2219f095aDaniel Dunbar} 380