LLVM API Documentation

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
ELFObjectWriter.cpp
Go to the documentation of this file.
1 //===- lib/MC/ELFObjectWriter.cpp - ELF File Writer -----------------------===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This file implements ELF object file writer information.
11 //
12 //===----------------------------------------------------------------------===//
13 
15 #include "llvm/ADT/OwningPtr.h"
16 #include "llvm/ADT/STLExtras.h"
17 #include "llvm/ADT/SmallPtrSet.h"
18 #include "llvm/ADT/SmallString.h"
19 #include "llvm/ADT/StringMap.h"
20 #include "llvm/MC/MCAsmBackend.h"
21 #include "llvm/MC/MCAsmLayout.h"
22 #include "llvm/MC/MCAssembler.h"
23 #include "llvm/MC/MCContext.h"
24 #include "llvm/MC/MCELF.h"
26 #include "llvm/MC/MCExpr.h"
28 #include "llvm/MC/MCObjectWriter.h"
29 #include "llvm/MC/MCSectionELF.h"
30 #include "llvm/MC/MCValue.h"
31 #include "llvm/Support/Debug.h"
32 #include "llvm/Support/ELF.h"
34 #include <vector>
35 using namespace llvm;
36 
37 #undef DEBUG_TYPE
38 #define DEBUG_TYPE "reloc-info"
39 
40 namespace {
41 class ELFObjectWriter : public MCObjectWriter {
42  protected:
43 
44  static bool isFixupKindPCRel(const MCAssembler &Asm, unsigned Kind);
45  static bool RelocNeedsGOT(MCSymbolRefExpr::VariantKind Variant);
46  static uint64_t SymbolValue(MCSymbolData &Data, const MCAsmLayout &Layout);
47  static bool isInSymtab(const MCAssembler &Asm, const MCSymbolData &Data,
48  bool Used, bool Renamed);
49  static bool isLocal(const MCSymbolData &Data, bool isSignature,
50  bool isUsedInReloc);
51  static bool IsELFMetaDataSection(const MCSectionData &SD);
52  static uint64_t DataSectionSize(const MCSectionData &SD);
53  static uint64_t GetSectionFileSize(const MCAsmLayout &Layout,
54  const MCSectionData &SD);
55  static uint64_t GetSectionAddressSize(const MCAsmLayout &Layout,
56  const MCSectionData &SD);
57 
58  void WriteDataSectionData(MCAssembler &Asm,
59  const MCAsmLayout &Layout,
60  const MCSectionELF &Section);
61 
62  /*static bool isFixupKindX86RIPRel(unsigned Kind) {
63  return Kind == X86::reloc_riprel_4byte ||
64  Kind == X86::reloc_riprel_4byte_movq_load;
65  }*/
66 
67  /// ELFSymbolData - Helper struct for containing some precomputed
68  /// information on symbols.
69  struct ELFSymbolData {
70  MCSymbolData *SymbolData;
71  uint64_t StringIndex;
72  uint32_t SectionIndex;
73 
74  // Support lexicographic sorting.
75  bool operator<(const ELFSymbolData &RHS) const {
76  return SymbolData->getSymbol().getName() <
77  RHS.SymbolData->getSymbol().getName();
78  }
79  };
80 
81  /// The target specific ELF writer instance.
83 
85  SmallPtrSet<const MCSymbol *, 16> WeakrefUsedInReloc;
87 
89  std::vector<ELFRelocationEntry> > Relocations;
90  DenseMap<const MCSection*, uint64_t> SectionStringTableIndex;
91 
92  /// @}
93  /// @name Symbol Table Data
94  /// @{
95 
96  SmallString<256> StringTable;
97  std::vector<uint64_t> FileSymbolData;
98  std::vector<ELFSymbolData> LocalSymbolData;
99  std::vector<ELFSymbolData> ExternalSymbolData;
100  std::vector<ELFSymbolData> UndefinedSymbolData;
101 
102  /// @}
103 
104  bool NeedsGOT;
105 
106  bool NeedsSymtabShndx;
107 
108  // This holds the symbol table index of the last local symbol.
109  unsigned LastLocalSymbolIndex;
110  // This holds the .strtab section index.
111  unsigned StringTableIndex;
112  // This holds the .symtab section index.
113  unsigned SymbolTableIndex;
114 
115  unsigned ShstrtabIndex;
116 
117 
118  const MCSymbol *SymbolToReloc(const MCAssembler &Asm,
119  const MCValue &Target,
120  const MCFragment &F,
121  const MCFixup &Fixup,
122  bool IsPCRel) const;
123 
124  // TargetObjectWriter wrappers.
125  const MCSymbol *ExplicitRelSym(const MCAssembler &Asm,
126  const MCValue &Target,
127  const MCFragment &F,
128  const MCFixup &Fixup,
129  bool IsPCRel) const {
130  return TargetObjectWriter->ExplicitRelSym(Asm, Target, F, Fixup, IsPCRel);
131  }
132  const MCSymbol *undefinedExplicitRelSym(const MCValue &Target,
133  const MCFixup &Fixup,
134  bool IsPCRel) const {
135  return TargetObjectWriter->undefinedExplicitRelSym(Target, Fixup,
136  IsPCRel);
137  }
138 
139  bool is64Bit() const { return TargetObjectWriter->is64Bit(); }
140  bool hasRelocationAddend() const {
141  return TargetObjectWriter->hasRelocationAddend();
142  }
143  unsigned GetRelocType(const MCValue &Target, const MCFixup &Fixup,
144  bool IsPCRel, bool IsRelocWithSymbol,
145  int64_t Addend) const {
146  return TargetObjectWriter->GetRelocType(Target, Fixup, IsPCRel,
147  IsRelocWithSymbol, Addend);
148  }
149 
150  public:
151  ELFObjectWriter(MCELFObjectTargetWriter *MOTW,
152  raw_ostream &_OS, bool IsLittleEndian)
153  : MCObjectWriter(_OS, IsLittleEndian),
154  TargetObjectWriter(MOTW),
155  NeedsGOT(false), NeedsSymtabShndx(false) {
156  }
157 
158  virtual ~ELFObjectWriter();
159 
160  void WriteWord(uint64_t W) {
161  if (is64Bit())
162  Write64(W);
163  else
164  Write32(W);
165  }
166 
167  void StringLE16(char *buf, uint16_t Value) {
168  buf[0] = char(Value >> 0);
169  buf[1] = char(Value >> 8);
170  }
171 
172  void StringLE32(char *buf, uint32_t Value) {
173  StringLE16(buf, uint16_t(Value >> 0));
174  StringLE16(buf + 2, uint16_t(Value >> 16));
175  }
176 
177  void StringLE64(char *buf, uint64_t Value) {
178  StringLE32(buf, uint32_t(Value >> 0));
179  StringLE32(buf + 4, uint32_t(Value >> 32));
180  }
181 
182  void StringBE16(char *buf ,uint16_t Value) {
183  buf[0] = char(Value >> 8);
184  buf[1] = char(Value >> 0);
185  }
186 
187  void StringBE32(char *buf, uint32_t Value) {
188  StringBE16(buf, uint16_t(Value >> 16));
189  StringBE16(buf + 2, uint16_t(Value >> 0));
190  }
191 
192  void StringBE64(char *buf, uint64_t Value) {
193  StringBE32(buf, uint32_t(Value >> 32));
194  StringBE32(buf + 4, uint32_t(Value >> 0));
195  }
196 
197  void String8(MCDataFragment &F, uint8_t Value) {
198  char buf[1];
199  buf[0] = Value;
200  F.getContents().append(&buf[0], &buf[1]);
201  }
202 
203  void String16(MCDataFragment &F, uint16_t Value) {
204  char buf[2];
205  if (isLittleEndian())
206  StringLE16(buf, Value);
207  else
208  StringBE16(buf, Value);
209  F.getContents().append(&buf[0], &buf[2]);
210  }
211 
212  void String32(MCDataFragment &F, uint32_t Value) {
213  char buf[4];
214  if (isLittleEndian())
215  StringLE32(buf, Value);
216  else
217  StringBE32(buf, Value);
218  F.getContents().append(&buf[0], &buf[4]);
219  }
220 
221  void String64(MCDataFragment &F, uint64_t Value) {
222  char buf[8];
223  if (isLittleEndian())
224  StringLE64(buf, Value);
225  else
226  StringBE64(buf, Value);
227  F.getContents().append(&buf[0], &buf[8]);
228  }
229 
230  void WriteHeader(const MCAssembler &Asm,
231  uint64_t SectionDataSize,
232  unsigned NumberOfSections);
233 
234  void WriteSymbolEntry(MCDataFragment *SymtabF,
235  MCDataFragment *ShndxF,
236  uint64_t name, uint8_t info,
237  uint64_t value, uint64_t size,
238  uint8_t other, uint32_t shndx,
239  bool Reserved);
240 
241  void WriteSymbol(MCDataFragment *SymtabF, MCDataFragment *ShndxF,
242  ELFSymbolData &MSD,
243  const MCAsmLayout &Layout);
244 
245  typedef DenseMap<const MCSectionELF*, uint32_t> SectionIndexMapTy;
246  void WriteSymbolTable(MCDataFragment *SymtabF,
247  MCDataFragment *ShndxF,
248  const MCAssembler &Asm,
249  const MCAsmLayout &Layout,
250  const SectionIndexMapTy &SectionIndexMap);
251 
252  virtual void RecordRelocation(const MCAssembler &Asm,
253  const MCAsmLayout &Layout,
254  const MCFragment *Fragment,
255  const MCFixup &Fixup,
256  MCValue Target, uint64_t &FixedValue);
257 
258  uint64_t getSymbolIndexInSymbolTable(const MCAssembler &Asm,
259  const MCSymbol *S);
260 
261  // Map from a group section to the signature symbol
263  // Map from a signature symbol to the group section
265  // Map from a section to the section with the relocations
267  // Map from a section to its offset
268  typedef DenseMap<const MCSectionELF*, uint64_t> SectionOffsetMapTy;
269 
270  /// ComputeSymbolTable - Compute the symbol table data
271  ///
272  /// \param Asm - The assembler.
273  /// \param SectionIndexMap - Maps a section to its index.
274  /// \param RevGroupMap - Maps a signature symbol to the group section.
275  /// \param NumRegularSections - Number of non-relocation sections.
276  void ComputeSymbolTable(MCAssembler &Asm,
277  const SectionIndexMapTy &SectionIndexMap,
278  RevGroupMapTy RevGroupMap,
279  unsigned NumRegularSections);
280 
281  void ComputeIndexMap(MCAssembler &Asm,
282  SectionIndexMapTy &SectionIndexMap,
283  const RelMapTy &RelMap);
284 
285  void CreateRelocationSections(MCAssembler &Asm, MCAsmLayout &Layout,
286  RelMapTy &RelMap);
287 
288  void WriteRelocations(MCAssembler &Asm, MCAsmLayout &Layout,
289  const RelMapTy &RelMap);
290 
291  void CreateMetadataSections(MCAssembler &Asm, MCAsmLayout &Layout,
292  SectionIndexMapTy &SectionIndexMap,
293  const RelMapTy &RelMap);
294 
295  // Create the sections that show up in the symbol table. Currently
296  // those are the .note.GNU-stack section and the group sections.
297  void CreateIndexedSections(MCAssembler &Asm, MCAsmLayout &Layout,
298  GroupMapTy &GroupMap,
299  RevGroupMapTy &RevGroupMap,
300  SectionIndexMapTy &SectionIndexMap,
301  const RelMapTy &RelMap);
302 
303  virtual void ExecutePostLayoutBinding(MCAssembler &Asm,
304  const MCAsmLayout &Layout);
305 
306  void WriteSectionHeader(MCAssembler &Asm, const GroupMapTy &GroupMap,
307  const MCAsmLayout &Layout,
308  const SectionIndexMapTy &SectionIndexMap,
309  const SectionOffsetMapTy &SectionOffsetMap);
310 
311  void ComputeSectionOrder(MCAssembler &Asm,
312  std::vector<const MCSectionELF*> &Sections);
313 
314  void WriteSecHdrEntry(uint32_t Name, uint32_t Type, uint64_t Flags,
315  uint64_t Address, uint64_t Offset,
316  uint64_t Size, uint32_t Link, uint32_t Info,
317  uint64_t Alignment, uint64_t EntrySize);
318 
319  void WriteRelocationsFragment(const MCAssembler &Asm,
320  MCDataFragment *F,
321  const MCSectionData *SD);
322 
323  virtual bool
324  IsSymbolRefDifferenceFullyResolvedImpl(const MCAssembler &Asm,
325  const MCSymbolData &DataA,
326  const MCFragment &FB,
327  bool InSet,
328  bool IsPCRel) const;
329 
330  virtual void WriteObject(MCAssembler &Asm, const MCAsmLayout &Layout);
331  void WriteSection(MCAssembler &Asm,
332  const SectionIndexMapTy &SectionIndexMap,
333  uint32_t GroupSymbolIndex,
334  uint64_t Offset, uint64_t Size, uint64_t Alignment,
335  const MCSectionELF &Section);
336  };
337 }
338 
339 bool ELFObjectWriter::isFixupKindPCRel(const MCAssembler &Asm, unsigned Kind) {
340  const MCFixupKindInfo &FKI =
342 
343  return FKI.Flags & MCFixupKindInfo::FKF_IsPCRel;
344 }
345 
346 bool ELFObjectWriter::RelocNeedsGOT(MCSymbolRefExpr::VariantKind Variant) {
347  switch (Variant) {
348  default:
349  return false;
363  return true;
364  }
365 }
366 
367 ELFObjectWriter::~ELFObjectWriter()
368 {}
369 
370 // Emit the ELF header.
371 void ELFObjectWriter::WriteHeader(const MCAssembler &Asm,
372  uint64_t SectionDataSize,
373  unsigned NumberOfSections) {
374  // ELF Header
375  // ----------
376  //
377  // Note
378  // ----
379  // emitWord method behaves differently for ELF32 and ELF64, writing
380  // 4 bytes in the former and 8 in the latter.
381 
382  Write8(0x7f); // e_ident[EI_MAG0]
383  Write8('E'); // e_ident[EI_MAG1]
384  Write8('L'); // e_ident[EI_MAG2]
385  Write8('F'); // e_ident[EI_MAG3]
386 
387  Write8(is64Bit() ? ELF::ELFCLASS64 : ELF::ELFCLASS32); // e_ident[EI_CLASS]
388 
389  // e_ident[EI_DATA]
390  Write8(isLittleEndian() ? ELF::ELFDATA2LSB : ELF::ELFDATA2MSB);
391 
392  Write8(ELF::EV_CURRENT); // e_ident[EI_VERSION]
393  // e_ident[EI_OSABI]
394  Write8(TargetObjectWriter->getOSABI());
395  Write8(0); // e_ident[EI_ABIVERSION]
396 
397  WriteZeros(ELF::EI_NIDENT - ELF::EI_PAD);
398 
399  Write16(ELF::ET_REL); // e_type
400 
401  Write16(TargetObjectWriter->getEMachine()); // e_machine = target
402 
403  Write32(ELF::EV_CURRENT); // e_version
404  WriteWord(0); // e_entry, no entry point in .o file
405  WriteWord(0); // e_phoff, no program header for .o
406  WriteWord(SectionDataSize + (is64Bit() ? sizeof(ELF::Elf64_Ehdr) :
407  sizeof(ELF::Elf32_Ehdr))); // e_shoff = sec hdr table off in bytes
408 
409  // e_flags = whatever the target wants
410  Write32(Asm.getELFHeaderEFlags());
411 
412  // e_ehsize = ELF header size
413  Write16(is64Bit() ? sizeof(ELF::Elf64_Ehdr) : sizeof(ELF::Elf32_Ehdr));
414 
415  Write16(0); // e_phentsize = prog header entry size
416  Write16(0); // e_phnum = # prog header entries = 0
417 
418  // e_shentsize = Section header entry size
419  Write16(is64Bit() ? sizeof(ELF::Elf64_Shdr) : sizeof(ELF::Elf32_Shdr));
420 
421  // e_shnum = # of section header ents
422  if (NumberOfSections >= ELF::SHN_LORESERVE)
423  Write16(ELF::SHN_UNDEF);
424  else
425  Write16(NumberOfSections);
426 
427  // e_shstrndx = Section # of '.shstrtab'
428  if (ShstrtabIndex >= ELF::SHN_LORESERVE)
429  Write16(ELF::SHN_XINDEX);
430  else
431  Write16(ShstrtabIndex);
432 }
433 
434 void ELFObjectWriter::WriteSymbolEntry(MCDataFragment *SymtabF,
435  MCDataFragment *ShndxF,
436  uint64_t name,
437  uint8_t info, uint64_t value,
438  uint64_t size, uint8_t other,
439  uint32_t shndx,
440  bool Reserved) {
441  if (ShndxF) {
442  if (shndx >= ELF::SHN_LORESERVE && !Reserved)
443  String32(*ShndxF, shndx);
444  else
445  String32(*ShndxF, 0);
446  }
447 
448  uint16_t Index = (shndx >= ELF::SHN_LORESERVE && !Reserved) ?
449  uint16_t(ELF::SHN_XINDEX) : shndx;
450 
451  if (is64Bit()) {
452  String32(*SymtabF, name); // st_name
453  String8(*SymtabF, info); // st_info
454  String8(*SymtabF, other); // st_other
455  String16(*SymtabF, Index); // st_shndx
456  String64(*SymtabF, value); // st_value
457  String64(*SymtabF, size); // st_size
458  } else {
459  String32(*SymtabF, name); // st_name
460  String32(*SymtabF, value); // st_value
461  String32(*SymtabF, size); // st_size
462  String8(*SymtabF, info); // st_info
463  String8(*SymtabF, other); // st_other
464  String16(*SymtabF, Index); // st_shndx
465  }
466 }
467 
468 uint64_t ELFObjectWriter::SymbolValue(MCSymbolData &Data,
469  const MCAsmLayout &Layout) {
470  if (Data.isCommon() && Data.isExternal())
471  return Data.getCommonAlignment();
472 
473  const MCSymbol &Symbol = Data.getSymbol();
474 
475  if (Symbol.isAbsolute() && Symbol.isVariable()) {
476  if (const MCExpr *Value = Symbol.getVariableValue()) {
477  int64_t IntValue;
478  if (Value->EvaluateAsAbsolute(IntValue, Layout))
479  return (uint64_t)IntValue;
480  }
481  }
482 
483  if (!Symbol.isInSection())
484  return 0;
485 
486 
487  if (Data.getFragment()) {
488  if (Data.getFlags() & ELF_Other_ThumbFunc)
489  return Layout.getSymbolOffset(&Data)+1;
490  else
491  return Layout.getSymbolOffset(&Data);
492  }
493 
494  return 0;
495 }
496 
497 void ELFObjectWriter::ExecutePostLayoutBinding(MCAssembler &Asm,
498  const MCAsmLayout &Layout) {
499  // The presence of symbol versions causes undefined symbols and
500  // versions declared with @@@ to be renamed.
501 
503  ie = Asm.symbol_end(); it != ie; ++it) {
504  const MCSymbol &Alias = it->getSymbol();
505  const MCSymbol &Symbol = Alias.AliasedSymbol();
506  MCSymbolData &SD = Asm.getSymbolData(Symbol);
507 
508  // Not an alias.
509  if (&Symbol == &Alias)
510  continue;
511 
512  StringRef AliasName = Alias.getName();
513  size_t Pos = AliasName.find('@');
514  if (Pos == StringRef::npos)
515  continue;
516 
517  // Aliases defined with .symvar copy the binding from the symbol they alias.
518  // This is the first place we are able to copy this information.
519  it->setExternal(SD.isExternal());
521 
522  StringRef Rest = AliasName.substr(Pos);
523  if (!Symbol.isUndefined() && !Rest.startswith("@@@"))
524  continue;
525 
526  // FIXME: produce a better error message.
527  if (Symbol.isUndefined() && Rest.startswith("@@") &&
528  !Rest.startswith("@@@"))
529  report_fatal_error("A @@ version cannot be undefined");
530 
531  Renames.insert(std::make_pair(&Symbol, &Alias));
532  }
533 }
534 
535 void ELFObjectWriter::WriteSymbol(MCDataFragment *SymtabF,
536  MCDataFragment *ShndxF,
537  ELFSymbolData &MSD,
538  const MCAsmLayout &Layout) {
539  MCSymbolData &OrigData = *MSD.SymbolData;
540  MCSymbolData &Data =
541  Layout.getAssembler().getSymbolData(OrigData.getSymbol().AliasedSymbol());
542 
543  bool IsReserved = Data.isCommon() || Data.getSymbol().isAbsolute() ||
544  Data.getSymbol().isVariable();
545 
546  // Binding and Type share the same byte as upper and lower nibbles
547  uint8_t Binding = MCELF::GetBinding(OrigData);
548  uint8_t Type = MCELF::GetType(Data);
549  uint8_t Info = (Binding << ELF_STB_Shift) | (Type << ELF_STT_Shift);
550 
551  // Other and Visibility share the same byte with Visibility using the lower
552  // 2 bits
553  uint8_t Visibility = MCELF::GetVisibility(OrigData);
554  uint8_t Other = MCELF::getOther(OrigData) <<
556  Other |= Visibility;
557 
558  uint64_t Value = SymbolValue(Data, Layout);
559  uint64_t Size = 0;
560 
561  assert(!(Data.isCommon() && !Data.isExternal()));
562 
563  const MCExpr *ESize = Data.getSize();
564  if (ESize) {
565  int64_t Res;
566  if (!ESize->EvaluateAsAbsolute(Res, Layout))
567  report_fatal_error("Size expression must be absolute.");
568  Size = Res;
569  }
570 
571  // Write out the symbol table entry
572  WriteSymbolEntry(SymtabF, ShndxF, MSD.StringIndex, Info, Value,
573  Size, Other, MSD.SectionIndex, IsReserved);
574 }
575 
576 void ELFObjectWriter::WriteSymbolTable(MCDataFragment *SymtabF,
577  MCDataFragment *ShndxF,
578  const MCAssembler &Asm,
579  const MCAsmLayout &Layout,
580  const SectionIndexMapTy &SectionIndexMap) {
581  // The string table must be emitted first because we need the index
582  // into the string table for all the symbol names.
583  assert(StringTable.size() && "Missing string table");
584 
585  // FIXME: Make sure the start of the symbol table is aligned.
586 
587  // The first entry is the undefined symbol entry.
588  WriteSymbolEntry(SymtabF, ShndxF, 0, 0, 0, 0, 0, 0, false);
589 
590  for (unsigned i = 0, e = FileSymbolData.size(); i != e; ++i) {
591  WriteSymbolEntry(SymtabF, ShndxF, FileSymbolData[i],
594  }
595 
596  // Write the symbol table entries.
597  LastLocalSymbolIndex = FileSymbolData.size() + LocalSymbolData.size() + 1;
598 
599  for (unsigned i = 0, e = LocalSymbolData.size(); i != e; ++i) {
600  ELFSymbolData &MSD = LocalSymbolData[i];
601  WriteSymbol(SymtabF, ShndxF, MSD, Layout);
602  }
603 
604  // Write out a symbol table entry for each regular section.
605  for (MCAssembler::const_iterator i = Asm.begin(), e = Asm.end(); i != e;
606  ++i) {
607  const MCSectionELF &Section =
608  static_cast<const MCSectionELF&>(i->getSection());
609  if (Section.getType() == ELF::SHT_RELA ||
610  Section.getType() == ELF::SHT_REL ||
611  Section.getType() == ELF::SHT_STRTAB ||
612  Section.getType() == ELF::SHT_SYMTAB ||
613  Section.getType() == ELF::SHT_SYMTAB_SHNDX)
614  continue;
615  WriteSymbolEntry(SymtabF, ShndxF, 0, ELF::STT_SECTION, 0, 0,
616  ELF::STV_DEFAULT, SectionIndexMap.lookup(&Section),
617  false);
618  LastLocalSymbolIndex++;
619  }
620 
621  for (unsigned i = 0, e = ExternalSymbolData.size(); i != e; ++i) {
622  ELFSymbolData &MSD = ExternalSymbolData[i];
623  MCSymbolData &Data = *MSD.SymbolData;
624  assert(((Data.getFlags() & ELF_STB_Global) ||
625  (Data.getFlags() & ELF_STB_Weak)) &&
626  "External symbol requires STB_GLOBAL or STB_WEAK flag");
627  WriteSymbol(SymtabF, ShndxF, MSD, Layout);
628  if (MCELF::GetBinding(Data) == ELF::STB_LOCAL)
629  LastLocalSymbolIndex++;
630  }
631 
632  for (unsigned i = 0, e = UndefinedSymbolData.size(); i != e; ++i) {
633  ELFSymbolData &MSD = UndefinedSymbolData[i];
634  MCSymbolData &Data = *MSD.SymbolData;
635  WriteSymbol(SymtabF, ShndxF, MSD, Layout);
636  if (MCELF::GetBinding(Data) == ELF::STB_LOCAL)
637  LastLocalSymbolIndex++;
638  }
639 }
640 
641 const MCSymbol *ELFObjectWriter::SymbolToReloc(const MCAssembler &Asm,
642  const MCValue &Target,
643  const MCFragment &F,
644  const MCFixup &Fixup,
645  bool IsPCRel) const {
646  const MCSymbol &Symbol = Target.getSymA()->getSymbol();
647  const MCSymbol &ASymbol = Symbol.AliasedSymbol();
648  const MCSymbol *Renamed = Renames.lookup(&Symbol);
649  const MCSymbolData &SD = Asm.getSymbolData(Symbol);
650 
651  if (ASymbol.isUndefined()) {
652  if (Renamed)
653  return Renamed;
654  return undefinedExplicitRelSym(Target, Fixup, IsPCRel);
655  }
656 
657  if (SD.isExternal()) {
658  if (Renamed)
659  return Renamed;
660  return &Symbol;
661  }
662 
663  const MCSectionELF &Section =
664  static_cast<const MCSectionELF&>(ASymbol.getSection());
665  const SectionKind secKind = Section.getKind();
666 
667  if (secKind.isBSS())
668  return ExplicitRelSym(Asm, Target, F, Fixup, IsPCRel);
669 
670  if (secKind.isThreadLocal()) {
671  if (Renamed)
672  return Renamed;
673  return &Symbol;
674  }
675 
676  MCSymbolRefExpr::VariantKind Kind = Target.getSymA()->getKind();
677  const MCSectionELF &Sec2 =
678  static_cast<const MCSectionELF&>(F.getParent()->getSection());
679 
680  if (&Sec2 != &Section &&
681  (Kind == MCSymbolRefExpr::VK_PLT ||
683  Kind == MCSymbolRefExpr::VK_GOTOFF)) {
684  if (Renamed)
685  return Renamed;
686  return &Symbol;
687  }
688 
689  if (Section.getFlags() & ELF::SHF_MERGE) {
690  if (Target.getConstant() == 0)
691  return ExplicitRelSym(Asm, Target, F, Fixup, IsPCRel);
692  if (Renamed)
693  return Renamed;
694  return &Symbol;
695  }
696 
697  return ExplicitRelSym(Asm, Target, F, Fixup, IsPCRel);
698 
699 }
700 
701 
702 void ELFObjectWriter::RecordRelocation(const MCAssembler &Asm,
703  const MCAsmLayout &Layout,
704  const MCFragment *Fragment,
705  const MCFixup &Fixup,
706  MCValue Target,
707  uint64_t &FixedValue) {
708  int64_t Addend = 0;
709  int Index = 0;
710  int64_t Value = Target.getConstant();
711  const MCSymbol *RelocSymbol = NULL;
712 
713  bool IsPCRel = isFixupKindPCRel(Asm, Fixup.getKind());
714  if (!Target.isAbsolute()) {
715  const MCSymbol &Symbol = Target.getSymA()->getSymbol();
716  const MCSymbol &ASymbol = Symbol.AliasedSymbol();
717  RelocSymbol = SymbolToReloc(Asm, Target, *Fragment, Fixup, IsPCRel);
718 
719  if (const MCSymbolRefExpr *RefB = Target.getSymB()) {
720  const MCSymbol &SymbolB = RefB->getSymbol();
721  MCSymbolData &SDB = Asm.getSymbolData(SymbolB);
722  IsPCRel = true;
723 
724  // Offset of the symbol in the section
725  int64_t a = Layout.getSymbolOffset(&SDB);
726 
727  // Offset of the relocation in the section
728  int64_t b = Layout.getFragmentOffset(Fragment) + Fixup.getOffset();
729  Value += b - a;
730  }
731 
732  if (!RelocSymbol) {
733  MCSymbolData &SD = Asm.getSymbolData(ASymbol);
734  MCFragment *F = SD.getFragment();
735 
736  if (F) {
737  Index = F->getParent()->getOrdinal() + 1;
738  // Offset of the symbol in the section
739  Value += Layout.getSymbolOffset(&SD);
740  } else {
741  Index = 0;
742  }
743  } else {
744  if (Asm.getSymbolData(Symbol).getFlags() & ELF_Other_Weakref)
745  WeakrefUsedInReloc.insert(RelocSymbol);
746  else
747  UsedInReloc.insert(RelocSymbol);
748  Index = -1;
749  }
750  Addend = Value;
751  if (hasRelocationAddend())
752  Value = 0;
753  }
754 
755  FixedValue = Value;
756  unsigned Type = GetRelocType(Target, Fixup, IsPCRel,
757  (RelocSymbol != 0), Addend);
758  MCSymbolRefExpr::VariantKind Modifier = Target.isAbsolute() ?
760  if (RelocNeedsGOT(Modifier))
761  NeedsGOT = true;
762 
763  uint64_t RelocOffset = Layout.getFragmentOffset(Fragment) +
764  Fixup.getOffset();
765 
766  if (!hasRelocationAddend())
767  Addend = 0;
768 
769  if (is64Bit())
770  assert(isInt<64>(Addend));
771  else
772  assert(isInt<32>(Addend));
773 
774  ELFRelocationEntry ERE(RelocOffset, Index, Type, RelocSymbol, Addend, Fixup);
775  Relocations[Fragment->getParent()].push_back(ERE);
776 }
777 
778 
779 uint64_t
780 ELFObjectWriter::getSymbolIndexInSymbolTable(const MCAssembler &Asm,
781  const MCSymbol *S) {
782  MCSymbolData &SD = Asm.getSymbolData(*S);
783  return SD.getIndex();
784 }
785 
786 bool ELFObjectWriter::isInSymtab(const MCAssembler &Asm,
787  const MCSymbolData &Data,
788  bool Used, bool Renamed) {
789  if (Data.getFlags() & ELF_Other_Weakref)
790  return false;
791 
792  if (Used)
793  return true;
794 
795  if (Renamed)
796  return false;
797 
798  const MCSymbol &Symbol = Data.getSymbol();
799 
800  if (Symbol.getName() == "_GLOBAL_OFFSET_TABLE_")
801  return true;
802 
803  const MCSymbol &A = Symbol.AliasedSymbol();
804  if (Symbol.isVariable() && !A.isVariable() && A.isUndefined())
805  return false;
806 
807  bool IsGlobal = MCELF::GetBinding(Data) == ELF::STB_GLOBAL;
808  if (!Symbol.isVariable() && Symbol.isUndefined() && !IsGlobal)
809  return false;
810 
811  if (!Asm.isSymbolLinkerVisible(Symbol) && !Symbol.isUndefined())
812  return false;
813 
814  if (Symbol.isTemporary())
815  return false;
816 
817  return true;
818 }
819 
820 bool ELFObjectWriter::isLocal(const MCSymbolData &Data, bool isSignature,
821  bool isUsedInReloc) {
822  if (Data.isExternal())
823  return false;
824 
825  const MCSymbol &Symbol = Data.getSymbol();
826  const MCSymbol &RefSymbol = Symbol.AliasedSymbol();
827 
828  if (RefSymbol.isUndefined() && !RefSymbol.isVariable()) {
829  if (isSignature && !isUsedInReloc)
830  return true;
831 
832  return false;
833  }
834 
835  return true;
836 }
837 
838 void ELFObjectWriter::ComputeIndexMap(MCAssembler &Asm,
839  SectionIndexMapTy &SectionIndexMap,
840  const RelMapTy &RelMap) {
841  unsigned Index = 1;
842  for (MCAssembler::iterator it = Asm.begin(),
843  ie = Asm.end(); it != ie; ++it) {
844  const MCSectionELF &Section =
845  static_cast<const MCSectionELF &>(it->getSection());
846  if (Section.getType() != ELF::SHT_GROUP)
847  continue;
848  SectionIndexMap[&Section] = Index++;
849  }
850 
851  for (MCAssembler::iterator it = Asm.begin(),
852  ie = Asm.end(); it != ie; ++it) {
853  const MCSectionELF &Section =
854  static_cast<const MCSectionELF &>(it->getSection());
855  if (Section.getType() == ELF::SHT_GROUP ||
856  Section.getType() == ELF::SHT_REL ||
857  Section.getType() == ELF::SHT_RELA)
858  continue;
859  SectionIndexMap[&Section] = Index++;
860  const MCSectionELF *RelSection = RelMap.lookup(&Section);
861  if (RelSection)
862  SectionIndexMap[RelSection] = Index++;
863  }
864 }
865 
866 void ELFObjectWriter::ComputeSymbolTable(MCAssembler &Asm,
867  const SectionIndexMapTy &SectionIndexMap,
868  RevGroupMapTy RevGroupMap,
869  unsigned NumRegularSections) {
870  // FIXME: Is this the correct place to do this?
871  // FIXME: Why is an undefined reference to _GLOBAL_OFFSET_TABLE_ needed?
872  if (NeedsGOT) {
873  StringRef Name = "_GLOBAL_OFFSET_TABLE_";
874  MCSymbol *Sym = Asm.getContext().GetOrCreateSymbol(Name);
875  MCSymbolData &Data = Asm.getOrCreateSymbolData(*Sym);
876  Data.setExternal(true);
878  }
879 
880  // Index 0 is always the empty string.
881  StringMap<uint64_t> StringIndexMap;
882  StringTable += '\x00';
883 
884  // FIXME: We could optimize suffixes in strtab in the same way we
885  // optimize them in shstrtab.
886 
888  ie = Asm.file_names_end();
889  it != ie;
890  ++it) {
891  StringRef Name = *it;
892  uint64_t &Entry = StringIndexMap[Name];
893  if (!Entry) {
894  Entry = StringTable.size();
895  StringTable += Name;
896  StringTable += '\x00';
897  }
898  FileSymbolData.push_back(Entry);
899  }
900 
901  // Add the data for the symbols.
903  ie = Asm.symbol_end(); it != ie; ++it) {
904  const MCSymbol &Symbol = it->getSymbol();
905 
906  bool Used = UsedInReloc.count(&Symbol);
907  bool WeakrefUsed = WeakrefUsedInReloc.count(&Symbol);
908  bool isSignature = RevGroupMap.count(&Symbol);
909 
910  if (!isInSymtab(Asm, *it,
911  Used || WeakrefUsed || isSignature,
912  Renames.count(&Symbol)))
913  continue;
914 
915  ELFSymbolData MSD;
916  MSD.SymbolData = it;
917  const MCSymbol &RefSymbol = Symbol.AliasedSymbol();
918 
919  // Undefined symbols are global, but this is the first place we
920  // are able to set it.
921  bool Local = isLocal(*it, isSignature, Used);
922  if (!Local && MCELF::GetBinding(*it) == ELF::STB_LOCAL) {
923  MCSymbolData &SD = Asm.getSymbolData(RefSymbol);
926  }
927 
928  if (RefSymbol.isUndefined() && !Used && WeakrefUsed)
930 
931  if (it->isCommon()) {
932  assert(!Local);
933  MSD.SectionIndex = ELF::SHN_COMMON;
934  } else if (Symbol.isAbsolute() || RefSymbol.isVariable()) {
935  MSD.SectionIndex = ELF::SHN_ABS;
936  } else if (RefSymbol.isUndefined()) {
937  if (isSignature && !Used)
938  MSD.SectionIndex = SectionIndexMap.lookup(RevGroupMap[&Symbol]);
939  else
940  MSD.SectionIndex = ELF::SHN_UNDEF;
941  } else {
942  const MCSectionELF &Section =
943  static_cast<const MCSectionELF&>(RefSymbol.getSection());
944  MSD.SectionIndex = SectionIndexMap.lookup(&Section);
945  if (MSD.SectionIndex >= ELF::SHN_LORESERVE)
946  NeedsSymtabShndx = true;
947  assert(MSD.SectionIndex && "Invalid section index!");
948  }
949 
950  // The @@@ in symbol version is replaced with @ in undefined symbols and
951  // @@ in defined ones.
952  StringRef Name = Symbol.getName();
953  SmallString<32> Buf;
954 
955  size_t Pos = Name.find("@@@");
956  if (Pos != StringRef::npos) {
957  Buf += Name.substr(0, Pos);
958  unsigned Skip = MSD.SectionIndex == ELF::SHN_UNDEF ? 2 : 1;
959  Buf += Name.substr(Pos + Skip);
960  Name = Buf;
961  }
962 
963  uint64_t &Entry = StringIndexMap[Name];
964  if (!Entry) {
965  Entry = StringTable.size();
966  StringTable += Name;
967  StringTable += '\x00';
968  }
969  MSD.StringIndex = Entry;
970  if (MSD.SectionIndex == ELF::SHN_UNDEF)
971  UndefinedSymbolData.push_back(MSD);
972  else if (Local)
973  LocalSymbolData.push_back(MSD);
974  else
975  ExternalSymbolData.push_back(MSD);
976  }
977 
978  // Symbols are required to be in lexicographic order.
979  array_pod_sort(LocalSymbolData.begin(), LocalSymbolData.end());
980  array_pod_sort(ExternalSymbolData.begin(), ExternalSymbolData.end());
981  array_pod_sort(UndefinedSymbolData.begin(), UndefinedSymbolData.end());
982 
983  // Set the symbol indices. Local symbols must come before all other
984  // symbols with non-local bindings.
985  unsigned Index = FileSymbolData.size() + 1;
986  for (unsigned i = 0, e = LocalSymbolData.size(); i != e; ++i)
987  LocalSymbolData[i].SymbolData->setIndex(Index++);
988 
989  Index += NumRegularSections;
990 
991  for (unsigned i = 0, e = ExternalSymbolData.size(); i != e; ++i)
992  ExternalSymbolData[i].SymbolData->setIndex(Index++);
993  for (unsigned i = 0, e = UndefinedSymbolData.size(); i != e; ++i)
994  UndefinedSymbolData[i].SymbolData->setIndex(Index++);
995 
996  if (Index >= ELF::SHN_LORESERVE)
997  NeedsSymtabShndx = true;
998 }
999 
1000 void ELFObjectWriter::CreateRelocationSections(MCAssembler &Asm,
1001  MCAsmLayout &Layout,
1002  RelMapTy &RelMap) {
1003  for (MCAssembler::const_iterator it = Asm.begin(),
1004  ie = Asm.end(); it != ie; ++it) {
1005  const MCSectionData &SD = *it;
1006  if (Relocations[&SD].empty())
1007  continue;
1008 
1009  MCContext &Ctx = Asm.getContext();
1010  const MCSectionELF &Section =
1011  static_cast<const MCSectionELF&>(SD.getSection());
1012 
1013  const StringRef SectionName = Section.getSectionName();
1014  std::string RelaSectionName = hasRelocationAddend() ? ".rela" : ".rel";
1015  RelaSectionName += SectionName;
1016 
1017  unsigned EntrySize;
1018  if (hasRelocationAddend())
1019  EntrySize = is64Bit() ? sizeof(ELF::Elf64_Rela) : sizeof(ELF::Elf32_Rela);
1020  else
1021  EntrySize = is64Bit() ? sizeof(ELF::Elf64_Rel) : sizeof(ELF::Elf32_Rel);
1022 
1023  unsigned Flags = 0;
1024  StringRef Group = "";
1025  if (Section.getFlags() & ELF::SHF_GROUP) {
1026  Flags = ELF::SHF_GROUP;
1027  Group = Section.getGroup()->getName();
1028  }
1029 
1030  const MCSectionELF *RelaSection =
1031  Ctx.getELFSection(RelaSectionName, hasRelocationAddend() ?
1032  ELF::SHT_RELA : ELF::SHT_REL, Flags,
1034  EntrySize, Group);
1035  RelMap[&Section] = RelaSection;
1036  Asm.getOrCreateSectionData(*RelaSection);
1037  }
1038 }
1039 
1040 void ELFObjectWriter::WriteRelocations(MCAssembler &Asm, MCAsmLayout &Layout,
1041  const RelMapTy &RelMap) {
1042  for (MCAssembler::const_iterator it = Asm.begin(),
1043  ie = Asm.end(); it != ie; ++it) {
1044  const MCSectionData &SD = *it;
1045  const MCSectionELF &Section =
1046  static_cast<const MCSectionELF&>(SD.getSection());
1047 
1048  const MCSectionELF *RelaSection = RelMap.lookup(&Section);
1049  if (!RelaSection)
1050  continue;
1051  MCSectionData &RelaSD = Asm.getOrCreateSectionData(*RelaSection);
1052  RelaSD.setAlignment(is64Bit() ? 8 : 4);
1053 
1054  MCDataFragment *F = new MCDataFragment(&RelaSD);
1055  WriteRelocationsFragment(Asm, F, &*it);
1056  }
1057 }
1058 
1059 void ELFObjectWriter::WriteSecHdrEntry(uint32_t Name, uint32_t Type,
1060  uint64_t Flags, uint64_t Address,
1061  uint64_t Offset, uint64_t Size,
1062  uint32_t Link, uint32_t Info,
1063  uint64_t Alignment,
1064  uint64_t EntrySize) {
1065  Write32(Name); // sh_name: index into string table
1066  Write32(Type); // sh_type
1067  WriteWord(Flags); // sh_flags
1068  WriteWord(Address); // sh_addr
1069  WriteWord(Offset); // sh_offset
1070  WriteWord(Size); // sh_size
1071  Write32(Link); // sh_link
1072  Write32(Info); // sh_info
1073  WriteWord(Alignment); // sh_addralign
1074  WriteWord(EntrySize); // sh_entsize
1075 }
1076 
1077 void ELFObjectWriter::WriteRelocationsFragment(const MCAssembler &Asm,
1078  MCDataFragment *F,
1079  const MCSectionData *SD) {
1080  std::vector<ELFRelocationEntry> &Relocs = Relocations[SD];
1081 
1082  // Sort the relocation entries. Most targets just sort by r_offset, but some
1083  // (e.g., MIPS) have additional constraints.
1084  TargetObjectWriter->sortRelocs(Asm, Relocs);
1085 
1086  for (unsigned i = 0, e = Relocs.size(); i != e; ++i) {
1087  ELFRelocationEntry entry = Relocs[e - i - 1];
1088 
1089  if (!entry.Index)
1090  ;
1091  else if (entry.Index < 0)
1092  entry.Index = getSymbolIndexInSymbolTable(Asm, entry.Symbol);
1093  else
1094  entry.Index += FileSymbolData.size() + LocalSymbolData.size();
1095  if (is64Bit()) {
1096  String64(*F, entry.r_offset);
1097  if (TargetObjectWriter->isN64()) {
1098  String32(*F, entry.Index);
1099 
1100  String8(*F, TargetObjectWriter->getRSsym(entry.Type));
1101  String8(*F, TargetObjectWriter->getRType3(entry.Type));
1102  String8(*F, TargetObjectWriter->getRType2(entry.Type));
1103  String8(*F, TargetObjectWriter->getRType(entry.Type));
1104  }
1105  else {
1106  struct ELF::Elf64_Rela ERE64;
1107  ERE64.setSymbolAndType(entry.Index, entry.Type);
1108  String64(*F, ERE64.r_info);
1109  }
1110  if (hasRelocationAddend())
1111  String64(*F, entry.r_addend);
1112  } else {
1113  String32(*F, entry.r_offset);
1114 
1115  struct ELF::Elf32_Rela ERE32;
1116  ERE32.setSymbolAndType(entry.Index, entry.Type);
1117  String32(*F, ERE32.r_info);
1118 
1119  if (hasRelocationAddend())
1120  String32(*F, entry.r_addend);
1121  }
1122  }
1123 }
1124 
1125 static int compareBySuffix(const MCSectionELF *const *a,
1126  const MCSectionELF *const *b) {
1127  const StringRef &NameA = (*a)->getSectionName();
1128  const StringRef &NameB = (*b)->getSectionName();
1129  const unsigned sizeA = NameA.size();
1130  const unsigned sizeB = NameB.size();
1131  const unsigned len = std::min(sizeA, sizeB);
1132  for (unsigned int i = 0; i < len; ++i) {
1133  char ca = NameA[sizeA - i - 1];
1134  char cb = NameB[sizeB - i - 1];
1135  if (ca != cb)
1136  return cb - ca;
1137  }
1138 
1139  return sizeB - sizeA;
1140 }
1141 
1142 void ELFObjectWriter::CreateMetadataSections(MCAssembler &Asm,
1143  MCAsmLayout &Layout,
1144  SectionIndexMapTy &SectionIndexMap,
1145  const RelMapTy &RelMap) {
1146  MCContext &Ctx = Asm.getContext();
1147  MCDataFragment *F;
1148 
1149  unsigned EntrySize = is64Bit() ? ELF::SYMENTRY_SIZE64 : ELF::SYMENTRY_SIZE32;
1150 
1151  // We construct .shstrtab, .symtab and .strtab in this order to match gnu as.
1152  const MCSectionELF *ShstrtabSection =
1153  Ctx.getELFSection(".shstrtab", ELF::SHT_STRTAB, 0,
1155  MCSectionData &ShstrtabSD = Asm.getOrCreateSectionData(*ShstrtabSection);
1156  ShstrtabSD.setAlignment(1);
1157 
1158  const MCSectionELF *SymtabSection =
1159  Ctx.getELFSection(".symtab", ELF::SHT_SYMTAB, 0,
1161  EntrySize, "");
1162  MCSectionData &SymtabSD = Asm.getOrCreateSectionData(*SymtabSection);
1163  SymtabSD.setAlignment(is64Bit() ? 8 : 4);
1164 
1165  MCSectionData *SymtabShndxSD = NULL;
1166 
1167  if (NeedsSymtabShndx) {
1168  const MCSectionELF *SymtabShndxSection =
1169  Ctx.getELFSection(".symtab_shndx", ELF::SHT_SYMTAB_SHNDX, 0,
1170  SectionKind::getReadOnly(), 4, "");
1171  SymtabShndxSD = &Asm.getOrCreateSectionData(*SymtabShndxSection);
1172  SymtabShndxSD->setAlignment(4);
1173  }
1174 
1175  const MCSectionELF *StrtabSection;
1176  StrtabSection = Ctx.getELFSection(".strtab", ELF::SHT_STRTAB, 0,
1178  MCSectionData &StrtabSD = Asm.getOrCreateSectionData(*StrtabSection);
1179  StrtabSD.setAlignment(1);
1180 
1181  ComputeIndexMap(Asm, SectionIndexMap, RelMap);
1182 
1183  ShstrtabIndex = SectionIndexMap.lookup(ShstrtabSection);
1184  SymbolTableIndex = SectionIndexMap.lookup(SymtabSection);
1185  StringTableIndex = SectionIndexMap.lookup(StrtabSection);
1186 
1187  // Symbol table
1188  F = new MCDataFragment(&SymtabSD);
1189  MCDataFragment *ShndxF = NULL;
1190  if (NeedsSymtabShndx) {
1191  ShndxF = new MCDataFragment(SymtabShndxSD);
1192  }
1193  WriteSymbolTable(F, ShndxF, Asm, Layout, SectionIndexMap);
1194 
1195  F = new MCDataFragment(&StrtabSD);
1196  F->getContents().append(StringTable.begin(), StringTable.end());
1197 
1198  F = new MCDataFragment(&ShstrtabSD);
1199 
1200  std::vector<const MCSectionELF*> Sections;
1201  for (MCAssembler::const_iterator it = Asm.begin(),
1202  ie = Asm.end(); it != ie; ++it) {
1203  const MCSectionELF &Section =
1204  static_cast<const MCSectionELF&>(it->getSection());
1205  Sections.push_back(&Section);
1206  }
1207  array_pod_sort(Sections.begin(), Sections.end(), compareBySuffix);
1208 
1209  // Section header string table.
1210  //
1211  // The first entry of a string table holds a null character so skip
1212  // section 0.
1213  uint64_t Index = 1;
1214  F->getContents().push_back('\x00');
1215 
1216  for (unsigned int I = 0, E = Sections.size(); I != E; ++I) {
1217  const MCSectionELF &Section = *Sections[I];
1218 
1219  StringRef Name = Section.getSectionName();
1220  if (I != 0) {
1221  StringRef PreviousName = Sections[I - 1]->getSectionName();
1222  if (PreviousName.endswith(Name)) {
1223  SectionStringTableIndex[&Section] = Index - Name.size() - 1;
1224  continue;
1225  }
1226  }
1227  // Remember the index into the string table so we can write it
1228  // into the sh_name field of the section header table.
1229  SectionStringTableIndex[&Section] = Index;
1230 
1231  Index += Name.size() + 1;
1232  F->getContents().append(Name.begin(), Name.end());
1233  F->getContents().push_back('\x00');
1234  }
1235 }
1236 
1237 void ELFObjectWriter::CreateIndexedSections(MCAssembler &Asm,
1238  MCAsmLayout &Layout,
1239  GroupMapTy &GroupMap,
1240  RevGroupMapTy &RevGroupMap,
1241  SectionIndexMapTy &SectionIndexMap,
1242  const RelMapTy &RelMap) {
1243  // Create the .note.GNU-stack section if needed.
1244  MCContext &Ctx = Asm.getContext();
1245  if (Asm.getNoExecStack()) {
1246  const MCSectionELF *GnuStackSection =
1247  Ctx.getELFSection(".note.GNU-stack", ELF::SHT_PROGBITS, 0,
1249  Asm.getOrCreateSectionData(*GnuStackSection);
1250  }
1251 
1252  // Build the groups
1253  for (MCAssembler::const_iterator it = Asm.begin(), ie = Asm.end();
1254  it != ie; ++it) {
1255  const MCSectionELF &Section =
1256  static_cast<const MCSectionELF&>(it->getSection());
1257  if (!(Section.getFlags() & ELF::SHF_GROUP))
1258  continue;
1259 
1260  const MCSymbol *SignatureSymbol = Section.getGroup();
1261  Asm.getOrCreateSymbolData(*SignatureSymbol);
1262  const MCSectionELF *&Group = RevGroupMap[SignatureSymbol];
1263  if (!Group) {
1264  Group = Ctx.CreateELFGroupSection();
1265  MCSectionData &Data = Asm.getOrCreateSectionData(*Group);
1266  Data.setAlignment(4);
1267  MCDataFragment *F = new MCDataFragment(&Data);
1268  String32(*F, ELF::GRP_COMDAT);
1269  }
1270  GroupMap[Group] = SignatureSymbol;
1271  }
1272 
1273  ComputeIndexMap(Asm, SectionIndexMap, RelMap);
1274 
1275  // Add sections to the groups
1276  for (MCAssembler::const_iterator it = Asm.begin(), ie = Asm.end();
1277  it != ie; ++it) {
1278  const MCSectionELF &Section =
1279  static_cast<const MCSectionELF&>(it->getSection());
1280  if (!(Section.getFlags() & ELF::SHF_GROUP))
1281  continue;
1282  const MCSectionELF *Group = RevGroupMap[Section.getGroup()];
1283  MCSectionData &Data = Asm.getOrCreateSectionData(*Group);
1284  // FIXME: we could use the previous fragment
1285  MCDataFragment *F = new MCDataFragment(&Data);
1286  unsigned Index = SectionIndexMap.lookup(&Section);
1287  String32(*F, Index);
1288  }
1289 }
1290 
1291 void ELFObjectWriter::WriteSection(MCAssembler &Asm,
1292  const SectionIndexMapTy &SectionIndexMap,
1293  uint32_t GroupSymbolIndex,
1294  uint64_t Offset, uint64_t Size,
1295  uint64_t Alignment,
1296  const MCSectionELF &Section) {
1297  uint64_t sh_link = 0;
1298  uint64_t sh_info = 0;
1299 
1300  switch(Section.getType()) {
1301  case ELF::SHT_DYNAMIC:
1302  sh_link = SectionStringTableIndex[&Section];
1303  sh_info = 0;
1304  break;
1305 
1306  case ELF::SHT_REL:
1307  case ELF::SHT_RELA: {
1308  const MCSectionELF *SymtabSection;
1309  const MCSectionELF *InfoSection;
1310  SymtabSection = Asm.getContext().getELFSection(".symtab", ELF::SHT_SYMTAB,
1311  0,
1313  sh_link = SectionIndexMap.lookup(SymtabSection);
1314  assert(sh_link && ".symtab not found");
1315 
1316  // Remove ".rel" and ".rela" prefixes.
1317  unsigned SecNameLen = (Section.getType() == ELF::SHT_REL) ? 4 : 5;
1318  StringRef SectionName = Section.getSectionName().substr(SecNameLen);
1319  StringRef GroupName =
1320  Section.getGroup() ? Section.getGroup()->getName() : "";
1321 
1322  InfoSection = Asm.getContext().getELFSection(SectionName, ELF::SHT_PROGBITS,
1324  0, GroupName);
1325  sh_info = SectionIndexMap.lookup(InfoSection);
1326  break;
1327  }
1328 
1329  case ELF::SHT_SYMTAB:
1330  case ELF::SHT_DYNSYM:
1331  sh_link = StringTableIndex;
1332  sh_info = LastLocalSymbolIndex;
1333  break;
1334 
1335  case ELF::SHT_SYMTAB_SHNDX:
1336  sh_link = SymbolTableIndex;
1337  break;
1338 
1339  case ELF::SHT_PROGBITS:
1340  case ELF::SHT_STRTAB:
1341  case ELF::SHT_NOBITS:
1342  case ELF::SHT_NOTE:
1343  case ELF::SHT_NULL:
1344  case ELF::SHT_ARM_ATTRIBUTES:
1345  case ELF::SHT_INIT_ARRAY:
1346  case ELF::SHT_FINI_ARRAY:
1347  case ELF::SHT_PREINIT_ARRAY:
1348  case ELF::SHT_X86_64_UNWIND:
1349  case ELF::SHT_MIPS_REGINFO:
1350  case ELF::SHT_MIPS_OPTIONS:
1351  // Nothing to do.
1352  break;
1353 
1354  case ELF::SHT_GROUP:
1355  sh_link = SymbolTableIndex;
1356  sh_info = GroupSymbolIndex;
1357  break;
1358 
1359  default:
1360  assert(0 && "FIXME: sh_type value not supported!");
1361  break;
1362  }
1363 
1364  if (TargetObjectWriter->getEMachine() == ELF::EM_ARM &&
1365  Section.getType() == ELF::SHT_ARM_EXIDX) {
1366  StringRef SecName(Section.getSectionName());
1367  if (SecName == ".ARM.exidx") {
1368  sh_link = SectionIndexMap.lookup(
1369  Asm.getContext().getELFSection(".text",
1370  ELF::SHT_PROGBITS,
1371  ELF::SHF_EXECINSTR | ELF::SHF_ALLOC,
1373  } else if (SecName.startswith(".ARM.exidx")) {
1374  StringRef GroupName =
1375  Section.getGroup() ? Section.getGroup()->getName() : "";
1376  sh_link = SectionIndexMap.lookup(Asm.getContext().getELFSection(
1377  SecName.substr(sizeof(".ARM.exidx") - 1), ELF::SHT_PROGBITS,
1378  ELF::SHF_EXECINSTR | ELF::SHF_ALLOC, SectionKind::getText(), 0,
1379  GroupName));
1380  }
1381  }
1382 
1383  WriteSecHdrEntry(SectionStringTableIndex[&Section], Section.getType(),
1384  Section.getFlags(), 0, Offset, Size, sh_link, sh_info,
1385  Alignment, Section.getEntrySize());
1386 }
1387 
1388 bool ELFObjectWriter::IsELFMetaDataSection(const MCSectionData &SD) {
1389  return SD.getOrdinal() == ~UINT32_C(0) &&
1390  !SD.getSection().isVirtualSection();
1391 }
1392 
1393 uint64_t ELFObjectWriter::DataSectionSize(const MCSectionData &SD) {
1394  uint64_t Ret = 0;
1395  for (MCSectionData::const_iterator i = SD.begin(), e = SD.end(); i != e;
1396  ++i) {
1397  const MCFragment &F = *i;
1398  assert(F.getKind() == MCFragment::FT_Data);
1399  Ret += cast<MCDataFragment>(F).getContents().size();
1400  }
1401  return Ret;
1402 }
1403 
1404 uint64_t ELFObjectWriter::GetSectionFileSize(const MCAsmLayout &Layout,
1405  const MCSectionData &SD) {
1406  if (IsELFMetaDataSection(SD))
1407  return DataSectionSize(SD);
1408  return Layout.getSectionFileSize(&SD);
1409 }
1410 
1411 uint64_t ELFObjectWriter::GetSectionAddressSize(const MCAsmLayout &Layout,
1412  const MCSectionData &SD) {
1413  if (IsELFMetaDataSection(SD))
1414  return DataSectionSize(SD);
1415  return Layout.getSectionAddressSize(&SD);
1416 }
1417 
1418 void ELFObjectWriter::WriteDataSectionData(MCAssembler &Asm,
1419  const MCAsmLayout &Layout,
1420  const MCSectionELF &Section) {
1421  const MCSectionData &SD = Asm.getOrCreateSectionData(Section);
1422 
1423  uint64_t Padding = OffsetToAlignment(OS.tell(), SD.getAlignment());
1424  WriteZeros(Padding);
1425 
1426  if (IsELFMetaDataSection(SD)) {
1427  for (MCSectionData::const_iterator i = SD.begin(), e = SD.end(); i != e;
1428  ++i) {
1429  const MCFragment &F = *i;
1430  assert(F.getKind() == MCFragment::FT_Data);
1431  WriteBytes(cast<MCDataFragment>(F).getContents());
1432  }
1433  } else {
1434  Asm.writeSectionData(&SD, Layout);
1435  }
1436 }
1437 
1438 void ELFObjectWriter::WriteSectionHeader(MCAssembler &Asm,
1439  const GroupMapTy &GroupMap,
1440  const MCAsmLayout &Layout,
1441  const SectionIndexMapTy &SectionIndexMap,
1442  const SectionOffsetMapTy &SectionOffsetMap) {
1443  const unsigned NumSections = Asm.size() + 1;
1444 
1445  std::vector<const MCSectionELF*> Sections;
1446  Sections.resize(NumSections - 1);
1447 
1448  for (SectionIndexMapTy::const_iterator i=
1449  SectionIndexMap.begin(), e = SectionIndexMap.end(); i != e; ++i) {
1450  const std::pair<const MCSectionELF*, uint32_t> &p = *i;
1451  Sections[p.second - 1] = p.first;
1452  }
1453 
1454  // Null section first.
1455  uint64_t FirstSectionSize =
1456  NumSections >= ELF::SHN_LORESERVE ? NumSections : 0;
1457  uint32_t FirstSectionLink =
1458  ShstrtabIndex >= ELF::SHN_LORESERVE ? ShstrtabIndex : 0;
1459  WriteSecHdrEntry(0, 0, 0, 0, 0, FirstSectionSize, FirstSectionLink, 0, 0, 0);
1460 
1461  for (unsigned i = 0; i < NumSections - 1; ++i) {
1462  const MCSectionELF &Section = *Sections[i];
1463  const MCSectionData &SD = Asm.getOrCreateSectionData(Section);
1464  uint32_t GroupSymbolIndex;
1465  if (Section.getType() != ELF::SHT_GROUP)
1466  GroupSymbolIndex = 0;
1467  else
1468  GroupSymbolIndex = getSymbolIndexInSymbolTable(Asm,
1469  GroupMap.lookup(&Section));
1470 
1471  uint64_t Size = GetSectionAddressSize(Layout, SD);
1472 
1473  WriteSection(Asm, SectionIndexMap, GroupSymbolIndex,
1474  SectionOffsetMap.lookup(&Section), Size,
1475  SD.getAlignment(), Section);
1476  }
1477 }
1478 
1479 void ELFObjectWriter::ComputeSectionOrder(MCAssembler &Asm,
1480  std::vector<const MCSectionELF*> &Sections) {
1481  for (MCAssembler::iterator it = Asm.begin(),
1482  ie = Asm.end(); it != ie; ++it) {
1483  const MCSectionELF &Section =
1484  static_cast<const MCSectionELF &>(it->getSection());
1485  if (Section.getType() == ELF::SHT_GROUP)
1486  Sections.push_back(&Section);
1487  }
1488 
1489  for (MCAssembler::iterator it = Asm.begin(),
1490  ie = Asm.end(); it != ie; ++it) {
1491  const MCSectionELF &Section =
1492  static_cast<const MCSectionELF &>(it->getSection());
1493  if (Section.getType() != ELF::SHT_GROUP &&
1494  Section.getType() != ELF::SHT_REL &&
1495  Section.getType() != ELF::SHT_RELA)
1496  Sections.push_back(&Section);
1497  }
1498 
1499  for (MCAssembler::iterator it = Asm.begin(),
1500  ie = Asm.end(); it != ie; ++it) {
1501  const MCSectionELF &Section =
1502  static_cast<const MCSectionELF &>(it->getSection());
1503  if (Section.getType() == ELF::SHT_REL ||
1504  Section.getType() == ELF::SHT_RELA)
1505  Sections.push_back(&Section);
1506  }
1507 }
1508 
1509 void ELFObjectWriter::WriteObject(MCAssembler &Asm,
1510  const MCAsmLayout &Layout) {
1511  GroupMapTy GroupMap;
1512  RevGroupMapTy RevGroupMap;
1513  SectionIndexMapTy SectionIndexMap;
1514 
1515  unsigned NumUserSections = Asm.size();
1516 
1518  CreateRelocationSections(Asm, const_cast<MCAsmLayout&>(Layout), RelMap);
1519 
1520  const unsigned NumUserAndRelocSections = Asm.size();
1521  CreateIndexedSections(Asm, const_cast<MCAsmLayout&>(Layout), GroupMap,
1522  RevGroupMap, SectionIndexMap, RelMap);
1523  const unsigned AllSections = Asm.size();
1524  const unsigned NumIndexedSections = AllSections - NumUserAndRelocSections;
1525 
1526  unsigned NumRegularSections = NumUserSections + NumIndexedSections;
1527 
1528  // Compute symbol table information.
1529  ComputeSymbolTable(Asm, SectionIndexMap, RevGroupMap, NumRegularSections);
1530 
1531 
1532  WriteRelocations(Asm, const_cast<MCAsmLayout&>(Layout), RelMap);
1533 
1534  CreateMetadataSections(const_cast<MCAssembler&>(Asm),
1535  const_cast<MCAsmLayout&>(Layout),
1536  SectionIndexMap,
1537  RelMap);
1538 
1539  uint64_t NaturalAlignment = is64Bit() ? 8 : 4;
1540  uint64_t HeaderSize = is64Bit() ? sizeof(ELF::Elf64_Ehdr) :
1541  sizeof(ELF::Elf32_Ehdr);
1542  uint64_t FileOff = HeaderSize;
1543 
1544  std::vector<const MCSectionELF*> Sections;
1545  ComputeSectionOrder(Asm, Sections);
1546  unsigned NumSections = Sections.size();
1547  SectionOffsetMapTy SectionOffsetMap;
1548  for (unsigned i = 0; i < NumRegularSections + 1; ++i) {
1549  const MCSectionELF &Section = *Sections[i];
1550  const MCSectionData &SD = Asm.getOrCreateSectionData(Section);
1551 
1552  FileOff = RoundUpToAlignment(FileOff, SD.getAlignment());
1553 
1554  // Remember the offset into the file for this section.
1555  SectionOffsetMap[&Section] = FileOff;
1556 
1557  // Get the size of the section in the output file (including padding).
1558  FileOff += GetSectionFileSize(Layout, SD);
1559  }
1560 
1561  FileOff = RoundUpToAlignment(FileOff, NaturalAlignment);
1562 
1563  const unsigned SectionHeaderOffset = FileOff - HeaderSize;
1564 
1565  uint64_t SectionHeaderEntrySize = is64Bit() ?
1566  sizeof(ELF::Elf64_Shdr) : sizeof(ELF::Elf32_Shdr);
1567  FileOff += (NumSections + 1) * SectionHeaderEntrySize;
1568 
1569  for (unsigned i = NumRegularSections + 1; i < NumSections; ++i) {
1570  const MCSectionELF &Section = *Sections[i];
1571  const MCSectionData &SD = Asm.getOrCreateSectionData(Section);
1572 
1573  FileOff = RoundUpToAlignment(FileOff, SD.getAlignment());
1574 
1575  // Remember the offset into the file for this section.
1576  SectionOffsetMap[&Section] = FileOff;
1577 
1578  // Get the size of the section in the output file (including padding).
1579  FileOff += GetSectionFileSize(Layout, SD);
1580  }
1581 
1582  // Write out the ELF header ...
1583  WriteHeader(Asm, SectionHeaderOffset, NumSections + 1);
1584 
1585  // ... then the regular sections ...
1586  // + because of .shstrtab
1587  for (unsigned i = 0; i < NumRegularSections + 1; ++i)
1588  WriteDataSectionData(Asm, Layout, *Sections[i]);
1589 
1590  uint64_t Padding = OffsetToAlignment(OS.tell(), NaturalAlignment);
1591  WriteZeros(Padding);
1592 
1593  // ... then the section header table ...
1594  WriteSectionHeader(Asm, GroupMap, Layout, SectionIndexMap,
1595  SectionOffsetMap);
1596 
1597  // ... and then the remaining sections ...
1598  for (unsigned i = NumRegularSections + 1; i < NumSections; ++i)
1599  WriteDataSectionData(Asm, Layout, *Sections[i]);
1600 }
1601 
1602 bool
1603 ELFObjectWriter::IsSymbolRefDifferenceFullyResolvedImpl(const MCAssembler &Asm,
1604  const MCSymbolData &DataA,
1605  const MCFragment &FB,
1606  bool InSet,
1607  bool IsPCRel) const {
1608  if (DataA.getFlags() & ELF_STB_Weak)
1609  return false;
1611  Asm, DataA, FB,InSet, IsPCRel);
1612 }
1613 
1615  raw_ostream &OS,
1616  bool IsLittleEndian) {
1617  return new ELFObjectWriter(MOTW, OS, IsLittleEndian);
1618 }
bool isInt< 32 >(int64_t x)
Definition: MathExtras.h:276
const MCSectionELF * CreateELFGroupSection()
Definition: MCContext.cpp:276
void push_back(const T &Elt)
Definition: SmallVector.h:236
void setExternal(bool Value)
Definition: MCAssembler.h:731
StringRef getSectionName() const
Definition: MCSectionELF.h:61
void setSymbolAndType(Elf32_Word s, unsigned char t)
Definition: Support/ELF.h:1392
const MCSymbol & getSymbol() const
Definition: MCExpr.h:283
size_t size() const
size - Get the string size.
Definition: StringRef.h:113
const MCExpr * getSize() const
Definition: MCAssembler.h:758
static unsigned getOther(MCSymbolData &SD)
Definition: MCELF.cpp:79
iterator begin()
Definition: MCAssembler.h:1039
const MCSymbol * getGroup() const
Definition: MCSectionELF.h:70
size_t find(char C, size_t From=0) const
Definition: StringRef.h:233
const MCSectionELF * getELFSection(StringRef Section, unsigned Type, unsigned Flags, SectionKind Kind)
Definition: MCContext.cpp:244
bool endswith(StringRef Suffix) const
Check if this string ends with the given Suffix.
Definition: StringRef.h:217
bool getNoExecStack() const
Definition: MCAssembler.h:1016
bool isBSS() const
Definition: SectionKind.h:176
unsigned getFlags() const
Definition: MCSectionELF.h:68
StringRef substr(size_t Start, size_t N=npos) const
Definition: StringRef.h:392
void operator<(const Optional< T > &X, const Optional< U > &Y)
Poison comparison between two Optional objects. Clients needs to explicitly compare the underlying va...
F(f)
virtual SmallVectorImpl< char > & getContents()
Definition: MCAssembler.h:221
void setSymbolAndType(Elf64_Word s, Elf64_Word t)
Definition: Support/ELF.h:1429
unsigned getELFHeaderEFlags() const
ELF e_header flags.
Definition: MCAssembler.h:971
MCContext & getContext() const
Definition: MCAssembler.h:992
const MCSymbol & getSymbol() const
Definition: MCAssembler.h:718
LLVM_ATTRIBUTE_NORETURN void report_fatal_error(const char *reason, bool gen_crash_diag=true)
symbol_iterator symbol_begin()
Definition: MCAssembler.h:1054
lazy value info
static unsigned GetVisibility(MCSymbolData &SD)
Definition: MCELF.cpp:64
MCSymbol * GetOrCreateSymbol(StringRef Name)
Definition: MCContext.cpp:118
uint64_t getIndex() const
getIndex - Get the (implementation defined) index.
Definition: MCAssembler.h:781
const MCSection & getSection() const
Definition: MCSymbol.h:111
const MCExpr * getVariableValue() const
getVariableValue() - Get the value for variable symbols.
Definition: MCSymbol.h:137
static unsigned GetType(const MCSymbolData &SD)
Definition: MCELF.cpp:46
bool isInSection() const
Definition: MCSymbol.h:95
virtual bool IsSymbolRefDifferenceFullyResolvedImpl(const MCAssembler &Asm, const MCSymbolData &DataA, const MCFragment &FB, bool InSet, bool IsPCRel) const
bool isExternal() const
Definition: MCAssembler.h:730
bool isAbsolute() const
isAbsolute - Is this an absolute (as opposed to relocatable) value.
Definition: MCValue.h:47
MCFragment * getFragment() const
Definition: MCAssembler.h:720
const MCSection & getSection() const
Definition: MCAssembler.h:605
uint32_t getOffset() const
Definition: MCFixup.h:90
unsigned getOrdinal() const
Definition: MCAssembler.h:613
iterator begin() const
Definition: StringRef.h:97
static void SetBinding(MCSymbolData &SD, unsigned Binding)
Definition: MCELF.cpp:22
void array_pod_sort(IteratorTy Start, IteratorTy End)
Definition: STLExtras.h:289
MCSectionData * getParent() const
Definition: MCAssembler.h:95
uint32_t getFlags() const
getFlags - Get the (implementation defined) symbol flags.
Definition: MCAssembler.h:770
FragmentType getKind() const
Definition: MCAssembler.h:93
unsigned size() const
Definition: StringMap.h:104
MCFixupKind
MCFixupKind - Extensible enumeration to represent the type of a fixup.
Definition: MCFixup.h:22
size_t size() const
Definition: MCAssembler.h:1045
FileNameVectorType::const_iterator const_file_name_iterator
Definition: MCAssembler.h:821
uint64_t getSectionFileSize(const MCSectionData *SD) const
Get the data size of the given section, as emitted to the object file. This may include additional pa...
void append(in_iter in_start, in_iter in_end)
Definition: SmallVector.h:445
MCFixupKind getKind() const
Definition: MCFixup.h:88
const MCSymbolRefExpr * getSymB() const
Definition: MCValue.h:44
MCObjectWriter * createELFObjectWriter(MCELFObjectTargetWriter *MOTW, raw_ostream &OS, bool IsLittleEndian)
Construct a new ELF writer instance.
bool isAbsolute() const
isAbsolute - Check if this is an absolute symbol.
Definition: MCSymbol.h:105
bool isThreadLocal() const
Definition: SectionKind.h:165
MCSymbolData & getOrCreateSymbolData(const MCSymbol &Symbol, bool *Created=0)
Definition: MCAssembler.h:1151
bool isSymbolLinkerVisible(const MCSymbol &SD) const
MCSymbolData & getSymbolData(const MCSymbol &Symbol) const
Definition: MCAssembler.h:1145
static int compareBySuffix(const MCSectionELF *const *a, const MCSectionELF *const *b)
bool startswith(StringRef Prefix) const
Check if this string starts with the given Prefix.
Definition: StringRef.h:208
SectionKind getKind() const
Definition: MCSection.h:47
const MCSymbolRefExpr * getSymA() const
Definition: MCValue.h:43
unsigned getCommonAlignment() const
getCommonAlignment - Return the alignment of a 'common' symbol.
Definition: MCAssembler.h:764
virtual bool isVirtualSection() const =0
unsigned getAlignment() const
Definition: MCAssembler.h:607
bool isCommon() const
isCommon - Is this a 'common' symbol.
Definition: MCAssembler.h:737
const_file_name_iterator file_names_begin() const
Definition: MCAssembler.h:1162
uint64_t getSymbolOffset(const MCSymbolData *SD) const
Get the offset of the given symbol, as computed in the current layout.
uint64_t getSectionAddressSize(const MCSectionData *SD) const
Get the address space size of the given section, as it effects layout. This may differ from the size ...
bool isTemporary() const
isTemporary - Check if this is an assembler temporary symbol.
Definition: MCSymbol.h:76
const_file_name_iterator file_names_end() const
Definition: MCAssembler.h:1166
uint64_t RoundUpToAlignment(uint64_t Value, uint64_t Align)
Definition: MathExtras.h:565
MCSectionData & getOrCreateSectionData(const MCSection &Section, bool *Created=0)
Definition: MCAssembler.h:1134
static unsigned GetBinding(const MCSymbolData &SD)
Definition: MCELF.cpp:29
StringRef getName() const
getName - Get the symbol name.
Definition: MCSymbol.h:70
static const size_t npos
Definition: StringRef.h:45
const MCSymbol & AliasedSymbol() const
Definition: MCSymbol.cpp:42
MCAsmBackend & getBackend() const
Definition: MCAssembler.h:994
#define I(x, y, z)
Definition: MD5.cpp:54
uint64_t getFragmentOffset(const MCFragment *F) const
Get the offset of the given fragment inside its containing section.
void setAlignment(unsigned Value)
Definition: MCAssembler.h:608
MCFixupKindInfo - Target independent information on a fixup kind.
bool isVariable() const
isVariable - Check if this is a variable symbol.
Definition: MCSymbol.h:132
VariantKind getKind() const
Definition: MCExpr.h:285
int64_t getConstant() const
Definition: MCValue.h:42
LLVM Value Representation.
Definition: Value.h:66
MCAssembler & getAssembler() const
Get the assembler object this is a layout for.
Definition: MCAsmLayout.h:61
uint64_t OffsetToAlignment(uint64_t Value, uint64_t Align)
Definition: MathExtras.h:572
iterator end() const
Definition: StringRef.h:99
void writeSectionData(const MCSectionData *Section, const MCAsmLayout &Layout) const
Emit the section contents using the given object writer.
unsigned getType() const
Definition: MCSectionELF.h:67
bool isUndefined() const
isUndefined - Check if this symbol undefined (i.e., implicitly defined).
Definition: MCSymbol.h:100
virtual const MCFixupKindInfo & getFixupKindInfo(MCFixupKind Kind) const
getFixupKindInfo - Get information on a fixup kind.
static SectionKind getReadOnly()
Definition: SectionKind.h:209
unsigned Flags
Flags describing additional information on this fixup kind.
static SectionKind getText()
Definition: SectionKind.h:208
symbol_iterator symbol_end()
Definition: MCAssembler.h:1057