xref: /llvm-project/llvm/lib/MC/ELFObjectWriter.cpp (revision 36293eea68cae03a71389fb2e91dbc2cc0b43b4b)
1 //===- lib/MC/ELFObjectWriter.cpp - ELF File Writer -----------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This file implements ELF object file writer information.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #include "llvm/ADT/ArrayRef.h"
14 #include "llvm/ADT/DenseMap.h"
15 #include "llvm/ADT/STLExtras.h"
16 #include "llvm/ADT/SmallVector.h"
17 #include "llvm/ADT/Statistic.h"
18 #include "llvm/ADT/StringExtras.h"
19 #include "llvm/ADT/StringRef.h"
20 #include "llvm/ADT/Twine.h"
21 #include "llvm/ADT/iterator.h"
22 #include "llvm/BinaryFormat/ELF.h"
23 #include "llvm/MC/MCAsmBackend.h"
24 #include "llvm/MC/MCAsmInfo.h"
25 #include "llvm/MC/MCAssembler.h"
26 #include "llvm/MC/MCContext.h"
27 #include "llvm/MC/MCELFExtras.h"
28 #include "llvm/MC/MCELFObjectWriter.h"
29 #include "llvm/MC/MCExpr.h"
30 #include "llvm/MC/MCFixup.h"
31 #include "llvm/MC/MCFixupKindInfo.h"
32 #include "llvm/MC/MCFragment.h"
33 #include "llvm/MC/MCObjectWriter.h"
34 #include "llvm/MC/MCSection.h"
35 #include "llvm/MC/MCSectionELF.h"
36 #include "llvm/MC/MCSymbol.h"
37 #include "llvm/MC/MCSymbolELF.h"
38 #include "llvm/MC/MCTargetOptions.h"
39 #include "llvm/MC/MCValue.h"
40 #include "llvm/MC/StringTableBuilder.h"
41 #include "llvm/Support/Alignment.h"
42 #include "llvm/Support/Casting.h"
43 #include "llvm/Support/CommandLine.h"
44 #include "llvm/Support/Compression.h"
45 #include "llvm/Support/Endian.h"
46 #include "llvm/Support/EndianStream.h"
47 #include "llvm/Support/Error.h"
48 #include "llvm/Support/ErrorHandling.h"
49 #include "llvm/Support/LEB128.h"
50 #include "llvm/Support/MathExtras.h"
51 #include "llvm/Support/SMLoc.h"
52 #include "llvm/Support/raw_ostream.h"
53 #include "llvm/TargetParser/Host.h"
54 #include <algorithm>
55 #include <cassert>
56 #include <cstddef>
57 #include <cstdint>
58 #include <map>
59 #include <memory>
60 #include <string>
61 #include <utility>
62 #include <vector>
63 
64 using namespace llvm;
65 
66 #define DEBUG_TYPE "elf-object-writer"
67 
68 namespace {
69 namespace stats {
70 
71 STATISTIC(AllocTextBytes, "Total size of SHF_ALLOC text sections");
72 STATISTIC(AllocROBytes, "Total size of SHF_ALLOC readonly sections");
73 STATISTIC(AllocRWBytes, "Total size of SHF_ALLOC read-write sections");
74 STATISTIC(StrtabBytes, "Total size of SHT_STRTAB sections");
75 STATISTIC(SymtabBytes, "Total size of SHT_SYMTAB sections");
76 STATISTIC(RelocationBytes, "Total size of relocation sections");
77 STATISTIC(DynsymBytes, "Total size of SHT_DYNSYM sections");
78 STATISTIC(DebugBytes, "Total size of debug info sections");
79 STATISTIC(UnwindBytes, "Total size of unwind sections");
80 STATISTIC(OtherBytes, "Total size of uncategorized sections");
81 
82 } // namespace stats
83 
84 struct ELFWriter;
85 
86 bool isDwoSection(const MCSectionELF &Sec) {
87   return Sec.getName().ends_with(".dwo");
88 }
89 
90 class SymbolTableWriter {
91   ELFWriter &EWriter;
92   bool Is64Bit;
93 
94   // indexes we are going to write to .symtab_shndx.
95   std::vector<uint32_t> ShndxIndexes;
96 
97   // The numbel of symbols written so far.
98   unsigned NumWritten;
99 
100   void createSymtabShndx();
101 
102   template <typename T> void write(T Value);
103 
104 public:
105   SymbolTableWriter(ELFWriter &EWriter, bool Is64Bit);
106 
107   void writeSymbol(uint32_t name, uint8_t info, uint64_t value, uint64_t size,
108                    uint8_t other, uint32_t shndx, bool Reserved);
109 
110   ArrayRef<uint32_t> getShndxIndexes() const { return ShndxIndexes; }
111 };
112 
113 struct ELFWriter {
114   ELFObjectWriter &OWriter;
115   support::endian::Writer W;
116 
117   enum DwoMode {
118     AllSections,
119     NonDwoOnly,
120     DwoOnly,
121   } Mode;
122 
123   static uint64_t symbolValue(const MCAssembler &Asm, const MCSymbol &Sym);
124   static bool isInSymtab(const MCAssembler &Asm, const MCSymbolELF &Symbol,
125                          bool Used, bool Renamed);
126 
127   /// Helper struct for containing some precomputed information on symbols.
128   struct ELFSymbolData {
129     const MCSymbolELF *Symbol;
130     StringRef Name;
131     uint32_t SectionIndex;
132     uint32_t Order;
133   };
134 
135   /// @}
136   /// @name Symbol Table Data
137   /// @{
138 
139   StringTableBuilder StrTabBuilder{StringTableBuilder::ELF};
140 
141   /// @}
142 
143   // This holds the symbol table index of the last local symbol.
144   unsigned LastLocalSymbolIndex = ~0u;
145   // This holds the .strtab section index.
146   unsigned StringTableIndex = ~0u;
147   // This holds the .symtab section index.
148   unsigned SymbolTableIndex = ~0u;
149 
150   // Sections in the order they are to be output in the section table.
151   std::vector<MCSectionELF *> SectionTable;
152   unsigned addToSectionTable(MCSectionELF *Sec);
153 
154   // TargetObjectWriter wrappers.
155   bool is64Bit() const;
156 
157   uint64_t align(Align Alignment);
158 
159   bool maybeWriteCompression(uint32_t ChType, uint64_t Size,
160                              SmallVectorImpl<uint8_t> &CompressedContents,
161                              Align Alignment);
162 
163 public:
164   ELFWriter(ELFObjectWriter &OWriter, raw_pwrite_stream &OS,
165             bool IsLittleEndian, DwoMode Mode)
166       : OWriter(OWriter), W(OS, IsLittleEndian ? llvm::endianness::little
167                                                : llvm::endianness::big),
168         Mode(Mode) {}
169 
170   void writeWord(uint64_t Word) {
171     if (is64Bit())
172       W.write<uint64_t>(Word);
173     else
174       W.write<uint32_t>(Word);
175   }
176 
177   template <typename T> void write(T Val) {
178     W.write(Val);
179   }
180 
181   void writeHeader(const MCAssembler &Asm);
182 
183   void writeSymbol(const MCAssembler &Asm, SymbolTableWriter &Writer,
184                    uint32_t StringIndex, ELFSymbolData &MSD);
185 
186   // Map from a signature symbol to the group section index
187   using RevGroupMapTy = DenseMap<const MCSymbol *, unsigned>;
188 
189   /// Compute the symbol table data
190   ///
191   /// \param Asm - The assembler.
192   /// \param RevGroupMap - Maps a signature symbol to the group section.
193   void computeSymbolTable(MCAssembler &Asm, const RevGroupMapTy &RevGroupMap);
194 
195   void writeAddrsigSection();
196 
197   MCSectionELF *createRelocationSection(MCContext &Ctx,
198                                         const MCSectionELF &Sec);
199 
200   void writeSectionHeaders(const MCAssembler &Asm);
201 
202   void writeSectionData(const MCAssembler &Asm, MCSection &Sec);
203 
204   void writeSectionHeaderEntry(uint32_t Name, uint32_t Type, uint64_t Flags,
205                                uint64_t Address, uint64_t Offset, uint64_t Size,
206                                uint32_t Link, uint32_t Info,
207                                MaybeAlign Alignment, uint64_t EntrySize);
208 
209   void writeRelocations(const MCAssembler &Asm, const MCSectionELF &Sec);
210 
211   uint64_t writeObject(MCAssembler &Asm);
212   void writeSectionHeader(uint32_t GroupSymbolIndex, uint64_t Offset,
213                           uint64_t Size, const MCSectionELF &Section);
214 };
215 } // end anonymous namespace
216 
217 uint64_t ELFWriter::align(Align Alignment) {
218   uint64_t Offset = W.OS.tell();
219   uint64_t NewOffset = alignTo(Offset, Alignment);
220   W.OS.write_zeros(NewOffset - Offset);
221   return NewOffset;
222 }
223 
224 unsigned ELFWriter::addToSectionTable(MCSectionELF *Sec) {
225   SectionTable.push_back(Sec);
226   StrTabBuilder.add(Sec->getName());
227   return SectionTable.size();
228 }
229 
230 void SymbolTableWriter::createSymtabShndx() {
231   if (!ShndxIndexes.empty())
232     return;
233 
234   ShndxIndexes.resize(NumWritten);
235 }
236 
237 template <typename T> void SymbolTableWriter::write(T Value) {
238   EWriter.write(Value);
239 }
240 
241 SymbolTableWriter::SymbolTableWriter(ELFWriter &EWriter, bool Is64Bit)
242     : EWriter(EWriter), Is64Bit(Is64Bit), NumWritten(0) {}
243 
244 void SymbolTableWriter::writeSymbol(uint32_t name, uint8_t info, uint64_t value,
245                                     uint64_t size, uint8_t other,
246                                     uint32_t shndx, bool Reserved) {
247   bool LargeIndex = shndx >= ELF::SHN_LORESERVE && !Reserved;
248 
249   if (LargeIndex)
250     createSymtabShndx();
251 
252   if (!ShndxIndexes.empty()) {
253     if (LargeIndex)
254       ShndxIndexes.push_back(shndx);
255     else
256       ShndxIndexes.push_back(0);
257   }
258 
259   uint16_t Index = LargeIndex ? uint16_t(ELF::SHN_XINDEX) : shndx;
260 
261   if (Is64Bit) {
262     write(name);  // st_name
263     write(info);  // st_info
264     write(other); // st_other
265     write(Index); // st_shndx
266     write(value); // st_value
267     write(size);  // st_size
268   } else {
269     write(name);            // st_name
270     write(uint32_t(value)); // st_value
271     write(uint32_t(size));  // st_size
272     write(info);            // st_info
273     write(other);           // st_other
274     write(Index);           // st_shndx
275   }
276 
277   ++NumWritten;
278 }
279 
280 bool ELFWriter::is64Bit() const {
281   return OWriter.TargetObjectWriter->is64Bit();
282 }
283 
284 // Emit the ELF header.
285 void ELFWriter::writeHeader(const MCAssembler &Asm) {
286   // ELF Header
287   // ----------
288   //
289   // Note
290   // ----
291   // emitWord method behaves differently for ELF32 and ELF64, writing
292   // 4 bytes in the former and 8 in the latter.
293 
294   W.OS << ELF::ElfMagic; // e_ident[EI_MAG0] to e_ident[EI_MAG3]
295 
296   W.OS << char(is64Bit() ? ELF::ELFCLASS64 : ELF::ELFCLASS32); // e_ident[EI_CLASS]
297 
298   // e_ident[EI_DATA]
299   W.OS << char(W.Endian == llvm::endianness::little ? ELF::ELFDATA2LSB
300                                                     : ELF::ELFDATA2MSB);
301 
302   W.OS << char(ELF::EV_CURRENT);        // e_ident[EI_VERSION]
303   // e_ident[EI_OSABI]
304   uint8_t OSABI = OWriter.TargetObjectWriter->getOSABI();
305   W.OS << char(OSABI == ELF::ELFOSABI_NONE && OWriter.seenGnuAbi()
306                    ? int(ELF::ELFOSABI_GNU)
307                    : OSABI);
308   // e_ident[EI_ABIVERSION]
309   W.OS << char(OWriter.OverrideABIVersion
310                    ? *OWriter.OverrideABIVersion
311                    : OWriter.TargetObjectWriter->getABIVersion());
312 
313   W.OS.write_zeros(ELF::EI_NIDENT - ELF::EI_PAD);
314 
315   W.write<uint16_t>(ELF::ET_REL);             // e_type
316 
317   W.write<uint16_t>(OWriter.TargetObjectWriter->getEMachine()); // e_machine = target
318 
319   W.write<uint32_t>(ELF::EV_CURRENT);         // e_version
320   writeWord(0); // e_entry, no entry point in .o file
321   writeWord(0); // e_phoff, no program header for .o
322   writeWord(0); // e_shoff = sec hdr table off in bytes
323 
324   // e_flags = whatever the target wants
325   W.write<uint32_t>(OWriter.getELFHeaderEFlags());
326 
327   // e_ehsize = ELF header size
328   W.write<uint16_t>(is64Bit() ? sizeof(ELF::Elf64_Ehdr)
329                               : sizeof(ELF::Elf32_Ehdr));
330 
331   W.write<uint16_t>(0);                  // e_phentsize = prog header entry size
332   W.write<uint16_t>(0);                  // e_phnum = # prog header entries = 0
333 
334   // e_shentsize = Section header entry size
335   W.write<uint16_t>(is64Bit() ? sizeof(ELF::Elf64_Shdr)
336                               : sizeof(ELF::Elf32_Shdr));
337 
338   // e_shnum     = # of section header ents
339   W.write<uint16_t>(0);
340 
341   // e_shstrndx  = Section # of '.strtab'
342   assert(StringTableIndex < ELF::SHN_LORESERVE);
343   W.write<uint16_t>(StringTableIndex);
344 }
345 
346 uint64_t ELFWriter::symbolValue(const MCAssembler &Asm, const MCSymbol &Sym) {
347   if (Sym.isCommon())
348     return Sym.getCommonAlignment()->value();
349 
350   uint64_t Res;
351   if (!Asm.getSymbolOffset(Sym, Res))
352     return 0;
353 
354   if (Asm.isThumbFunc(&Sym))
355     Res |= 1;
356 
357   return Res;
358 }
359 
360 static uint8_t mergeTypeForSet(uint8_t origType, uint8_t newType) {
361   uint8_t Type = newType;
362 
363   // Propagation rules:
364   // IFUNC > FUNC > OBJECT > NOTYPE
365   // TLS_OBJECT > OBJECT > NOTYPE
366   //
367   // dont let the new type degrade the old type
368   switch (origType) {
369   default:
370     break;
371   case ELF::STT_GNU_IFUNC:
372     if (Type == ELF::STT_FUNC || Type == ELF::STT_OBJECT ||
373         Type == ELF::STT_NOTYPE || Type == ELF::STT_TLS)
374       Type = ELF::STT_GNU_IFUNC;
375     break;
376   case ELF::STT_FUNC:
377     if (Type == ELF::STT_OBJECT || Type == ELF::STT_NOTYPE ||
378         Type == ELF::STT_TLS)
379       Type = ELF::STT_FUNC;
380     break;
381   case ELF::STT_OBJECT:
382     if (Type == ELF::STT_NOTYPE)
383       Type = ELF::STT_OBJECT;
384     break;
385   case ELF::STT_TLS:
386     if (Type == ELF::STT_OBJECT || Type == ELF::STT_NOTYPE ||
387         Type == ELF::STT_GNU_IFUNC || Type == ELF::STT_FUNC)
388       Type = ELF::STT_TLS;
389     break;
390   }
391 
392   return Type;
393 }
394 
395 static bool isIFunc(const MCSymbolELF *Symbol) {
396   while (Symbol->getType() != ELF::STT_GNU_IFUNC) {
397     const MCSymbolRefExpr *Value;
398     if (!Symbol->isVariable() ||
399         !(Value = dyn_cast<MCSymbolRefExpr>(Symbol->getVariableValue())) ||
400         Value->getKind() != MCSymbolRefExpr::VK_None ||
401         mergeTypeForSet(Symbol->getType(), ELF::STT_GNU_IFUNC) != ELF::STT_GNU_IFUNC)
402       return false;
403     Symbol = &cast<MCSymbolELF>(Value->getSymbol());
404   }
405   return true;
406 }
407 
408 void ELFWriter::writeSymbol(const MCAssembler &Asm, SymbolTableWriter &Writer,
409                             uint32_t StringIndex, ELFSymbolData &MSD) {
410   const auto &Symbol = cast<MCSymbolELF>(*MSD.Symbol);
411   const MCSymbolELF *Base =
412       cast_or_null<MCSymbolELF>(Asm.getBaseSymbol(Symbol));
413 
414   // This has to be in sync with when computeSymbolTable uses SHN_ABS or
415   // SHN_COMMON.
416   bool IsReserved = !Base || Symbol.isCommon();
417 
418   // Binding and Type share the same byte as upper and lower nibbles
419   uint8_t Binding = Symbol.getBinding();
420   uint8_t Type = Symbol.getType();
421   if (isIFunc(&Symbol))
422     Type = ELF::STT_GNU_IFUNC;
423   if (Base) {
424     Type = mergeTypeForSet(Type, Base->getType());
425   }
426   uint8_t Info = (Binding << 4) | Type;
427 
428   // Other and Visibility share the same byte with Visibility using the lower
429   // 2 bits
430   uint8_t Visibility = Symbol.getVisibility();
431   uint8_t Other = Symbol.getOther() | Visibility;
432 
433   uint64_t Value = symbolValue(Asm, *MSD.Symbol);
434   uint64_t Size = 0;
435 
436   const MCExpr *ESize = MSD.Symbol->getSize();
437   if (!ESize && Base) {
438     // For expressions like .set y, x+1, if y's size is unset, inherit from x.
439     ESize = Base->getSize();
440 
441     // For `.size x, 2; y = x; .size y, 1; z = y; z1 = z; .symver y, y@v1`, z,
442     // z1, and y@v1's st_size equals y's. However, `Base` is `x` which will give
443     // us 2. Follow the MCSymbolRefExpr assignment chain, which covers most
444     // needs. MCBinaryExpr is not handled.
445     const MCSymbolELF *Sym = &Symbol;
446     while (Sym->isVariable()) {
447       if (auto *Expr =
448               dyn_cast<MCSymbolRefExpr>(Sym->getVariableValue(false))) {
449         Sym = cast<MCSymbolELF>(&Expr->getSymbol());
450         if (!Sym->getSize())
451           continue;
452         ESize = Sym->getSize();
453       }
454       break;
455     }
456   }
457 
458   if (ESize) {
459     int64_t Res;
460     if (!ESize->evaluateKnownAbsolute(Res, Asm))
461       report_fatal_error("Size expression must be absolute.");
462     Size = Res;
463   }
464 
465   // Write out the symbol table entry
466   Writer.writeSymbol(StringIndex, Info, Value, Size, Other, MSD.SectionIndex,
467                      IsReserved);
468 }
469 
470 bool ELFWriter::isInSymtab(const MCAssembler &Asm, const MCSymbolELF &Symbol,
471                            bool Used, bool Renamed) {
472   if (Symbol.isVariable()) {
473     const MCExpr *Expr = Symbol.getVariableValue();
474     // Target Expressions that are always inlined do not appear in the symtab
475     if (const auto *T = dyn_cast<MCTargetExpr>(Expr))
476       if (T->inlineAssignedExpr())
477         return false;
478     if (const MCSymbolRefExpr *Ref = dyn_cast<MCSymbolRefExpr>(Expr)) {
479       if (Ref->getKind() == MCSymbolRefExpr::VK_WEAKREF)
480         return false;
481     }
482   }
483 
484   if (Used)
485     return true;
486 
487   if (Renamed)
488     return false;
489 
490   if (Symbol.isVariable() && Symbol.isUndefined()) {
491     // FIXME: this is here just to diagnose the case of a var = commmon_sym.
492     Asm.getBaseSymbol(Symbol);
493     return false;
494   }
495 
496   if (Symbol.isTemporary())
497     return false;
498 
499   if (Symbol.getType() == ELF::STT_SECTION)
500     return false;
501 
502   return true;
503 }
504 
505 void ELFWriter::computeSymbolTable(MCAssembler &Asm,
506                                    const RevGroupMapTy &RevGroupMap) {
507   MCContext &Ctx = Asm.getContext();
508   SymbolTableWriter Writer(*this, is64Bit());
509 
510   // Symbol table
511   unsigned EntrySize = is64Bit() ? ELF::SYMENTRY_SIZE64 : ELF::SYMENTRY_SIZE32;
512   MCSectionELF *SymtabSection =
513       Ctx.getELFSection(".symtab", ELF::SHT_SYMTAB, 0, EntrySize);
514   SymtabSection->setAlignment(is64Bit() ? Align(8) : Align(4));
515   SymbolTableIndex = addToSectionTable(SymtabSection);
516 
517   uint64_t SecStart = align(SymtabSection->getAlign());
518 
519   // The first entry is the undefined symbol entry.
520   Writer.writeSymbol(0, 0, 0, 0, 0, 0, false);
521 
522   std::vector<ELFSymbolData> LocalSymbolData;
523   std::vector<ELFSymbolData> ExternalSymbolData;
524   MutableArrayRef<std::pair<std::string, size_t>> FileNames =
525       OWriter.getFileNames();
526   for (const std::pair<std::string, size_t> &F : FileNames)
527     StrTabBuilder.add(F.first);
528 
529   // Add the data for the symbols.
530   bool HasLargeSectionIndex = false;
531   for (auto It : llvm::enumerate(Asm.symbols())) {
532     const auto &Symbol = cast<MCSymbolELF>(It.value());
533     bool Used = Symbol.isUsedInReloc();
534     bool WeakrefUsed = Symbol.isWeakrefUsedInReloc();
535     bool isSignature = Symbol.isSignature();
536 
537     if (!isInSymtab(Asm, Symbol, Used || WeakrefUsed || isSignature,
538                     OWriter.Renames.count(&Symbol)))
539       continue;
540 
541     if (Symbol.isTemporary() && Symbol.isUndefined()) {
542       Ctx.reportError(SMLoc(), "Undefined temporary symbol " + Symbol.getName());
543       continue;
544     }
545 
546     ELFSymbolData MSD;
547     MSD.Symbol = cast<MCSymbolELF>(&Symbol);
548     MSD.Order = It.index();
549 
550     bool Local = Symbol.getBinding() == ELF::STB_LOCAL;
551     assert(Local || !Symbol.isTemporary());
552 
553     if (Symbol.isAbsolute()) {
554       MSD.SectionIndex = ELF::SHN_ABS;
555     } else if (Symbol.isCommon()) {
556       if (Symbol.isTargetCommon()) {
557         MSD.SectionIndex = Symbol.getIndex();
558       } else {
559         assert(!Local);
560         MSD.SectionIndex = ELF::SHN_COMMON;
561       }
562     } else if (Symbol.isUndefined()) {
563       if (isSignature && !Used) {
564         MSD.SectionIndex = RevGroupMap.lookup(&Symbol);
565         if (MSD.SectionIndex >= ELF::SHN_LORESERVE)
566           HasLargeSectionIndex = true;
567       } else {
568         MSD.SectionIndex = ELF::SHN_UNDEF;
569       }
570     } else {
571       const MCSectionELF &Section =
572           static_cast<const MCSectionELF &>(Symbol.getSection());
573 
574       // We may end up with a situation when section symbol is technically
575       // defined, but should not be. That happens because we explicitly
576       // pre-create few .debug_* sections to have accessors.
577       // And if these sections were not really defined in the code, but were
578       // referenced, we simply error out.
579       if (!Section.isRegistered()) {
580         assert(static_cast<const MCSymbolELF &>(Symbol).getType() ==
581                ELF::STT_SECTION);
582         Ctx.reportError(SMLoc(),
583                         "Undefined section reference: " + Symbol.getName());
584         continue;
585       }
586 
587       if (Mode == NonDwoOnly && isDwoSection(Section))
588         continue;
589       MSD.SectionIndex = Section.getOrdinal();
590       assert(MSD.SectionIndex && "Invalid section index!");
591       if (MSD.SectionIndex >= ELF::SHN_LORESERVE)
592         HasLargeSectionIndex = true;
593     }
594 
595     // Temporary symbols generated for certain assembler features (.eh_frame,
596     // .debug_line) of an empty name may be referenced by relocations due to
597     // linker relaxation. Rename them to ".L0 " to match the gas fake label name
598     // and allow ld/objcopy --discard-locals to discard such symbols.
599     StringRef Name = Symbol.getName();
600     if (Name.empty())
601       Name = ".L0 ";
602 
603     // Sections have their own string table
604     if (Symbol.getType() != ELF::STT_SECTION) {
605       MSD.Name = Name;
606       StrTabBuilder.add(Name);
607     }
608 
609     if (Local)
610       LocalSymbolData.push_back(MSD);
611     else
612       ExternalSymbolData.push_back(MSD);
613   }
614 
615   // This holds the .symtab_shndx section index.
616   unsigned SymtabShndxSectionIndex = 0;
617 
618   if (HasLargeSectionIndex) {
619     MCSectionELF *SymtabShndxSection =
620         Ctx.getELFSection(".symtab_shndx", ELF::SHT_SYMTAB_SHNDX, 0, 4);
621     SymtabShndxSectionIndex = addToSectionTable(SymtabShndxSection);
622     SymtabShndxSection->setAlignment(Align(4));
623   }
624 
625   StrTabBuilder.finalize();
626 
627   // Make the first STT_FILE precede previous local symbols.
628   unsigned Index = 1;
629   auto FileNameIt = FileNames.begin();
630   if (!FileNames.empty())
631     FileNames[0].second = 0;
632 
633   for (ELFSymbolData &MSD : LocalSymbolData) {
634     // Emit STT_FILE symbols before their associated local symbols.
635     for (; FileNameIt != FileNames.end() && FileNameIt->second <= MSD.Order;
636          ++FileNameIt) {
637       Writer.writeSymbol(StrTabBuilder.getOffset(FileNameIt->first),
638                          ELF::STT_FILE | ELF::STB_LOCAL, 0, 0, ELF::STV_DEFAULT,
639                          ELF::SHN_ABS, true);
640       ++Index;
641     }
642 
643     unsigned StringIndex = MSD.Symbol->getType() == ELF::STT_SECTION
644                                ? 0
645                                : StrTabBuilder.getOffset(MSD.Name);
646     MSD.Symbol->setIndex(Index++);
647     writeSymbol(Asm, Writer, StringIndex, MSD);
648   }
649   for (; FileNameIt != FileNames.end(); ++FileNameIt) {
650     Writer.writeSymbol(StrTabBuilder.getOffset(FileNameIt->first),
651                        ELF::STT_FILE | ELF::STB_LOCAL, 0, 0, ELF::STV_DEFAULT,
652                        ELF::SHN_ABS, true);
653     ++Index;
654   }
655 
656   // Write the symbol table entries.
657   LastLocalSymbolIndex = Index;
658 
659   for (ELFSymbolData &MSD : ExternalSymbolData) {
660     unsigned StringIndex = StrTabBuilder.getOffset(MSD.Name);
661     MSD.Symbol->setIndex(Index++);
662     writeSymbol(Asm, Writer, StringIndex, MSD);
663     assert(MSD.Symbol->getBinding() != ELF::STB_LOCAL);
664   }
665 
666   uint64_t SecEnd = W.OS.tell();
667   SymtabSection->setOffsets(SecStart, SecEnd);
668 
669   ArrayRef<uint32_t> ShndxIndexes = Writer.getShndxIndexes();
670   if (ShndxIndexes.empty()) {
671     assert(SymtabShndxSectionIndex == 0);
672     return;
673   }
674   assert(SymtabShndxSectionIndex != 0);
675 
676   SecStart = W.OS.tell();
677   MCSectionELF *SymtabShndxSection = SectionTable[SymtabShndxSectionIndex - 1];
678   for (uint32_t Index : ShndxIndexes)
679     write(Index);
680   SecEnd = W.OS.tell();
681   SymtabShndxSection->setOffsets(SecStart, SecEnd);
682 }
683 
684 void ELFWriter::writeAddrsigSection() {
685   for (const MCSymbol *Sym : OWriter.getAddrsigSyms())
686     if (Sym->getIndex() != 0)
687       encodeULEB128(Sym->getIndex(), W.OS);
688 }
689 
690 MCSectionELF *ELFWriter::createRelocationSection(MCContext &Ctx,
691                                                  const MCSectionELF &Sec) {
692   if (OWriter.Relocations[&Sec].empty())
693     return nullptr;
694 
695   unsigned Flags = ELF::SHF_INFO_LINK;
696   if (Sec.getFlags() & ELF::SHF_GROUP)
697     Flags = ELF::SHF_GROUP;
698 
699   const StringRef SectionName = Sec.getName();
700   const MCTargetOptions *TO = Ctx.getTargetOptions();
701   if (TO && TO->Crel) {
702     MCSectionELF *RelaSection =
703         Ctx.createELFRelSection(".crel" + SectionName, ELF::SHT_CREL, Flags,
704                                 /*EntrySize=*/1, Sec.getGroup(), &Sec);
705     return RelaSection;
706   }
707 
708   const bool Rela = OWriter.usesRela(TO, Sec);
709   unsigned EntrySize;
710   if (Rela)
711     EntrySize = is64Bit() ? sizeof(ELF::Elf64_Rela) : sizeof(ELF::Elf32_Rela);
712   else
713     EntrySize = is64Bit() ? sizeof(ELF::Elf64_Rel) : sizeof(ELF::Elf32_Rel);
714 
715   MCSectionELF *RelaSection =
716       Ctx.createELFRelSection(((Rela ? ".rela" : ".rel") + SectionName),
717                               Rela ? ELF::SHT_RELA : ELF::SHT_REL, Flags,
718                               EntrySize, Sec.getGroup(), &Sec);
719   RelaSection->setAlignment(is64Bit() ? Align(8) : Align(4));
720   return RelaSection;
721 }
722 
723 // Include the debug info compression header.
724 bool ELFWriter::maybeWriteCompression(
725     uint32_t ChType, uint64_t Size,
726     SmallVectorImpl<uint8_t> &CompressedContents, Align Alignment) {
727   uint64_t HdrSize =
728       is64Bit() ? sizeof(ELF::Elf64_Chdr) : sizeof(ELF::Elf32_Chdr);
729   if (Size <= HdrSize + CompressedContents.size())
730     return false;
731   // Platform specific header is followed by compressed data.
732   if (is64Bit()) {
733     // Write Elf64_Chdr header.
734     write(static_cast<ELF::Elf64_Word>(ChType));
735     write(static_cast<ELF::Elf64_Word>(0)); // ch_reserved field.
736     write(static_cast<ELF::Elf64_Xword>(Size));
737     write(static_cast<ELF::Elf64_Xword>(Alignment.value()));
738   } else {
739     // Write Elf32_Chdr header otherwise.
740     write(static_cast<ELF::Elf32_Word>(ChType));
741     write(static_cast<ELF::Elf32_Word>(Size));
742     write(static_cast<ELF::Elf32_Word>(Alignment.value()));
743   }
744   return true;
745 }
746 
747 void ELFWriter::writeSectionData(const MCAssembler &Asm, MCSection &Sec) {
748   MCSectionELF &Section = static_cast<MCSectionELF &>(Sec);
749   StringRef SectionName = Section.getName();
750   auto &Ctx = Asm.getContext();
751   const DebugCompressionType CompressionType =
752       Ctx.getTargetOptions() ? Ctx.getTargetOptions()->CompressDebugSections
753                              : DebugCompressionType::None;
754   if (CompressionType == DebugCompressionType::None ||
755       !SectionName.starts_with(".debug_")) {
756     Asm.writeSectionData(W.OS, &Section);
757     return;
758   }
759 
760   SmallVector<char, 128> UncompressedData;
761   raw_svector_ostream VecOS(UncompressedData);
762   Asm.writeSectionData(VecOS, &Section);
763   ArrayRef<uint8_t> Uncompressed =
764       ArrayRef(reinterpret_cast<uint8_t *>(UncompressedData.data()),
765                UncompressedData.size());
766 
767   SmallVector<uint8_t, 128> Compressed;
768   uint32_t ChType;
769   switch (CompressionType) {
770   case DebugCompressionType::None:
771     llvm_unreachable("has been handled");
772   case DebugCompressionType::Zlib:
773     ChType = ELF::ELFCOMPRESS_ZLIB;
774     break;
775   case DebugCompressionType::Zstd:
776     ChType = ELF::ELFCOMPRESS_ZSTD;
777     break;
778   }
779   compression::compress(compression::Params(CompressionType), Uncompressed,
780                         Compressed);
781   if (!maybeWriteCompression(ChType, UncompressedData.size(), Compressed,
782                              Sec.getAlign())) {
783     W.OS << UncompressedData;
784     return;
785   }
786 
787   Section.setFlags(Section.getFlags() | ELF::SHF_COMPRESSED);
788   // Alignment field should reflect the requirements of
789   // the compressed section header.
790   Section.setAlignment(is64Bit() ? Align(8) : Align(4));
791   W.OS << toStringRef(Compressed);
792 }
793 
794 void ELFWriter::writeSectionHeaderEntry(uint32_t Name, uint32_t Type,
795                                         uint64_t Flags, uint64_t Address,
796                                         uint64_t Offset, uint64_t Size,
797                                         uint32_t Link, uint32_t Info,
798                                         MaybeAlign Alignment,
799                                         uint64_t EntrySize) {
800   W.write<uint32_t>(Name);        // sh_name: index into string table
801   W.write<uint32_t>(Type);        // sh_type
802   writeWord(Flags);               // sh_flags
803   writeWord(Address);             // sh_addr
804   writeWord(Offset);              // sh_offset
805   writeWord(Size);                // sh_size
806   W.write<uint32_t>(Link);        // sh_link
807   W.write<uint32_t>(Info);        // sh_info
808   writeWord(Alignment ? Alignment->value() : 0); // sh_addralign
809   writeWord(EntrySize);                          // sh_entsize
810 }
811 
812 template <bool Is64>
813 static void encodeCrel(ArrayRef<ELFRelocationEntry> Relocs, raw_ostream &OS) {
814   using uint = std::conditional_t<Is64, uint64_t, uint32_t>;
815   ELF::encodeCrel<Is64>(OS, Relocs, [&](const ELFRelocationEntry &R) {
816     uint32_t SymIdx = R.Symbol ? R.Symbol->getIndex() : 0;
817     return ELF::Elf_Crel<Is64>{static_cast<uint>(R.Offset), SymIdx, R.Type,
818                                std::make_signed_t<uint>(R.Addend)};
819   });
820 }
821 
822 void ELFWriter::writeRelocations(const MCAssembler &Asm,
823                                        const MCSectionELF &Sec) {
824   std::vector<ELFRelocationEntry> &Relocs = OWriter.Relocations[&Sec];
825   const MCTargetOptions *TO = Asm.getContext().getTargetOptions();
826   const bool Rela = OWriter.usesRela(TO, Sec);
827 
828   // Sort the relocation entries. MIPS needs this.
829   OWriter.TargetObjectWriter->sortRelocs(Asm, Relocs);
830 
831   if (OWriter.TargetObjectWriter->getEMachine() == ELF::EM_MIPS) {
832     for (const ELFRelocationEntry &Entry : Relocs) {
833       uint32_t SymIdx = Entry.Symbol ? Entry.Symbol->getIndex() : 0;
834       if (is64Bit()) {
835         write(Entry.Offset);
836         write(uint32_t(SymIdx));
837         write(OWriter.TargetObjectWriter->getRSsym(Entry.Type));
838         write(OWriter.TargetObjectWriter->getRType3(Entry.Type));
839         write(OWriter.TargetObjectWriter->getRType2(Entry.Type));
840         write(OWriter.TargetObjectWriter->getRType(Entry.Type));
841         if (Rela)
842           write(Entry.Addend);
843       } else {
844         write(uint32_t(Entry.Offset));
845         ELF::Elf32_Rela ERE32;
846         ERE32.setSymbolAndType(SymIdx, Entry.Type);
847         write(ERE32.r_info);
848         if (Rela)
849           write(uint32_t(Entry.Addend));
850         if (uint32_t RType =
851                 OWriter.TargetObjectWriter->getRType2(Entry.Type)) {
852           write(uint32_t(Entry.Offset));
853           ERE32.setSymbolAndType(0, RType);
854           write(ERE32.r_info);
855           write(uint32_t(0));
856         }
857         if (uint32_t RType =
858                 OWriter.TargetObjectWriter->getRType3(Entry.Type)) {
859           write(uint32_t(Entry.Offset));
860           ERE32.setSymbolAndType(0, RType);
861           write(ERE32.r_info);
862           write(uint32_t(0));
863         }
864       }
865     }
866   } else if (TO && TO->Crel) {
867     if (is64Bit())
868       encodeCrel<true>(Relocs, W.OS);
869     else
870       encodeCrel<false>(Relocs, W.OS);
871   } else {
872     for (const ELFRelocationEntry &Entry : Relocs) {
873       uint32_t Symidx = Entry.Symbol ? Entry.Symbol->getIndex() : 0;
874       if (is64Bit()) {
875         write(Entry.Offset);
876         ELF::Elf64_Rela ERE;
877         ERE.setSymbolAndType(Symidx, Entry.Type);
878         write(ERE.r_info);
879         if (Rela)
880           write(Entry.Addend);
881       } else {
882         write(uint32_t(Entry.Offset));
883         ELF::Elf32_Rela ERE;
884         ERE.setSymbolAndType(Symidx, Entry.Type);
885         write(ERE.r_info);
886         if (Rela)
887           write(uint32_t(Entry.Addend));
888       }
889     }
890   }
891 }
892 
893 void ELFWriter::writeSectionHeader(uint32_t GroupSymbolIndex, uint64_t Offset,
894                                    uint64_t Size, const MCSectionELF &Section) {
895   uint64_t sh_link = 0;
896   uint64_t sh_info = 0;
897 
898   switch(Section.getType()) {
899   default:
900     // Nothing to do.
901     break;
902 
903   case ELF::SHT_DYNAMIC:
904     llvm_unreachable("SHT_DYNAMIC in a relocatable object");
905 
906   case ELF::SHT_REL:
907   case ELF::SHT_RELA:
908   case ELF::SHT_CREL: {
909     sh_link = SymbolTableIndex;
910     assert(sh_link && ".symtab not found");
911     const MCSection *InfoSection = Section.getLinkedToSection();
912     sh_info = InfoSection->getOrdinal();
913     break;
914   }
915 
916   case ELF::SHT_SYMTAB:
917     sh_link = StringTableIndex;
918     sh_info = LastLocalSymbolIndex;
919     break;
920 
921   case ELF::SHT_SYMTAB_SHNDX:
922   case ELF::SHT_LLVM_CALL_GRAPH_PROFILE:
923   case ELF::SHT_LLVM_ADDRSIG:
924     sh_link = SymbolTableIndex;
925     break;
926 
927   case ELF::SHT_GROUP:
928     sh_link = SymbolTableIndex;
929     sh_info = GroupSymbolIndex;
930     break;
931   }
932 
933   if (Section.getFlags() & ELF::SHF_LINK_ORDER) {
934     // If the value in the associated metadata is not a definition, Sym will be
935     // undefined. Represent this with sh_link=0.
936     const MCSymbol *Sym = Section.getLinkedToSymbol();
937     if (Sym && Sym->isInSection())
938       sh_link = Sym->getSection().getOrdinal();
939   }
940 
941   writeSectionHeaderEntry(StrTabBuilder.getOffset(Section.getName()),
942                           Section.getType(), Section.getFlags(), 0, Offset,
943                           Size, sh_link, sh_info, Section.getAlign(),
944                           Section.getEntrySize());
945 }
946 
947 void ELFWriter::writeSectionHeaders(const MCAssembler &Asm) {
948   const unsigned NumSections = SectionTable.size();
949 
950   // Null section first.
951   uint64_t FirstSectionSize =
952       (NumSections + 1) >= ELF::SHN_LORESERVE ? NumSections + 1 : 0;
953   writeSectionHeaderEntry(0, 0, 0, 0, 0, FirstSectionSize, 0, 0, std::nullopt,
954                           0);
955 
956   for (const MCSectionELF *Section : SectionTable) {
957     uint32_t GroupSymbolIndex;
958     unsigned Type = Section->getType();
959     if (Type != ELF::SHT_GROUP)
960       GroupSymbolIndex = 0;
961     else
962       GroupSymbolIndex = Section->getGroup()->getIndex();
963 
964     std::pair<uint64_t, uint64_t> Offsets = Section->getOffsets();
965     uint64_t Size;
966     if (Type == ELF::SHT_NOBITS)
967       Size = Asm.getSectionAddressSize(*Section);
968     else
969       Size = Offsets.second - Offsets.first;
970 
971     auto SectionHasFlag = [&](uint64_t Flag) -> bool {
972       return Section->getFlags() & Flag;
973     };
974 
975     if (Section->getName().starts_with(".debug")) {
976       stats::DebugBytes += Size;
977     } else if (Section->getName().starts_with(".eh_frame")) {
978       stats::UnwindBytes += Size;
979     } else if (SectionHasFlag(ELF::SHF_ALLOC)) {
980       if (SectionHasFlag(ELF::SHF_EXECINSTR)) {
981         stats::AllocTextBytes += Size;
982       } else if (SectionHasFlag(ELF::SHF_WRITE)) {
983         stats::AllocRWBytes += Size;
984       } else {
985         stats::AllocROBytes += Size;
986       }
987     } else {
988       switch (Section->getType()) {
989       case ELF::SHT_STRTAB:
990         stats::StrtabBytes += Size;
991         break;
992       case ELF::SHT_SYMTAB:
993         stats::SymtabBytes += Size;
994         break;
995       case ELF::SHT_DYNSYM:
996         stats::DynsymBytes += Size;
997         break;
998       case ELF::SHT_REL:
999       case ELF::SHT_RELA:
1000       case ELF::SHT_CREL:
1001         stats::RelocationBytes += Size;
1002         break;
1003       default:
1004         stats::OtherBytes += Size;
1005         break;
1006       }
1007     }
1008 
1009     writeSectionHeader(GroupSymbolIndex, Offsets.first, Size, *Section);
1010   }
1011 }
1012 
1013 uint64_t ELFWriter::writeObject(MCAssembler &Asm) {
1014   uint64_t StartOffset = W.OS.tell();
1015 
1016   MCContext &Ctx = Asm.getContext();
1017   MCSectionELF *StrtabSection =
1018       Ctx.getELFSection(".strtab", ELF::SHT_STRTAB, 0);
1019   StringTableIndex = addToSectionTable(StrtabSection);
1020 
1021   RevGroupMapTy RevGroupMap;
1022 
1023   // Write out the ELF header ...
1024   writeHeader(Asm);
1025 
1026   // ... then the sections ...
1027   SmallVector<std::pair<MCSectionELF *, SmallVector<unsigned>>, 0> Groups;
1028   // Map from group section index to group
1029   SmallVector<unsigned, 0> GroupMap;
1030   SmallVector<MCSectionELF *> Relocations;
1031   for (MCSection &Sec : Asm) {
1032     MCSectionELF &Section = static_cast<MCSectionELF &>(Sec);
1033     if (Mode == NonDwoOnly && isDwoSection(Section))
1034       continue;
1035     if (Mode == DwoOnly && !isDwoSection(Section))
1036       continue;
1037 
1038     // Remember the offset into the file for this section.
1039     const uint64_t SecStart = align(Section.getAlign());
1040 
1041     const MCSymbolELF *SignatureSymbol = Section.getGroup();
1042     writeSectionData(Asm, Section);
1043 
1044     uint64_t SecEnd = W.OS.tell();
1045     Section.setOffsets(SecStart, SecEnd);
1046 
1047     MCSectionELF *RelSection = createRelocationSection(Ctx, Section);
1048 
1049     unsigned *GroupIdxEntry = nullptr;
1050     if (SignatureSymbol) {
1051       GroupIdxEntry = &RevGroupMap[SignatureSymbol];
1052       if (!*GroupIdxEntry) {
1053         MCSectionELF *Group =
1054             Ctx.createELFGroupSection(SignatureSymbol, Section.isComdat());
1055         *GroupIdxEntry = addToSectionTable(Group);
1056         Group->setAlignment(Align(4));
1057 
1058         GroupMap.resize(*GroupIdxEntry + 1);
1059         GroupMap[*GroupIdxEntry] = Groups.size();
1060         Groups.emplace_back(Group, SmallVector<unsigned>{});
1061       }
1062     }
1063 
1064     Section.setOrdinal(addToSectionTable(&Section));
1065     if (RelSection) {
1066       RelSection->setOrdinal(addToSectionTable(RelSection));
1067       Relocations.push_back(RelSection);
1068     }
1069 
1070     if (GroupIdxEntry) {
1071       auto &Members = Groups[GroupMap[*GroupIdxEntry]];
1072       Members.second.push_back(Section.getOrdinal());
1073       if (RelSection)
1074         Members.second.push_back(RelSection->getOrdinal());
1075     }
1076   }
1077 
1078   for (auto &[Group, Members] : Groups) {
1079     // Remember the offset into the file for this section.
1080     const uint64_t SecStart = align(Group->getAlign());
1081 
1082     write(uint32_t(Group->isComdat() ? unsigned(ELF::GRP_COMDAT) : 0));
1083     W.write<unsigned>(Members);
1084 
1085     uint64_t SecEnd = W.OS.tell();
1086     Group->setOffsets(SecStart, SecEnd);
1087   }
1088 
1089   if (Mode == DwoOnly) {
1090     // dwo files don't have symbol tables or relocations, but they do have
1091     // string tables.
1092     StrTabBuilder.finalize();
1093   } else {
1094     MCSectionELF *AddrsigSection;
1095     if (OWriter.getEmitAddrsigSection()) {
1096       AddrsigSection = Ctx.getELFSection(".llvm_addrsig", ELF::SHT_LLVM_ADDRSIG,
1097                                          ELF::SHF_EXCLUDE);
1098       addToSectionTable(AddrsigSection);
1099     }
1100 
1101     // Compute symbol table information.
1102     computeSymbolTable(Asm, RevGroupMap);
1103 
1104     for (MCSectionELF *RelSection : Relocations) {
1105       // Remember the offset into the file for this section.
1106       const uint64_t SecStart = align(RelSection->getAlign());
1107 
1108       writeRelocations(Asm,
1109                        cast<MCSectionELF>(*RelSection->getLinkedToSection()));
1110 
1111       uint64_t SecEnd = W.OS.tell();
1112       RelSection->setOffsets(SecStart, SecEnd);
1113     }
1114 
1115     if (OWriter.getEmitAddrsigSection()) {
1116       uint64_t SecStart = W.OS.tell();
1117       writeAddrsigSection();
1118       uint64_t SecEnd = W.OS.tell();
1119       AddrsigSection->setOffsets(SecStart, SecEnd);
1120     }
1121   }
1122 
1123   {
1124     uint64_t SecStart = W.OS.tell();
1125     StrTabBuilder.write(W.OS);
1126     StrtabSection->setOffsets(SecStart, W.OS.tell());
1127   }
1128 
1129   const uint64_t SectionHeaderOffset = align(is64Bit() ? Align(8) : Align(4));
1130 
1131   // ... then the section header table ...
1132   writeSectionHeaders(Asm);
1133 
1134   uint16_t NumSections = support::endian::byte_swap<uint16_t>(
1135       (SectionTable.size() + 1 >= ELF::SHN_LORESERVE) ? (uint16_t)ELF::SHN_UNDEF
1136                                                       : SectionTable.size() + 1,
1137       W.Endian);
1138   unsigned NumSectionsOffset;
1139 
1140   auto &Stream = static_cast<raw_pwrite_stream &>(W.OS);
1141   if (is64Bit()) {
1142     uint64_t Val =
1143         support::endian::byte_swap<uint64_t>(SectionHeaderOffset, W.Endian);
1144     Stream.pwrite(reinterpret_cast<char *>(&Val), sizeof(Val),
1145                   offsetof(ELF::Elf64_Ehdr, e_shoff));
1146     NumSectionsOffset = offsetof(ELF::Elf64_Ehdr, e_shnum);
1147   } else {
1148     uint32_t Val =
1149         support::endian::byte_swap<uint32_t>(SectionHeaderOffset, W.Endian);
1150     Stream.pwrite(reinterpret_cast<char *>(&Val), sizeof(Val),
1151                   offsetof(ELF::Elf32_Ehdr, e_shoff));
1152     NumSectionsOffset = offsetof(ELF::Elf32_Ehdr, e_shnum);
1153   }
1154   Stream.pwrite(reinterpret_cast<char *>(&NumSections), sizeof(NumSections),
1155                 NumSectionsOffset);
1156 
1157   return W.OS.tell() - StartOffset;
1158 }
1159 
1160 ELFObjectWriter::ELFObjectWriter(std::unique_ptr<MCELFObjectTargetWriter> MOTW,
1161                                  raw_pwrite_stream &OS, bool IsLittleEndian)
1162     : TargetObjectWriter(std::move(MOTW)), OS(OS),
1163       IsLittleEndian(IsLittleEndian) {}
1164 ELFObjectWriter::ELFObjectWriter(std::unique_ptr<MCELFObjectTargetWriter> MOTW,
1165                                  raw_pwrite_stream &OS,
1166                                  raw_pwrite_stream &DwoOS, bool IsLittleEndian)
1167     : TargetObjectWriter(std::move(MOTW)), OS(OS), DwoOS(&DwoOS),
1168       IsLittleEndian(IsLittleEndian) {}
1169 
1170 void ELFObjectWriter::reset() {
1171   ELFHeaderEFlags = 0;
1172   SeenGnuAbi = false;
1173   OverrideABIVersion.reset();
1174   Relocations.clear();
1175   Renames.clear();
1176   Symvers.clear();
1177   MCObjectWriter::reset();
1178 }
1179 
1180 bool ELFObjectWriter::hasRelocationAddend() const {
1181   return TargetObjectWriter->hasRelocationAddend();
1182 }
1183 
1184 void ELFObjectWriter::executePostLayoutBinding(MCAssembler &Asm) {
1185   // The presence of symbol versions causes undefined symbols and
1186   // versions declared with @@@ to be renamed.
1187   for (const Symver &S : Symvers) {
1188     StringRef AliasName = S.Name;
1189     const auto &Symbol = cast<MCSymbolELF>(*S.Sym);
1190     size_t Pos = AliasName.find('@');
1191     assert(Pos != StringRef::npos);
1192 
1193     StringRef Prefix = AliasName.substr(0, Pos);
1194     StringRef Rest = AliasName.substr(Pos);
1195     StringRef Tail = Rest;
1196     if (Rest.starts_with("@@@"))
1197       Tail = Rest.substr(Symbol.isUndefined() ? 2 : 1);
1198 
1199     auto *Alias =
1200         cast<MCSymbolELF>(Asm.getContext().getOrCreateSymbol(Prefix + Tail));
1201     Asm.registerSymbol(*Alias);
1202     const MCExpr *Value = MCSymbolRefExpr::create(&Symbol, Asm.getContext());
1203     Alias->setVariableValue(Value);
1204 
1205     // Aliases defined with .symvar copy the binding from the symbol they alias.
1206     // This is the first place we are able to copy this information.
1207     Alias->setBinding(Symbol.getBinding());
1208     Alias->setVisibility(Symbol.getVisibility());
1209     Alias->setOther(Symbol.getOther());
1210 
1211     if (!Symbol.isUndefined() && S.KeepOriginalSym)
1212       continue;
1213 
1214     if (Symbol.isUndefined() && Rest.starts_with("@@") &&
1215         !Rest.starts_with("@@@")) {
1216       Asm.getContext().reportError(S.Loc, "default version symbol " +
1217                                               AliasName + " must be defined");
1218       continue;
1219     }
1220 
1221     if (Renames.count(&Symbol) && Renames[&Symbol] != Alias) {
1222       Asm.getContext().reportError(S.Loc, Twine("multiple versions for ") +
1223                                               Symbol.getName());
1224       continue;
1225     }
1226 
1227     Renames.insert(std::make_pair(&Symbol, Alias));
1228   }
1229 
1230   for (const MCSymbol *&Sym : AddrsigSyms) {
1231     if (const MCSymbol *R = Renames.lookup(cast<MCSymbolELF>(Sym)))
1232       Sym = R;
1233     if (Sym->isInSection() && Sym->getName().starts_with(".L"))
1234       Sym = Sym->getSection().getBeginSymbol();
1235     Sym->setUsedInReloc();
1236   }
1237 }
1238 
1239 // It is always valid to create a relocation with a symbol. It is preferable
1240 // to use a relocation with a section if that is possible. Using the section
1241 // allows us to omit some local symbols from the symbol table.
1242 bool ELFObjectWriter::shouldRelocateWithSymbol(const MCAssembler &Asm,
1243                                                const MCValue &Val,
1244                                                const MCSymbolELF *Sym,
1245                                                uint64_t C,
1246                                                unsigned Type) const {
1247   const MCSymbolRefExpr *RefA = Val.getSymA();
1248   // A PCRel relocation to an absolute value has no symbol (or section). We
1249   // represent that with a relocation to a null section.
1250   if (!RefA)
1251     return false;
1252 
1253   MCSymbolRefExpr::VariantKind Kind = RefA->getKind();
1254   switch (Kind) {
1255   default:
1256     break;
1257   // The .odp creation emits a relocation against the symbol ".TOC." which
1258   // create a R_PPC64_TOC relocation. However the relocation symbol name
1259   // in final object creation should be NULL, since the symbol does not
1260   // really exist, it is just the reference to TOC base for the current
1261   // object file. Since the symbol is undefined, returning false results
1262   // in a relocation with a null section which is the desired result.
1263   case MCSymbolRefExpr::VK_PPC_TOCBASE:
1264     return false;
1265 
1266   // These VariantKind cause the relocation to refer to something other than
1267   // the symbol itself, like a linker generated table. Since the address of
1268   // symbol is not relevant, we cannot replace the symbol with the
1269   // section and patch the difference in the addend.
1270   case MCSymbolRefExpr::VK_GOT:
1271   case MCSymbolRefExpr::VK_PLT:
1272   case MCSymbolRefExpr::VK_GOTPCREL:
1273   case MCSymbolRefExpr::VK_GOTPCREL_NORELAX:
1274   case MCSymbolRefExpr::VK_PPC_GOT_LO:
1275   case MCSymbolRefExpr::VK_PPC_GOT_HI:
1276   case MCSymbolRefExpr::VK_PPC_GOT_HA:
1277     return true;
1278   }
1279 
1280   // An undefined symbol is not in any section, so the relocation has to point
1281   // to the symbol itself.
1282   assert(Sym && "Expected a symbol");
1283   if (Sym->isUndefined())
1284     return true;
1285 
1286   // For memory-tagged symbols, ensure that the relocation uses the symbol. For
1287   // tagged symbols, we emit an empty relocation (R_AARCH64_NONE) in a special
1288   // section (SHT_AARCH64_MEMTAG_GLOBALS_STATIC) to indicate to the linker that
1289   // this global needs to be tagged. In addition, the linker needs to know
1290   // whether to emit a special addend when relocating `end` symbols, and this
1291   // can only be determined by the attributes of the symbol itself.
1292   if (Sym->isMemtag())
1293     return true;
1294 
1295   unsigned Binding = Sym->getBinding();
1296   switch(Binding) {
1297   default:
1298     llvm_unreachable("Invalid Binding");
1299   case ELF::STB_LOCAL:
1300     break;
1301   case ELF::STB_WEAK:
1302     // If the symbol is weak, it might be overridden by a symbol in another
1303     // file. The relocation has to point to the symbol so that the linker
1304     // can update it.
1305     return true;
1306   case ELF::STB_GLOBAL:
1307   case ELF::STB_GNU_UNIQUE:
1308     // Global ELF symbols can be preempted by the dynamic linker. The relocation
1309     // has to point to the symbol for a reason analogous to the STB_WEAK case.
1310     return true;
1311   }
1312 
1313   // Keep symbol type for a local ifunc because it may result in an IRELATIVE
1314   // reloc that the dynamic loader will use to resolve the address at startup
1315   // time.
1316   if (Sym->getType() == ELF::STT_GNU_IFUNC)
1317     return true;
1318 
1319   // If a relocation points to a mergeable section, we have to be careful.
1320   // If the offset is zero, a relocation with the section will encode the
1321   // same information. With a non-zero offset, the situation is different.
1322   // For example, a relocation can point 42 bytes past the end of a string.
1323   // If we change such a relocation to use the section, the linker would think
1324   // that it pointed to another string and subtracting 42 at runtime will
1325   // produce the wrong value.
1326   if (Sym->isInSection()) {
1327     auto &Sec = cast<MCSectionELF>(Sym->getSection());
1328     unsigned Flags = Sec.getFlags();
1329     if (Flags & ELF::SHF_MERGE) {
1330       if (C != 0)
1331         return true;
1332 
1333       // gold<2.34 incorrectly ignored the addend for R_386_GOTOFF (9)
1334       // (http://sourceware.org/PR16794).
1335       if (TargetObjectWriter->getEMachine() == ELF::EM_386 &&
1336           Type == ELF::R_386_GOTOFF)
1337         return true;
1338 
1339       // ld.lld handles R_MIPS_HI16/R_MIPS_LO16 separately, not as a whole, so
1340       // it doesn't know that an R_MIPS_HI16 with implicit addend 1 and an
1341       // R_MIPS_LO16 with implicit addend -32768 represents 32768, which is in
1342       // range of a MergeInputSection. We could introduce a new RelExpr member
1343       // (like R_RISCV_PC_INDIRECT for R_RISCV_PCREL_HI20 / R_RISCV_PCREL_LO12)
1344       // but the complexity is unnecessary given that GNU as keeps the original
1345       // symbol for this case as well.
1346       if (TargetObjectWriter->getEMachine() == ELF::EM_MIPS &&
1347           !hasRelocationAddend())
1348         return true;
1349     }
1350 
1351     // Most TLS relocations use a got, so they need the symbol. Even those that
1352     // are just an offset (@tpoff), require a symbol in gold versions before
1353     // 5efeedf61e4fe720fd3e9a08e6c91c10abb66d42 (2014-09-26) which fixed
1354     // http://sourceware.org/PR16773.
1355     if (Flags & ELF::SHF_TLS)
1356       return true;
1357   }
1358 
1359   // If the symbol is a thumb function the final relocation must set the lowest
1360   // bit. With a symbol that is done by just having the symbol have that bit
1361   // set, so we would lose the bit if we relocated with the section.
1362   // FIXME: We could use the section but add the bit to the relocation value.
1363   if (Asm.isThumbFunc(Sym))
1364     return true;
1365 
1366   if (TargetObjectWriter->needsRelocateWithSymbol(Val, *Sym, Type))
1367     return true;
1368   return false;
1369 }
1370 
1371 bool ELFObjectWriter::checkRelocation(MCContext &Ctx, SMLoc Loc,
1372                                       const MCSectionELF *From,
1373                                       const MCSectionELF *To) {
1374   if (DwoOS) {
1375     if (isDwoSection(*From)) {
1376       Ctx.reportError(Loc, "A dwo section may not contain relocations");
1377       return false;
1378     }
1379     if (To && isDwoSection(*To)) {
1380       Ctx.reportError(Loc, "A relocation may not refer to a dwo section");
1381       return false;
1382     }
1383   }
1384   return true;
1385 }
1386 
1387 void ELFObjectWriter::recordRelocation(MCAssembler &Asm,
1388                                        const MCFragment *Fragment,
1389                                        const MCFixup &Fixup, MCValue Target,
1390                                        uint64_t &FixedValue) {
1391   MCAsmBackend &Backend = Asm.getBackend();
1392   bool IsPCRel = Backend.getFixupKindInfo(Fixup.getKind()).Flags &
1393                  MCFixupKindInfo::FKF_IsPCRel;
1394   const MCSectionELF &FixupSection = cast<MCSectionELF>(*Fragment->getParent());
1395   uint64_t C = Target.getConstant();
1396   uint64_t FixupOffset = Asm.getFragmentOffset(*Fragment) + Fixup.getOffset();
1397   MCContext &Ctx = Asm.getContext();
1398   const MCTargetOptions *TO = Ctx.getTargetOptions();
1399 
1400   if (const MCSymbolRefExpr *RefB = Target.getSymB()) {
1401     const auto &SymB = cast<MCSymbolELF>(RefB->getSymbol());
1402     if (SymB.isUndefined()) {
1403       Ctx.reportError(Fixup.getLoc(),
1404                       Twine("symbol '") + SymB.getName() +
1405                           "' can not be undefined in a subtraction expression");
1406       return;
1407     }
1408 
1409     assert(!SymB.isAbsolute() && "Should have been folded");
1410     const MCSection &SecB = SymB.getSection();
1411     if (&SecB != &FixupSection) {
1412       Ctx.reportError(Fixup.getLoc(),
1413                       "Cannot represent a difference across sections");
1414       return;
1415     }
1416 
1417     assert(!IsPCRel && "should have been folded");
1418     IsPCRel = true;
1419     C += FixupOffset - Asm.getSymbolOffset(SymB);
1420   }
1421 
1422   // We either rejected the fixup or folded B into C at this point.
1423   const MCSymbolRefExpr *RefA = Target.getSymA();
1424   const auto *SymA = RefA ? cast<MCSymbolELF>(&RefA->getSymbol()) : nullptr;
1425 
1426   bool ViaWeakRef = false;
1427   if (SymA && SymA->isVariable()) {
1428     const MCExpr *Expr = SymA->getVariableValue();
1429     if (const auto *Inner = dyn_cast<MCSymbolRefExpr>(Expr)) {
1430       if (Inner->getKind() == MCSymbolRefExpr::VK_WEAKREF) {
1431         SymA = cast<MCSymbolELF>(&Inner->getSymbol());
1432         ViaWeakRef = true;
1433       }
1434     }
1435   }
1436 
1437   const MCSectionELF *SecA = (SymA && SymA->isInSection())
1438                                  ? cast<MCSectionELF>(&SymA->getSection())
1439                                  : nullptr;
1440   if (!checkRelocation(Ctx, Fixup.getLoc(), &FixupSection, SecA))
1441     return;
1442 
1443   unsigned Type = TargetObjectWriter->getRelocType(Ctx, Target, Fixup, IsPCRel);
1444   const auto *Parent = cast<MCSectionELF>(Fragment->getParent());
1445   // Emiting relocation with sybmol for CG Profile to  help with --cg-profile.
1446   bool RelocateWithSymbol =
1447       shouldRelocateWithSymbol(Asm, Target, SymA, C, Type) ||
1448       (Parent->getType() == ELF::SHT_LLVM_CALL_GRAPH_PROFILE);
1449   uint64_t Addend = !RelocateWithSymbol && SymA && !SymA->isUndefined()
1450                         ? C + Asm.getSymbolOffset(*SymA)
1451                         : C;
1452   FixedValue = usesRela(TO, FixupSection) ? 0 : Addend;
1453 
1454   if (!RelocateWithSymbol) {
1455     const auto *SectionSymbol =
1456         SecA ? cast<MCSymbolELF>(SecA->getBeginSymbol()) : nullptr;
1457     if (SectionSymbol)
1458       SectionSymbol->setUsedInReloc();
1459     ELFRelocationEntry Rec(FixupOffset, SectionSymbol, Type, Addend);
1460     Relocations[&FixupSection].push_back(Rec);
1461     return;
1462   }
1463 
1464   const MCSymbolELF *RenamedSymA = SymA;
1465   if (SymA) {
1466     if (const MCSymbolELF *R = Renames.lookup(SymA))
1467       RenamedSymA = R;
1468 
1469     if (ViaWeakRef)
1470       RenamedSymA->setIsWeakrefUsedInReloc();
1471     else
1472       RenamedSymA->setUsedInReloc();
1473   }
1474   ELFRelocationEntry Rec(FixupOffset, RenamedSymA, Type, Addend);
1475   Relocations[&FixupSection].push_back(Rec);
1476 }
1477 
1478 bool ELFObjectWriter::usesRela(const MCTargetOptions *TO,
1479                                const MCSectionELF &Sec) const {
1480   return (hasRelocationAddend() &&
1481           Sec.getType() != ELF::SHT_LLVM_CALL_GRAPH_PROFILE) ||
1482          (TO && TO->Crel);
1483 }
1484 
1485 bool ELFObjectWriter::isSymbolRefDifferenceFullyResolvedImpl(
1486     const MCAssembler &Asm, const MCSymbol &SA, const MCFragment &FB,
1487     bool InSet, bool IsPCRel) const {
1488   const auto &SymA = cast<MCSymbolELF>(SA);
1489   if (IsPCRel) {
1490     assert(!InSet);
1491     if (SymA.getBinding() != ELF::STB_LOCAL ||
1492         SymA.getType() == ELF::STT_GNU_IFUNC)
1493       return false;
1494   }
1495   return &SymA.getSection() == FB.getParent();
1496 }
1497 
1498 uint64_t ELFObjectWriter::writeObject(MCAssembler &Asm) {
1499   uint64_t Size =
1500       ELFWriter(*this, OS, IsLittleEndian,
1501                 DwoOS ? ELFWriter::NonDwoOnly : ELFWriter::AllSections)
1502           .writeObject(Asm);
1503   if (DwoOS)
1504     Size += ELFWriter(*this, *DwoOS, IsLittleEndian, ELFWriter::DwoOnly)
1505                 .writeObject(Asm);
1506   return Size;
1507 }
1508