MCELFStreamer.cpp revision 221345
1212793Sdim//===- lib/MC/MCELFStreamer.cpp - ELF Object Output ------------===//
2212793Sdim//
3212793Sdim//                     The LLVM Compiler Infrastructure
4212793Sdim//
5212793Sdim// This file is distributed under the University of Illinois Open Source
6212793Sdim// License. See LICENSE.TXT for details.
7212793Sdim//
8212793Sdim//===----------------------------------------------------------------------===//
9212793Sdim//
10212793Sdim// This file assembles .s files and emits ELF .o object files.
11212793Sdim//
12212793Sdim//===----------------------------------------------------------------------===//
13212793Sdim
14221345Sdim#include "MCELFStreamer.h"
15221345Sdim#include "MCELF.h"
16212793Sdim#include "llvm/MC/MCStreamer.h"
17212793Sdim#include "llvm/MC/MCCodeEmitter.h"
18212793Sdim#include "llvm/MC/MCELFSymbolFlags.h"
19212793Sdim#include "llvm/MC/MCExpr.h"
20212793Sdim#include "llvm/MC/MCInst.h"
21212793Sdim#include "llvm/MC/MCSection.h"
22212793Sdim#include "llvm/MC/MCSymbol.h"
23218893Sdim#include "llvm/MC/MCValue.h"
24212793Sdim#include "llvm/Support/Debug.h"
25212793Sdim#include "llvm/Support/ELF.h"
26212793Sdim#include "llvm/Support/ErrorHandling.h"
27212793Sdim#include "llvm/Support/raw_ostream.h"
28212793Sdim#include "llvm/Target/TargetAsmBackend.h"
29218893Sdim#include "llvm/Target/TargetAsmInfo.h"
30212793Sdim
31212793Sdimusing namespace llvm;
32212793Sdim
33218893Sdimvoid MCELFStreamer::InitSections() {
34218893Sdim  // This emulates the same behavior of GNU as. This makes it easier
35218893Sdim  // to compare the output as the major sections are in the same order.
36218893Sdim  SetSectionText();
37218893Sdim  SetSectionData();
38218893Sdim  SetSectionBss();
39218893Sdim  SetSectionText();
40218893Sdim}
41218893Sdim
42212793Sdimvoid MCELFStreamer::EmitLabel(MCSymbol *Symbol) {
43212793Sdim  assert(Symbol->isUndefined() && "Cannot define a symbol twice!");
44212793Sdim
45218893Sdim  MCObjectStreamer::EmitLabel(Symbol);
46212793Sdim
47218893Sdim  const MCSectionELF &Section =
48218893Sdim    static_cast<const MCSectionELF&>(Symbol->getSection());
49218893Sdim  MCSymbolData &SD = getAssembler().getSymbolData(*Symbol);
50218893Sdim  if (Section.getFlags() & ELF::SHF_TLS)
51221345Sdim    MCELF::SetType(SD, ELF::STT_TLS);
52212793Sdim}
53212793Sdim
54212793Sdimvoid MCELFStreamer::EmitAssemblerFlag(MCAssemblerFlag Flag) {
55212793Sdim  switch (Flag) {
56218893Sdim  case MCAF_SyntaxUnified: return; // no-op here.
57218893Sdim  case MCAF_Code16: return; // no-op here.
58218893Sdim  case MCAF_Code32: return; // no-op here.
59212793Sdim  case MCAF_SubsectionsViaSymbols:
60212793Sdim    getAssembler().setSubsectionsViaSymbols(true);
61212793Sdim    return;
62212793Sdim  }
63212793Sdim
64212793Sdim  assert(0 && "invalid assembler flag!");
65212793Sdim}
66212793Sdim
67218893Sdimvoid MCELFStreamer::EmitThumbFunc(MCSymbol *Func) {
68218893Sdim  // FIXME: Anything needed here to flag the function as thumb?
69218893Sdim}
70218893Sdim
71212793Sdimvoid MCELFStreamer::EmitAssignment(MCSymbol *Symbol, const MCExpr *Value) {
72212793Sdim  // TODO: This is exactly the same as WinCOFFStreamer. Consider merging into
73212793Sdim  // MCObjectStreamer.
74212793Sdim  // FIXME: Lift context changes into super class.
75212793Sdim  getAssembler().getOrCreateSymbolData(*Symbol);
76212793Sdim  Symbol->setVariableValue(AddValueSymbols(Value));
77212793Sdim}
78212793Sdim
79218893Sdimvoid MCELFStreamer::ChangeSection(const MCSection *Section) {
80218893Sdim  const MCSymbol *Grp = static_cast<const MCSectionELF *>(Section)->getGroup();
81218893Sdim  if (Grp)
82218893Sdim    getAssembler().getOrCreateSymbolData(*Grp);
83218893Sdim  this->MCObjectStreamer::ChangeSection(Section);
84218893Sdim}
85218893Sdim
86218893Sdimvoid MCELFStreamer::EmitWeakReference(MCSymbol *Alias, const MCSymbol *Symbol) {
87218893Sdim  getAssembler().getOrCreateSymbolData(*Symbol);
88218893Sdim  MCSymbolData &AliasSD = getAssembler().getOrCreateSymbolData(*Alias);
89218893Sdim  AliasSD.setFlags(AliasSD.getFlags() | ELF_Other_Weakref);
90218893Sdim  const MCExpr *Value = MCSymbolRefExpr::Create(Symbol, getContext());
91218893Sdim  Alias->setVariableValue(Value);
92218893Sdim}
93218893Sdim
94212793Sdimvoid MCELFStreamer::EmitSymbolAttribute(MCSymbol *Symbol,
95212793Sdim                                          MCSymbolAttr Attribute) {
96212793Sdim  // Indirect symbols are handled differently, to match how 'as' handles
97212793Sdim  // them. This makes writing matching .o files easier.
98212793Sdim  if (Attribute == MCSA_IndirectSymbol) {
99212793Sdim    // Note that we intentionally cannot use the symbol data here; this is
100212793Sdim    // important for matching the string table that 'as' generates.
101212793Sdim    IndirectSymbolData ISD;
102212793Sdim    ISD.Symbol = Symbol;
103212793Sdim    ISD.SectionData = getCurrentSectionData();
104212793Sdim    getAssembler().getIndirectSymbols().push_back(ISD);
105212793Sdim    return;
106212793Sdim  }
107212793Sdim
108212793Sdim  // Adding a symbol attribute always introduces the symbol, note that an
109212793Sdim  // important side effect of calling getOrCreateSymbolData here is to register
110212793Sdim  // the symbol with the assembler.
111212793Sdim  MCSymbolData &SD = getAssembler().getOrCreateSymbolData(*Symbol);
112212793Sdim
113212793Sdim  // The implementation of symbol attributes is designed to match 'as', but it
114212793Sdim  // leaves much to desired. It doesn't really make sense to arbitrarily add and
115212793Sdim  // remove flags, but 'as' allows this (in particular, see .desc).
116212793Sdim  //
117212793Sdim  // In the future it might be worth trying to make these operations more well
118212793Sdim  // defined.
119212793Sdim  switch (Attribute) {
120212793Sdim  case MCSA_LazyReference:
121212793Sdim  case MCSA_Reference:
122212793Sdim  case MCSA_NoDeadStrip:
123218893Sdim  case MCSA_SymbolResolver:
124212793Sdim  case MCSA_PrivateExtern:
125212793Sdim  case MCSA_WeakDefinition:
126212793Sdim  case MCSA_WeakDefAutoPrivate:
127212793Sdim  case MCSA_Invalid:
128212793Sdim  case MCSA_ELF_TypeIndFunction:
129212793Sdim  case MCSA_IndirectSymbol:
130212793Sdim    assert(0 && "Invalid symbol attribute for ELF!");
131212793Sdim    break;
132212793Sdim
133218893Sdim  case MCSA_ELF_TypeGnuUniqueObject:
134218893Sdim    // Ignore for now.
135218893Sdim    break;
136218893Sdim
137212793Sdim  case MCSA_Global:
138221345Sdim    MCELF::SetBinding(SD, ELF::STB_GLOBAL);
139212793Sdim    SD.setExternal(true);
140218893Sdim    BindingExplicitlySet.insert(Symbol);
141212793Sdim    break;
142212793Sdim
143212793Sdim  case MCSA_WeakReference:
144212793Sdim  case MCSA_Weak:
145221345Sdim    MCELF::SetBinding(SD, ELF::STB_WEAK);
146218893Sdim    SD.setExternal(true);
147218893Sdim    BindingExplicitlySet.insert(Symbol);
148212793Sdim    break;
149212793Sdim
150212793Sdim  case MCSA_Local:
151221345Sdim    MCELF::SetBinding(SD, ELF::STB_LOCAL);
152218893Sdim    SD.setExternal(false);
153218893Sdim    BindingExplicitlySet.insert(Symbol);
154212793Sdim    break;
155212793Sdim
156212793Sdim  case MCSA_ELF_TypeFunction:
157221345Sdim    MCELF::SetType(SD, ELF::STT_FUNC);
158212793Sdim    break;
159212793Sdim
160212793Sdim  case MCSA_ELF_TypeObject:
161221345Sdim    MCELF::SetType(SD, ELF::STT_OBJECT);
162212793Sdim    break;
163212793Sdim
164212793Sdim  case MCSA_ELF_TypeTLS:
165221345Sdim    MCELF::SetType(SD, ELF::STT_TLS);
166212793Sdim    break;
167212793Sdim
168212793Sdim  case MCSA_ELF_TypeCommon:
169221345Sdim    MCELF::SetType(SD, ELF::STT_COMMON);
170212793Sdim    break;
171212793Sdim
172212793Sdim  case MCSA_ELF_TypeNoType:
173221345Sdim    MCELF::SetType(SD, ELF::STT_NOTYPE);
174212793Sdim    break;
175212793Sdim
176212793Sdim  case MCSA_Protected:
177221345Sdim    MCELF::SetVisibility(SD, ELF::STV_PROTECTED);
178212793Sdim    break;
179212793Sdim
180212793Sdim  case MCSA_Hidden:
181221345Sdim    MCELF::SetVisibility(SD, ELF::STV_HIDDEN);
182212793Sdim    break;
183212793Sdim
184212793Sdim  case MCSA_Internal:
185221345Sdim    MCELF::SetVisibility(SD, ELF::STV_INTERNAL);
186212793Sdim    break;
187212793Sdim  }
188212793Sdim}
189212793Sdim
190212793Sdimvoid MCELFStreamer::EmitCommonSymbol(MCSymbol *Symbol, uint64_t Size,
191212793Sdim                                       unsigned ByteAlignment) {
192212793Sdim  MCSymbolData &SD = getAssembler().getOrCreateSymbolData(*Symbol);
193212793Sdim
194218893Sdim  if (!BindingExplicitlySet.count(Symbol)) {
195221345Sdim    MCELF::SetBinding(SD, ELF::STB_GLOBAL);
196218893Sdim    SD.setExternal(true);
197218893Sdim  }
198218893Sdim
199221345Sdim  MCELF::SetType(SD, ELF::STT_OBJECT);
200218893Sdim
201221345Sdim  if (MCELF::GetBinding(SD) == ELF_STB_Local) {
202212793Sdim    const MCSection *Section = getAssembler().getContext().getELFSection(".bss",
203218893Sdim                                                                    ELF::SHT_NOBITS,
204218893Sdim                                                                    ELF::SHF_WRITE |
205218893Sdim                                                                    ELF::SHF_ALLOC,
206212793Sdim                                                                    SectionKind::getBSS());
207218893Sdim    Symbol->setSection(*Section);
208212793Sdim
209218893Sdim    struct LocalCommon L = {&SD, Size, ByteAlignment};
210218893Sdim    LocalCommons.push_back(L);
211218893Sdim  } else {
212218893Sdim    SD.setCommon(Size, ByteAlignment);
213212793Sdim  }
214212793Sdim
215218893Sdim  SD.setSize(MCConstantExpr::Create(Size, getContext()));
216218893Sdim}
217212793Sdim
218218893Sdimvoid MCELFStreamer::EmitLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size) {
219218893Sdim  // FIXME: Should this be caught and done earlier?
220218893Sdim  MCSymbolData &SD = getAssembler().getOrCreateSymbolData(*Symbol);
221221345Sdim  MCELF::SetBinding(SD, ELF::STB_LOCAL);
222218893Sdim  SD.setExternal(false);
223218893Sdim  BindingExplicitlySet.insert(Symbol);
224218893Sdim  // FIXME: ByteAlignment is not needed here, but is required.
225218893Sdim  EmitCommonSymbol(Symbol, Size, 1);
226212793Sdim}
227212793Sdim
228212793Sdimvoid MCELFStreamer::EmitBytes(StringRef Data, unsigned AddrSpace) {
229212793Sdim  // TODO: This is exactly the same as WinCOFFStreamer. Consider merging into
230212793Sdim  // MCObjectStreamer.
231212793Sdim  getOrCreateDataFragment()->getContents().append(Data.begin(), Data.end());
232212793Sdim}
233212793Sdim
234212793Sdimvoid MCELFStreamer::EmitValueToAlignment(unsigned ByteAlignment,
235212793Sdim                                           int64_t Value, unsigned ValueSize,
236212793Sdim                                           unsigned MaxBytesToEmit) {
237212793Sdim  // TODO: This is exactly the same as WinCOFFStreamer. Consider merging into
238212793Sdim  // MCObjectStreamer.
239212793Sdim  if (MaxBytesToEmit == 0)
240212793Sdim    MaxBytesToEmit = ByteAlignment;
241212793Sdim  new MCAlignFragment(ByteAlignment, Value, ValueSize, MaxBytesToEmit,
242212793Sdim                      getCurrentSectionData());
243212793Sdim
244212793Sdim  // Update the maximum alignment on the current section if necessary.
245212793Sdim  if (ByteAlignment > getCurrentSectionData()->getAlignment())
246212793Sdim    getCurrentSectionData()->setAlignment(ByteAlignment);
247212793Sdim}
248212793Sdim
249212793Sdimvoid MCELFStreamer::EmitCodeAlignment(unsigned ByteAlignment,
250212793Sdim                                        unsigned MaxBytesToEmit) {
251212793Sdim  // TODO: This is exactly the same as WinCOFFStreamer. Consider merging into
252212793Sdim  // MCObjectStreamer.
253212793Sdim  if (MaxBytesToEmit == 0)
254212793Sdim    MaxBytesToEmit = ByteAlignment;
255212793Sdim  MCAlignFragment *F = new MCAlignFragment(ByteAlignment, 0, 1, MaxBytesToEmit,
256212793Sdim                                           getCurrentSectionData());
257212793Sdim  F->setEmitNops(true);
258212793Sdim
259212793Sdim  // Update the maximum alignment on the current section if necessary.
260212793Sdim  if (ByteAlignment > getCurrentSectionData()->getAlignment())
261212793Sdim    getCurrentSectionData()->setAlignment(ByteAlignment);
262212793Sdim}
263212793Sdim
264212793Sdim// Add a symbol for the file name of this module. This is the second
265212793Sdim// entry in the module's symbol table (the first being the null symbol).
266212793Sdimvoid MCELFStreamer::EmitFileDirective(StringRef Filename) {
267212793Sdim  MCSymbol *Symbol = getAssembler().getContext().GetOrCreateSymbol(Filename);
268218893Sdim  Symbol->setSection(*getCurrentSection());
269212793Sdim  Symbol->setAbsolute();
270212793Sdim
271212793Sdim  MCSymbolData &SD = getAssembler().getOrCreateSymbolData(*Symbol);
272212793Sdim
273212793Sdim  SD.setFlags(ELF_STT_File | ELF_STB_Local | ELF_STV_Default);
274212793Sdim}
275212793Sdim
276218893Sdimvoid  MCELFStreamer::fixSymbolsInTLSFixups(const MCExpr *expr) {
277218893Sdim  switch (expr->getKind()) {
278218893Sdim  case MCExpr::Target: llvm_unreachable("Can't handle target exprs yet!");
279218893Sdim  case MCExpr::Constant:
280218893Sdim    break;
281212793Sdim
282218893Sdim  case MCExpr::Binary: {
283218893Sdim    const MCBinaryExpr *be = cast<MCBinaryExpr>(expr);
284218893Sdim    fixSymbolsInTLSFixups(be->getLHS());
285218893Sdim    fixSymbolsInTLSFixups(be->getRHS());
286218893Sdim    break;
287218893Sdim  }
288212793Sdim
289218893Sdim  case MCExpr::SymbolRef: {
290218893Sdim    const MCSymbolRefExpr &symRef = *cast<MCSymbolRefExpr>(expr);
291218893Sdim    switch (symRef.getKind()) {
292218893Sdim    default:
293218893Sdim      return;
294221345Sdim    case MCSymbolRefExpr::VK_GOTTPOFF:
295221345Sdim    case MCSymbolRefExpr::VK_INDNTPOFF:
296218893Sdim    case MCSymbolRefExpr::VK_NTPOFF:
297218893Sdim    case MCSymbolRefExpr::VK_GOTNTPOFF:
298218893Sdim    case MCSymbolRefExpr::VK_TLSGD:
299221345Sdim    case MCSymbolRefExpr::VK_TLSLD:
300218893Sdim    case MCSymbolRefExpr::VK_TLSLDM:
301218893Sdim    case MCSymbolRefExpr::VK_TPOFF:
302218893Sdim    case MCSymbolRefExpr::VK_DTPOFF:
303218893Sdim    case MCSymbolRefExpr::VK_ARM_TLSGD:
304221345Sdim    case MCSymbolRefExpr::VK_ARM_TPOFF:
305221345Sdim    case MCSymbolRefExpr::VK_ARM_GOTTPOFF:
306218893Sdim      break;
307218893Sdim    }
308218893Sdim    MCSymbolData &SD = getAssembler().getOrCreateSymbolData(symRef.getSymbol());
309221345Sdim    MCELF::SetType(SD, ELF::STT_TLS);
310218893Sdim    break;
311218893Sdim  }
312218893Sdim
313218893Sdim  case MCExpr::Unary:
314218893Sdim    fixSymbolsInTLSFixups(cast<MCUnaryExpr>(expr)->getSubExpr());
315218893Sdim    break;
316218893Sdim  }
317212793Sdim}
318212793Sdim
319218893Sdimvoid MCELFStreamer::EmitInstToFragment(const MCInst &Inst) {
320218893Sdim  this->MCObjectStreamer::EmitInstToFragment(Inst);
321218893Sdim  MCInstFragment &F = *cast<MCInstFragment>(getCurrentFragment());
322218893Sdim
323218893Sdim  for (unsigned i = 0, e = F.getFixups().size(); i != e; ++i)
324218893Sdim    fixSymbolsInTLSFixups(F.getFixups()[i].getValue());
325218893Sdim}
326218893Sdim
327212793Sdimvoid MCELFStreamer::EmitInstToData(const MCInst &Inst) {
328212793Sdim  MCDataFragment *DF = getOrCreateDataFragment();
329212793Sdim
330212793Sdim  SmallVector<MCFixup, 4> Fixups;
331212793Sdim  SmallString<256> Code;
332212793Sdim  raw_svector_ostream VecOS(Code);
333212793Sdim  getAssembler().getEmitter().EncodeInstruction(Inst, VecOS, Fixups);
334212793Sdim  VecOS.flush();
335212793Sdim
336218893Sdim  for (unsigned i = 0, e = Fixups.size(); i != e; ++i)
337218893Sdim    fixSymbolsInTLSFixups(Fixups[i].getValue());
338218893Sdim
339212793Sdim  // Add the fixups and data.
340212793Sdim  for (unsigned i = 0, e = Fixups.size(); i != e; ++i) {
341212793Sdim    Fixups[i].setOffset(Fixups[i].getOffset() + DF->getContents().size());
342212793Sdim    DF->addFixup(Fixups[i]);
343212793Sdim  }
344212793Sdim  DF->getContents().append(Code.begin(), Code.end());
345212793Sdim}
346212793Sdim
347218893Sdimvoid MCELFStreamer::Finish() {
348218893Sdim  if (getNumFrameInfos())
349221345Sdim    MCDwarfFrameEmitter::Emit(*this, true);
350212793Sdim
351218893Sdim  for (std::vector<LocalCommon>::const_iterator i = LocalCommons.begin(),
352218893Sdim                                                e = LocalCommons.end();
353218893Sdim       i != e; ++i) {
354218893Sdim    MCSymbolData *SD = i->SD;
355218893Sdim    uint64_t Size = i->Size;
356218893Sdim    unsigned ByteAlignment = i->ByteAlignment;
357218893Sdim    const MCSymbol &Symbol = SD->getSymbol();
358218893Sdim    const MCSection &Section = Symbol.getSection();
359212793Sdim
360218893Sdim    MCSectionData &SectData = getAssembler().getOrCreateSectionData(Section);
361218893Sdim    new MCAlignFragment(ByteAlignment, 0, 1, ByteAlignment, &SectData);
362212793Sdim
363218893Sdim    MCFragment *F = new MCFillFragment(0, 0, Size, &SectData);
364218893Sdim    SD->setFragment(F);
365218893Sdim
366218893Sdim    // Update the maximum alignment of the section if necessary.
367218893Sdim    if (ByteAlignment > SectData.getAlignment())
368218893Sdim      SectData.setAlignment(ByteAlignment);
369212793Sdim  }
370212793Sdim
371218893Sdim  this->MCObjectStreamer::Finish();
372212793Sdim}
373212793Sdim
374212793SdimMCStreamer *llvm::createELFStreamer(MCContext &Context, TargetAsmBackend &TAB,
375218893Sdim                                    raw_ostream &OS, MCCodeEmitter *CE,
376218893Sdim                                    bool RelaxAll, bool NoExecStack) {
377212793Sdim  MCELFStreamer *S = new MCELFStreamer(Context, TAB, OS, CE);
378212793Sdim  if (RelaxAll)
379212793Sdim    S->getAssembler().setRelaxAll(true);
380218893Sdim  if (NoExecStack)
381218893Sdim    S->getAssembler().setNoExecStack(true);
382212793Sdim  return S;
383212793Sdim}
384