1321369Sdim//===- MCMachOStreamer.cpp - MachO Streamer -------------------------------===//
2198090Srdivacky//
3353358Sdim// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4353358Sdim// See https://llvm.org/LICENSE.txt for license information.
5353358Sdim// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6198090Srdivacky//
7198090Srdivacky//===----------------------------------------------------------------------===//
8198090Srdivacky
9276479Sdim#include "llvm/ADT/DenseMap.h"
10321369Sdim#include "llvm/ADT/SmallString.h"
11276479Sdim#include "llvm/ADT/SmallVector.h"
12321369Sdim#include "llvm/ADT/StringRef.h"
13321369Sdim#include "llvm/ADT/Triple.h"
14249423Sdim#include "llvm/MC/MCAsmBackend.h"
15198090Srdivacky#include "llvm/MC/MCAssembler.h"
16249423Sdim#include "llvm/MC/MCCodeEmitter.h"
17198090Srdivacky#include "llvm/MC/MCContext.h"
18321369Sdim#include "llvm/MC/MCDirectives.h"
19198090Srdivacky#include "llvm/MC/MCExpr.h"
20321369Sdim#include "llvm/MC/MCFixup.h"
21321369Sdim#include "llvm/MC/MCFragment.h"
22198090Srdivacky#include "llvm/MC/MCInst.h"
23276479Sdim#include "llvm/MC/MCLinkerOptimizationHint.h"
24276479Sdim#include "llvm/MC/MCObjectFileInfo.h"
25210299Sed#include "llvm/MC/MCObjectStreamer.h"
26341825Sdim#include "llvm/MC/MCObjectWriter.h"
27198090Srdivacky#include "llvm/MC/MCSection.h"
28249423Sdim#include "llvm/MC/MCSectionMachO.h"
29321369Sdim#include "llvm/MC/MCStreamer.h"
30321369Sdim#include "llvm/MC/MCSymbol.h"
31288943Sdim#include "llvm/MC/MCSymbolMachO.h"
32309124Sdim#include "llvm/MC/MCValue.h"
33321369Sdim#include "llvm/Support/Casting.h"
34198090Srdivacky#include "llvm/Support/ErrorHandling.h"
35288943Sdim#include "llvm/Support/TargetRegistry.h"
36198090Srdivacky#include "llvm/Support/raw_ostream.h"
37321369Sdim#include <cassert>
38321369Sdim#include <vector>
39206083Srdivacky
40198090Srdivackyusing namespace llvm;
41198090Srdivacky
42198090Srdivackynamespace {
43198090Srdivacky
44210299Sedclass MCMachOStreamer : public MCObjectStreamer {
45198090Srdivackyprivate:
46276479Sdim  /// LabelSections - true if each section change should emit a linker local
47276479Sdim  /// label for use in relocations for assembler local references. Obviates the
48276479Sdim  /// need for local relocations. False by default.
49276479Sdim  bool LabelSections;
50208599Srdivacky
51288943Sdim  bool DWARFMustBeAtTheEnd;
52288943Sdim  bool CreatedADWARFSection;
53288943Sdim
54276479Sdim  /// HasSectionLabel - map of which sections have already had a non-local
55276479Sdim  /// label emitted to them. Used so we don't emit extraneous linker local
56276479Sdim  /// labels in the middle of the section.
57276479Sdim  DenseMap<const MCSection*, bool> HasSectionLabel;
58276479Sdim
59276479Sdim  void EmitInstToData(const MCInst &Inst, const MCSubtargetInfo &STI) override;
60276479Sdim
61239462Sdim  void EmitDataRegion(DataRegionData::KindTy Kind);
62239462Sdim  void EmitDataRegionEnd();
63276479Sdim
64198090Srdivackypublic:
65327952Sdim  MCMachOStreamer(MCContext &Context, std::unique_ptr<MCAsmBackend> MAB,
66341825Sdim                  std::unique_ptr<MCObjectWriter> OW,
67341825Sdim                  std::unique_ptr<MCCodeEmitter> Emitter,
68327952Sdim                  bool DWARFMustBeAtTheEnd, bool label)
69341825Sdim      : MCObjectStreamer(Context, std::move(MAB), std::move(OW),
70341825Sdim                         std::move(Emitter)),
71327952Sdim        LabelSections(label), DWARFMustBeAtTheEnd(DWARFMustBeAtTheEnd),
72327952Sdim        CreatedADWARFSection(false) {}
73198090Srdivacky
74280031Sdim  /// state management
75280031Sdim  void reset() override {
76296417Sdim    CreatedADWARFSection = false;
77280031Sdim    HasSectionLabel.clear();
78280031Sdim    MCObjectStreamer::reset();
79280031Sdim  }
80280031Sdim
81198090Srdivacky  /// @name MCStreamer Interface
82198090Srdivacky  /// @{
83198090Srdivacky
84288943Sdim  void ChangeSection(MCSection *Sect, const MCExpr *Subsect) override;
85321369Sdim  void EmitLabel(MCSymbol *Symbol, SMLoc Loc = SMLoc()) override;
86309124Sdim  void EmitAssignment(MCSymbol *Symbol, const MCExpr *Value) override;
87276479Sdim  void EmitEHSymAttributes(const MCSymbol *Symbol, MCSymbol *EHSymbol) override;
88276479Sdim  void EmitAssemblerFlag(MCAssemblerFlag Flag) override;
89276479Sdim  void EmitLinkerOptions(ArrayRef<std::string> Options) override;
90276479Sdim  void EmitDataRegion(MCDataRegionType Kind) override;
91344779Sdim  void EmitVersionMin(MCVersionMinType Kind, unsigned Major, unsigned Minor,
92344779Sdim                      unsigned Update, VersionTuple SDKVersion) override;
93344779Sdim  void EmitBuildVersion(unsigned Platform, unsigned Major, unsigned Minor,
94344779Sdim                        unsigned Update, VersionTuple SDKVersion) override;
95276479Sdim  void EmitThumbFunc(MCSymbol *Func) override;
96276479Sdim  bool EmitSymbolAttribute(MCSymbol *Symbol, MCSymbolAttr Attribute) override;
97276479Sdim  void EmitSymbolDesc(MCSymbol *Symbol, unsigned DescValue) override;
98276479Sdim  void EmitCommonSymbol(MCSymbol *Symbol, uint64_t Size,
99276479Sdim                        unsigned ByteAlignment) override;
100321369Sdim
101276479Sdim  void EmitLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size,
102276479Sdim                             unsigned ByteAlignment) override;
103288943Sdim  void EmitZerofill(MCSection *Section, MCSymbol *Symbol = nullptr,
104341825Sdim                    uint64_t Size = 0, unsigned ByteAlignment = 0,
105341825Sdim                    SMLoc Loc = SMLoc()) override;
106288943Sdim  void EmitTBSSSymbol(MCSection *Section, MCSymbol *Symbol, uint64_t Size,
107280031Sdim                      unsigned ByteAlignment = 0) override;
108208599Srdivacky
109276479Sdim  void EmitIdent(StringRef IdentString) override {
110261991Sdim    llvm_unreachable("macho doesn't support this directive");
111261991Sdim  }
112261991Sdim
113276479Sdim  void EmitLOHDirective(MCLOHType Kind, const MCLOHArgs &Args) override {
114276479Sdim    getAssembler().getLOHContainer().addDirective(Kind, Args);
115276479Sdim  }
116276479Sdim
117276479Sdim  void FinishImpl() override;
118198090Srdivacky};
119198090Srdivacky
120198090Srdivacky} // end anonymous namespace.
121198090Srdivacky
122288943Sdimstatic bool canGoAfterDWARF(const MCSectionMachO &MSec) {
123288943Sdim  // These sections are created by the assembler itself after the end of
124288943Sdim  // the .s file.
125288943Sdim  StringRef SegName = MSec.getSegmentName();
126288943Sdim  StringRef SecName = MSec.getSectionName();
127288943Sdim
128288943Sdim  if (SegName == "__LD" && SecName == "__compact_unwind")
129288943Sdim    return true;
130288943Sdim
131288943Sdim  if (SegName == "__IMPORT") {
132288943Sdim    if (SecName == "__jump_table")
133288943Sdim      return true;
134288943Sdim
135288943Sdim    if (SecName == "__pointers")
136288943Sdim      return true;
137288943Sdim  }
138288943Sdim
139288943Sdim  if (SegName == "__TEXT" && SecName == "__eh_frame")
140288943Sdim    return true;
141288943Sdim
142314564Sdim  if (SegName == "__DATA" && (SecName == "__nl_symbol_ptr" ||
143314564Sdim                              SecName == "__thread_ptr"))
144288943Sdim    return true;
145288943Sdim
146288943Sdim  return false;
147288943Sdim}
148288943Sdim
149288943Sdimvoid MCMachOStreamer::ChangeSection(MCSection *Section,
150276479Sdim                                    const MCExpr *Subsection) {
151276479Sdim  // Change the section normally.
152321369Sdim  bool Created = changeSectionImpl(Section, Subsection);
153288943Sdim  const MCSectionMachO &MSec = *cast<MCSectionMachO>(Section);
154288943Sdim  StringRef SegName = MSec.getSegmentName();
155288943Sdim  if (SegName == "__DWARF")
156288943Sdim    CreatedADWARFSection = true;
157288943Sdim  else if (Created && DWARFMustBeAtTheEnd && !canGoAfterDWARF(MSec))
158288943Sdim    assert(!CreatedADWARFSection && "Creating regular section after DWARF");
159288943Sdim
160276479Sdim  // Output a linker-local symbol so we don't need section-relative local
161276479Sdim  // relocations. The linker hates us when we do that.
162288943Sdim  if (LabelSections && !HasSectionLabel[Section] &&
163288943Sdim      !Section->getBeginSymbol()) {
164288943Sdim    MCSymbol *Label = getContext().createLinkerPrivateTempSymbol();
165288943Sdim    Section->setBeginSymbol(Label);
166276479Sdim    HasSectionLabel[Section] = true;
167276479Sdim  }
168249423Sdim}
169218893Sdim
170221345Sdimvoid MCMachOStreamer::EmitEHSymAttributes(const MCSymbol *Symbol,
171221345Sdim                                          MCSymbol *EHSymbol) {
172288943Sdim  getAssembler().registerSymbol(*Symbol);
173288943Sdim  if (Symbol->isExternal())
174221345Sdim    EmitSymbolAttribute(EHSymbol, MCSA_Global);
175288943Sdim  if (cast<MCSymbolMachO>(Symbol)->isWeakDefinition())
176221345Sdim    EmitSymbolAttribute(EHSymbol, MCSA_WeakDefinition);
177288943Sdim  if (Symbol->isPrivateExtern())
178221345Sdim    EmitSymbolAttribute(EHSymbol, MCSA_PrivateExtern);
179221345Sdim}
180221345Sdim
181321369Sdimvoid MCMachOStreamer::EmitLabel(MCSymbol *Symbol, SMLoc Loc) {
182210299Sed  // We have to create a new fragment if this is an atom defining symbol,
183210299Sed  // fragments cannot span atoms.
184218893Sdim  if (getAssembler().isSymbolLinkerVisible(*Symbol))
185251662Sdim    insert(new MCDataFragment());
186208599Srdivacky
187321369Sdim  MCObjectStreamer::EmitLabel(Symbol, Loc);
188198090Srdivacky
189208599Srdivacky  // This causes the reference type flag to be cleared. Darwin 'as' was "trying"
190208599Srdivacky  // to clear the weak reference and weak definition bits too, but the
191208599Srdivacky  // implementation was buggy. For now we just try to match 'as', for
192208599Srdivacky  // diffability.
193208599Srdivacky  //
194208599Srdivacky  // FIXME: Cleanup this code, these bits should be emitted based on semantic
195208599Srdivacky  // properties, not on the order of definition, etc.
196288943Sdim  cast<MCSymbolMachO>(Symbol)->clearReferenceType();
197198090Srdivacky}
198198090Srdivacky
199309124Sdimvoid MCMachOStreamer::EmitAssignment(MCSymbol *Symbol, const MCExpr *Value) {
200309124Sdim  MCValue Res;
201309124Sdim
202309124Sdim  if (Value->evaluateAsRelocatable(Res, nullptr, nullptr)) {
203309124Sdim    if (const MCSymbolRefExpr *SymAExpr = Res.getSymA()) {
204309124Sdim      const MCSymbol &SymA = SymAExpr->getSymbol();
205309124Sdim      if (!Res.getSymB() && (SymA.getName() == "" || Res.getConstant() != 0))
206309124Sdim        cast<MCSymbolMachO>(Symbol)->setAltEntry();
207309124Sdim    }
208309124Sdim  }
209309124Sdim  MCObjectStreamer::EmitAssignment(Symbol, Value);
210309124Sdim}
211309124Sdim
212239462Sdimvoid MCMachOStreamer::EmitDataRegion(DataRegionData::KindTy Kind) {
213239462Sdim  // Create a temporary label to mark the start of the data region.
214288943Sdim  MCSymbol *Start = getContext().createTempSymbol();
215239462Sdim  EmitLabel(Start);
216239462Sdim  // Record the region for the object writer to use.
217276479Sdim  DataRegionData Data = { Kind, Start, nullptr };
218239462Sdim  std::vector<DataRegionData> &Regions = getAssembler().getDataRegions();
219239462Sdim  Regions.push_back(Data);
220239462Sdim}
221239462Sdim
222239462Sdimvoid MCMachOStreamer::EmitDataRegionEnd() {
223239462Sdim  std::vector<DataRegionData> &Regions = getAssembler().getDataRegions();
224288943Sdim  assert(!Regions.empty() && "Mismatched .end_data_region!");
225239462Sdim  DataRegionData &Data = Regions.back();
226276479Sdim  assert(!Data.End && "Mismatched .end_data_region!");
227239462Sdim  // Create a temporary label to mark the end of the data region.
228288943Sdim  Data.End = getContext().createTempSymbol();
229239462Sdim  EmitLabel(Data.End);
230239462Sdim}
231239462Sdim
232202878Srdivackyvoid MCMachOStreamer::EmitAssemblerFlag(MCAssemblerFlag Flag) {
233218893Sdim  // Let the target do whatever target specific stuff it needs to do.
234234353Sdim  getAssembler().getBackend().handleAssemblerFlag(Flag);
235218893Sdim  // Do any generic stuff we need to do.
236198090Srdivacky  switch (Flag) {
237218893Sdim  case MCAF_SyntaxUnified: return; // no-op here.
238226633Sdim  case MCAF_Code16: return; // Change parsing mode; no-op here.
239226633Sdim  case MCAF_Code32: return; // Change parsing mode; no-op here.
240226633Sdim  case MCAF_Code64: return; // Change parsing mode; no-op here.
241202878Srdivacky  case MCAF_SubsectionsViaSymbols:
242210299Sed    getAssembler().setSubsectionsViaSymbols(true);
243198090Srdivacky    return;
244198090Srdivacky  }
245218893Sdim}
246198090Srdivacky
247249423Sdimvoid MCMachOStreamer::EmitLinkerOptions(ArrayRef<std::string> Options) {
248249423Sdim  getAssembler().getLinkerOptions().push_back(Options);
249249423Sdim}
250249423Sdim
251239462Sdimvoid MCMachOStreamer::EmitDataRegion(MCDataRegionType Kind) {
252239462Sdim  switch (Kind) {
253239462Sdim  case MCDR_DataRegion:
254239462Sdim    EmitDataRegion(DataRegionData::Data);
255239462Sdim    return;
256239462Sdim  case MCDR_DataRegionJT8:
257239462Sdim    EmitDataRegion(DataRegionData::JumpTable8);
258239462Sdim    return;
259239462Sdim  case MCDR_DataRegionJT16:
260239462Sdim    EmitDataRegion(DataRegionData::JumpTable16);
261239462Sdim    return;
262239462Sdim  case MCDR_DataRegionJT32:
263239462Sdim    EmitDataRegion(DataRegionData::JumpTable32);
264239462Sdim    return;
265239462Sdim  case MCDR_DataRegionEnd:
266239462Sdim    EmitDataRegionEnd();
267239462Sdim    return;
268239462Sdim  }
269239462Sdim}
270239462Sdim
271276479Sdimvoid MCMachOStreamer::EmitVersionMin(MCVersionMinType Kind, unsigned Major,
272344779Sdim                                     unsigned Minor, unsigned Update,
273344779Sdim                                     VersionTuple SDKVersion) {
274344779Sdim  getAssembler().setVersionMin(Kind, Major, Minor, Update, SDKVersion);
275276479Sdim}
276276479Sdim
277327952Sdimvoid MCMachOStreamer::EmitBuildVersion(unsigned Platform, unsigned Major,
278344779Sdim                                       unsigned Minor, unsigned Update,
279344779Sdim                                       VersionTuple SDKVersion) {
280327952Sdim  getAssembler().setBuildVersion((MachO::PlatformType)Platform, Major, Minor,
281344779Sdim                                 Update, SDKVersion);
282327952Sdim}
283327952Sdim
284218893Sdimvoid MCMachOStreamer::EmitThumbFunc(MCSymbol *Symbol) {
285218893Sdim  // Remember that the function is a thumb function. Fixup and relocation
286218893Sdim  // values will need adjusted.
287218893Sdim  getAssembler().setIsThumbFunc(Symbol);
288288943Sdim  cast<MCSymbolMachO>(Symbol)->setThumbFunc();
289198090Srdivacky}
290198090Srdivacky
291288943Sdimbool MCMachOStreamer::EmitSymbolAttribute(MCSymbol *Sym,
292202878Srdivacky                                          MCSymbolAttr Attribute) {
293288943Sdim  MCSymbolMachO *Symbol = cast<MCSymbolMachO>(Sym);
294288943Sdim
295198090Srdivacky  // Indirect symbols are handled differently, to match how 'as' handles
296198090Srdivacky  // them. This makes writing matching .o files easier.
297202878Srdivacky  if (Attribute == MCSA_IndirectSymbol) {
298198090Srdivacky    // Note that we intentionally cannot use the symbol data here; this is
299198090Srdivacky    // important for matching the string table that 'as' generates.
300198090Srdivacky    IndirectSymbolData ISD;
301198090Srdivacky    ISD.Symbol = Symbol;
302288943Sdim    ISD.Section = getCurrentSectionOnly();
303210299Sed    getAssembler().getIndirectSymbols().push_back(ISD);
304261991Sdim    return true;
305198090Srdivacky  }
306198090Srdivacky
307198090Srdivacky  // Adding a symbol attribute always introduces the symbol, note that an
308288943Sdim  // important side effect of calling registerSymbol here is to register
309205218Srdivacky  // the symbol with the assembler.
310288943Sdim  getAssembler().registerSymbol(*Symbol);
311198090Srdivacky
312198090Srdivacky  // The implementation of symbol attributes is designed to match 'as', but it
313198090Srdivacky  // leaves much to desired. It doesn't really make sense to arbitrarily add and
314198090Srdivacky  // remove flags, but 'as' allows this (in particular, see .desc).
315198090Srdivacky  //
316198090Srdivacky  // In the future it might be worth trying to make these operations more well
317198090Srdivacky  // defined.
318198090Srdivacky  switch (Attribute) {
319202878Srdivacky  case MCSA_Invalid:
320203954Srdivacky  case MCSA_ELF_TypeFunction:
321203954Srdivacky  case MCSA_ELF_TypeIndFunction:
322203954Srdivacky  case MCSA_ELF_TypeObject:
323203954Srdivacky  case MCSA_ELF_TypeTLS:
324203954Srdivacky  case MCSA_ELF_TypeCommon:
325203954Srdivacky  case MCSA_ELF_TypeNoType:
326218893Sdim  case MCSA_ELF_TypeGnuUniqueObject:
327226633Sdim  case MCSA_Hidden:
328202878Srdivacky  case MCSA_IndirectSymbol:
329202878Srdivacky  case MCSA_Internal:
330202878Srdivacky  case MCSA_Protected:
331202878Srdivacky  case MCSA_Weak:
332202878Srdivacky  case MCSA_Local:
333360784Sdim  case MCSA_LGlobal:
334261991Sdim    return false;
335198090Srdivacky
336202878Srdivacky  case MCSA_Global:
337288943Sdim    Symbol->setExternal(true);
338208599Srdivacky    // This effectively clears the undefined lazy bit, in Darwin 'as', although
339208599Srdivacky    // it isn't very consistent because it implements this as part of symbol
340208599Srdivacky    // lookup.
341208599Srdivacky    //
342208599Srdivacky    // FIXME: Cleanup this code, these bits should be emitted based on semantic
343208599Srdivacky    // properties, not on the order of definition, etc.
344288943Sdim    Symbol->setReferenceTypeUndefinedLazy(false);
345198090Srdivacky    break;
346198090Srdivacky
347202878Srdivacky  case MCSA_LazyReference:
348198090Srdivacky    // FIXME: This requires -dynamic.
349288943Sdim    Symbol->setNoDeadStrip();
350198090Srdivacky    if (Symbol->isUndefined())
351288943Sdim      Symbol->setReferenceTypeUndefinedLazy(true);
352198090Srdivacky    break;
353198090Srdivacky
354198090Srdivacky    // Since .reference sets the no dead strip bit, it is equivalent to
355198090Srdivacky    // .no_dead_strip in practice.
356202878Srdivacky  case MCSA_Reference:
357202878Srdivacky  case MCSA_NoDeadStrip:
358288943Sdim    Symbol->setNoDeadStrip();
359198090Srdivacky    break;
360198090Srdivacky
361218893Sdim  case MCSA_SymbolResolver:
362288943Sdim    Symbol->setSymbolResolver();
363218893Sdim    break;
364218893Sdim
365309124Sdim  case MCSA_AltEntry:
366309124Sdim    Symbol->setAltEntry();
367309124Sdim    break;
368309124Sdim
369202878Srdivacky  case MCSA_PrivateExtern:
370288943Sdim    Symbol->setExternal(true);
371288943Sdim    Symbol->setPrivateExtern(true);
372198090Srdivacky    break;
373198090Srdivacky
374202878Srdivacky  case MCSA_WeakReference:
375198090Srdivacky    // FIXME: This requires -dynamic.
376198090Srdivacky    if (Symbol->isUndefined())
377288943Sdim      Symbol->setWeakReference();
378198090Srdivacky    break;
379198090Srdivacky
380202878Srdivacky  case MCSA_WeakDefinition:
381198090Srdivacky    // FIXME: 'as' enforces that this is defined and global. The manual claims
382198090Srdivacky    // it has to be in a coalesced section, but this isn't enforced.
383288943Sdim    Symbol->setWeakDefinition();
384198090Srdivacky    break;
385210299Sed
386210299Sed  case MCSA_WeakDefAutoPrivate:
387288943Sdim    Symbol->setWeakDefinition();
388288943Sdim    Symbol->setWeakReference();
389210299Sed    break;
390353358Sdim
391353358Sdim  case MCSA_Cold:
392353358Sdim    Symbol->setCold();
393353358Sdim    break;
394198090Srdivacky  }
395261991Sdim
396261991Sdim  return true;
397198090Srdivacky}
398198090Srdivacky
399198090Srdivackyvoid MCMachOStreamer::EmitSymbolDesc(MCSymbol *Symbol, unsigned DescValue) {
400198090Srdivacky  // Encode the 'desc' value into the lowest implementation defined bits.
401288943Sdim  getAssembler().registerSymbol(*Symbol);
402288943Sdim  cast<MCSymbolMachO>(Symbol)->setDesc(DescValue);
403198090Srdivacky}
404198090Srdivacky
405202878Srdivackyvoid MCMachOStreamer::EmitCommonSymbol(MCSymbol *Symbol, uint64_t Size,
406198090Srdivacky                                       unsigned ByteAlignment) {
407198090Srdivacky  // FIXME: Darwin 'as' does appear to allow redef of a .comm by itself.
408198090Srdivacky  assert(Symbol->isUndefined() && "Cannot define a symbol twice!");
409198090Srdivacky
410288943Sdim  getAssembler().registerSymbol(*Symbol);
411288943Sdim  Symbol->setExternal(true);
412288943Sdim  Symbol->setCommon(Size, ByteAlignment);
413198090Srdivacky}
414198090Srdivacky
415243830Sdimvoid MCMachOStreamer::EmitLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size,
416243830Sdim                                            unsigned ByteAlignment) {
417243830Sdim  // '.lcomm' is equivalent to '.zerofill'.
418276479Sdim  return EmitZerofill(getContext().getObjectFileInfo()->getDataBSSSection(),
419243830Sdim                      Symbol, Size, ByteAlignment);
420243830Sdim}
421243830Sdim
422288943Sdimvoid MCMachOStreamer::EmitZerofill(MCSection *Section, MCSymbol *Symbol,
423341825Sdim                                   uint64_t Size, unsigned ByteAlignment,
424341825Sdim                                   SMLoc Loc) {
425341825Sdim  // On darwin all virtual sections have zerofill type. Disallow the usage of
426341825Sdim  // .zerofill in non-virtual functions. If something similar is needed, use
427341825Sdim  // .space or .zero.
428341825Sdim  if (!Section->isVirtualSection()) {
429341825Sdim    getContext().reportError(
430341825Sdim        Loc, "The usage of .zerofill is restricted to sections of "
431341825Sdim             "ZEROFILL type. Use .zero or .space instead.");
432341825Sdim    return; // Early returning here shouldn't harm. EmitZeros should work on any
433341825Sdim            // section.
434341825Sdim  }
435198090Srdivacky
436328595Semaste  PushSection();
437328595Semaste  SwitchSection(Section);
438198090Srdivacky
439328595Semaste  // The symbol may not be present, which only creates the section.
440328595Semaste  if (Symbol) {
441328595Semaste    EmitValueToAlignment(ByteAlignment, 0, 1, 0);
442328595Semaste    EmitLabel(Symbol);
443328595Semaste    EmitZeros(Size);
444328595Semaste  }
445328595Semaste  PopSection();
446198090Srdivacky}
447198090Srdivacky
448208599Srdivacky// This should always be called with the thread local bss section.  Like the
449208599Srdivacky// .zerofill directive this doesn't actually switch sections on us.
450288943Sdimvoid MCMachOStreamer::EmitTBSSSymbol(MCSection *Section, MCSymbol *Symbol,
451208599Srdivacky                                     uint64_t Size, unsigned ByteAlignment) {
452208599Srdivacky  EmitZerofill(Section, Symbol, Size, ByteAlignment);
453208599Srdivacky}
454208599Srdivacky
455276479Sdimvoid MCMachOStreamer::EmitInstToData(const MCInst &Inst,
456276479Sdim                                     const MCSubtargetInfo &STI) {
457208599Srdivacky  MCDataFragment *DF = getOrCreateDataFragment();
458208599Srdivacky
459203954Srdivacky  SmallVector<MCFixup, 4> Fixups;
460198090Srdivacky  SmallString<256> Code;
461198090Srdivacky  raw_svector_ostream VecOS(Code);
462288943Sdim  getAssembler().getEmitter().encodeInstruction(Inst, VecOS, Fixups, STI);
463203954Srdivacky
464208599Srdivacky  // Add the fixups and data.
465296417Sdim  for (MCFixup &Fixup : Fixups) {
466296417Sdim    Fixup.setOffset(Fixup.getOffset() + DF->getContents().size());
467296417Sdim    DF->getFixups().push_back(Fixup);
468203954Srdivacky  }
469341825Sdim  DF->setHasInstructions(STI);
470208599Srdivacky  DF->getContents().append(Code.begin(), Code.end());
471208599Srdivacky}
472206083Srdivacky
473234353Sdimvoid MCMachOStreamer::FinishImpl() {
474276479Sdim  EmitFrames(&getAssembler().getBackend());
475221345Sdim
476210299Sed  // We have to set the fragment atom associations so we can relax properly for
477210299Sed  // Mach-O.
478210299Sed
479210299Sed  // First, scan the symbol table to build a lookup table from fragments to
480210299Sed  // defining symbols.
481288943Sdim  DenseMap<const MCFragment *, const MCSymbol *> DefiningSymbolMap;
482288943Sdim  for (const MCSymbol &Symbol : getAssembler().symbols()) {
483296417Sdim    if (getAssembler().isSymbolLinkerVisible(Symbol) && Symbol.isInSection() &&
484296417Sdim        !Symbol.isVariable()) {
485210299Sed      // An atom defining symbol should never be internal to a fragment.
486288943Sdim      assert(Symbol.getOffset() == 0 &&
487288943Sdim             "Invalid offset in atom defining symbol!");
488288943Sdim      DefiningSymbolMap[Symbol.getFragment()] = &Symbol;
489210299Sed    }
490210299Sed  }
491210299Sed
492210299Sed  // Set the fragment atom associations by tracking the last seen atom defining
493210299Sed  // symbol.
494296417Sdim  for (MCSection &Sec : getAssembler()) {
495288943Sdim    const MCSymbol *CurrentAtom = nullptr;
496296417Sdim    for (MCFragment &Frag : Sec) {
497296417Sdim      if (const MCSymbol *Symbol = DefiningSymbolMap.lookup(&Frag))
498288943Sdim        CurrentAtom = Symbol;
499296417Sdim      Frag.setAtom(CurrentAtom);
500210299Sed    }
501210299Sed  }
502210299Sed
503234353Sdim  this->MCObjectStreamer::FinishImpl();
504198090Srdivacky}
505198090Srdivacky
506327952SdimMCStreamer *llvm::createMachOStreamer(MCContext &Context,
507327952Sdim                                      std::unique_ptr<MCAsmBackend> &&MAB,
508341825Sdim                                      std::unique_ptr<MCObjectWriter> &&OW,
509327952Sdim                                      std::unique_ptr<MCCodeEmitter> &&CE,
510288943Sdim                                      bool RelaxAll, bool DWARFMustBeAtTheEnd,
511276479Sdim                                      bool LabelSections) {
512327952Sdim  MCMachOStreamer *S =
513341825Sdim      new MCMachOStreamer(Context, std::move(MAB), std::move(OW), std::move(CE),
514327952Sdim                          DWARFMustBeAtTheEnd, LabelSections);
515327952Sdim  const Triple &Target = Context.getObjectFileInfo()->getTargetTriple();
516344779Sdim  S->EmitVersionForTarget(Target, Context.getObjectFileInfo()->getSDKVersion());
517206083Srdivacky  if (RelaxAll)
518206083Srdivacky    S->getAssembler().setRelaxAll(true);
519206083Srdivacky  return S;
520198090Srdivacky}
521