6adec37fa1f0ee49331429bf59cd84260510dad2
[oota-llvm.git] / include / llvm / Object / ELFObjectFile.h
1 //===- ELFObjectFile.h - ELF object file implementation ---------*- C++ -*-===//
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 declares the ELFObjectFile template class.
11 //
12 //===----------------------------------------------------------------------===//
13
14 #ifndef LLVM_OBJECT_ELFOBJECTFILE_H
15 #define LLVM_OBJECT_ELFOBJECTFILE_H
16
17 #include "llvm/ADT/DenseMap.h"
18 #include "llvm/ADT/PointerIntPair.h"
19 #include "llvm/ADT/SmallVector.h"
20 #include "llvm/ADT/StringSwitch.h"
21 #include "llvm/ADT/Triple.h"
22 #include "llvm/Object/ELF.h"
23 #include "llvm/Object/ObjectFile.h"
24 #include "llvm/Support/Casting.h"
25 #include "llvm/Support/ELF.h"
26 #include "llvm/Support/Endian.h"
27 #include "llvm/Support/ErrorHandling.h"
28 #include "llvm/Support/MemoryBuffer.h"
29 #include "llvm/Support/raw_ostream.h"
30 #include <algorithm>
31 #include <cctype>
32 #include <limits>
33 #include <utility>
34
35 namespace llvm {
36 namespace object {
37
38 class elf_symbol_iterator;
39 class ELFSymbolRef;
40
41 class ELFObjectFileBase : public ObjectFile {
42   friend class ELFSymbolRef;
43   friend class ELFSectionRef;
44
45 protected:
46   ELFObjectFileBase(unsigned int Type, MemoryBufferRef Source);
47
48   virtual uint64_t getSymbolSize(DataRefImpl Symb) const = 0;
49   virtual uint8_t getSymbolOther(DataRefImpl Symb) const = 0;
50   virtual uint8_t getSymbolELFType(DataRefImpl Symb) const = 0;
51
52   virtual uint32_t getSectionType(DataRefImpl Sec) const = 0;
53   virtual uint64_t getSectionFlags(DataRefImpl Sec) const = 0;
54
55 public:
56   virtual ErrorOr<int64_t> getRelocationAddend(DataRefImpl Rel) const = 0;
57
58   // FIXME: This is a bit of a hack. Every caller should know if it expecting
59   // and addend or not.
60   virtual bool hasRelocationAddend(DataRefImpl Rel) const = 0;
61
62   typedef iterator_range<elf_symbol_iterator> elf_symbol_iterator_range;
63   virtual elf_symbol_iterator_range getDynamicSymbolIterators() const = 0;
64
65   elf_symbol_iterator_range symbols() const;
66
67   static inline bool classof(const Binary *v) { return v->isELF(); }
68 };
69
70 class ELFSectionRef : public SectionRef {
71 public:
72   ELFSectionRef(const SectionRef &B) : SectionRef(B) {
73     assert(isa<ELFObjectFileBase>(SectionRef::getObject()));
74   }
75
76   const ELFObjectFileBase *getObject() const {
77     return cast<ELFObjectFileBase>(SectionRef::getObject());
78   }
79
80   uint32_t getType() const {
81     return getObject()->getSectionType(getRawDataRefImpl());
82   }
83
84   uint64_t getFlags() const {
85     return getObject()->getSectionFlags(getRawDataRefImpl());
86   }
87 };
88
89 class elf_section_iterator : public section_iterator {
90 public:
91   elf_section_iterator(const section_iterator &B) : section_iterator(B) {
92     assert(isa<ELFObjectFileBase>(B->getObject()));
93   }
94
95   const ELFSectionRef *operator->() const {
96     return static_cast<const ELFSectionRef *>(section_iterator::operator->());
97   }
98
99   const ELFSectionRef &operator*() const {
100     return static_cast<const ELFSectionRef &>(section_iterator::operator*());
101   }
102 };
103
104 class ELFSymbolRef : public SymbolRef {
105 public:
106   ELFSymbolRef(const SymbolRef &B) : SymbolRef(B) {
107     assert(isa<ELFObjectFileBase>(SymbolRef::getObject()));
108   }
109
110   const ELFObjectFileBase *getObject() const {
111     return cast<ELFObjectFileBase>(BasicSymbolRef::getObject());
112   }
113
114   uint64_t getSize() const {
115     return getObject()->getSymbolSize(getRawDataRefImpl());
116   }
117
118   uint8_t getOther() const {
119     return getObject()->getSymbolOther(getRawDataRefImpl());
120   }
121
122   uint8_t getELFType() const {
123     return getObject()->getSymbolELFType(getRawDataRefImpl());
124   }
125 };
126
127 class elf_symbol_iterator : public symbol_iterator {
128 public:
129   elf_symbol_iterator(const basic_symbol_iterator &B)
130       : symbol_iterator(SymbolRef(B->getRawDataRefImpl(),
131                                   cast<ELFObjectFileBase>(B->getObject()))) {}
132
133   const ELFSymbolRef *operator->() const {
134     return static_cast<const ELFSymbolRef *>(symbol_iterator::operator->());
135   }
136
137   const ELFSymbolRef &operator*() const {
138     return static_cast<const ELFSymbolRef &>(symbol_iterator::operator*());
139   }
140 };
141
142 inline ELFObjectFileBase::elf_symbol_iterator_range
143 ELFObjectFileBase::symbols() const {
144   return elf_symbol_iterator_range(symbol_begin(), symbol_end());
145 }
146
147 template <class ELFT> class ELFObjectFile : public ELFObjectFileBase {
148   uint64_t getSymbolSize(DataRefImpl Sym) const override;
149
150 public:
151   LLVM_ELF_IMPORT_TYPES_ELFT(ELFT)
152
153   typedef typename ELFFile<ELFT>::uintX_t uintX_t;
154
155   typedef typename ELFFile<ELFT>::Elf_Sym Elf_Sym;
156   typedef typename ELFFile<ELFT>::Elf_Shdr Elf_Shdr;
157   typedef typename ELFFile<ELFT>::Elf_Ehdr Elf_Ehdr;
158   typedef typename ELFFile<ELFT>::Elf_Rel Elf_Rel;
159   typedef typename ELFFile<ELFT>::Elf_Rela Elf_Rela;
160   typedef typename ELFFile<ELFT>::Elf_Dyn Elf_Dyn;
161
162   typedef typename ELFFile<ELFT>::Elf_Shdr_Iter Elf_Shdr_Iter;
163   typedef typename ELFFile<ELFT>::Elf_Dyn_Iter Elf_Dyn_Iter;
164
165 protected:
166   ELFFile<ELFT> EF;
167
168   void moveSymbolNext(DataRefImpl &Symb) const override;
169   std::error_code getSymbolName(DataRefImpl Symb,
170                                 StringRef &Res) const override;
171   std::error_code getSymbolAddress(DataRefImpl Symb,
172                                    uint64_t &Res) const override;
173   uint64_t getSymbolValue(DataRefImpl Symb) const override;
174   uint32_t getSymbolAlignment(DataRefImpl Symb) const override;
175   uint64_t getCommonSymbolSizeImpl(DataRefImpl Symb) const override;
176   uint32_t getSymbolFlags(DataRefImpl Symb) const override;
177   uint8_t getSymbolOther(DataRefImpl Symb) const override;
178   uint8_t getSymbolELFType(DataRefImpl Symb) const override;
179   SymbolRef::Type getSymbolType(DataRefImpl Symb) const override;
180   section_iterator getSymbolSection(const Elf_Sym *Symb) const;
181   std::error_code getSymbolSection(DataRefImpl Symb,
182                                    section_iterator &Res) const override;
183
184   void moveSectionNext(DataRefImpl &Sec) const override;
185   std::error_code getSectionName(DataRefImpl Sec,
186                                  StringRef &Res) const override;
187   uint64_t getSectionAddress(DataRefImpl Sec) const override;
188   uint64_t getSectionSize(DataRefImpl Sec) const override;
189   std::error_code getSectionContents(DataRefImpl Sec,
190                                      StringRef &Res) const override;
191   uint64_t getSectionAlignment(DataRefImpl Sec) const override;
192   bool isSectionText(DataRefImpl Sec) const override;
193   bool isSectionData(DataRefImpl Sec) const override;
194   bool isSectionBSS(DataRefImpl Sec) const override;
195   bool isSectionVirtual(DataRefImpl Sec) const override;
196   bool sectionContainsSymbol(DataRefImpl Sec, DataRefImpl Symb) const override;
197   relocation_iterator section_rel_begin(DataRefImpl Sec) const override;
198   relocation_iterator section_rel_end(DataRefImpl Sec) const override;
199   section_iterator getRelocatedSection(DataRefImpl Sec) const override;
200
201   void moveRelocationNext(DataRefImpl &Rel) const override;
202   std::error_code getRelocationAddress(DataRefImpl Rel,
203                                        uint64_t &Res) const override;
204   std::error_code getRelocationOffset(DataRefImpl Rel,
205                                       uint64_t &Res) const override;
206   symbol_iterator getRelocationSymbol(DataRefImpl Rel) const override;
207   std::error_code getRelocationType(DataRefImpl Rel,
208                                     uint64_t &Res) const override;
209   std::error_code
210   getRelocationTypeName(DataRefImpl Rel,
211                         SmallVectorImpl<char> &Result) const override;
212
213   uint32_t getSectionType(DataRefImpl Sec) const override;
214   uint64_t getSectionFlags(DataRefImpl Sec) const override;
215   uint64_t getROffset(DataRefImpl Rel) const;
216   StringRef getRelocationTypeName(uint32_t Type) const;
217
218   /// \brief Get the relocation section that contains \a Rel.
219   const Elf_Shdr *getRelSection(DataRefImpl Rel) const {
220     return EF.getSection(Rel.d.a);
221   }
222
223   const Elf_Rel *getRel(DataRefImpl Rel) const;
224   const Elf_Rela *getRela(DataRefImpl Rela) const;
225
226   const Elf_Sym *toELFSymIter(DataRefImpl Sym) const {
227     return reinterpret_cast<const Elf_Sym *>(Sym.p & ~uintptr_t(1));
228   }
229
230   DataRefImpl toDRI(const Elf_Sym *Sym, bool IsDynamic) const {
231     DataRefImpl DRI;
232     DRI.p =
233         reinterpret_cast<uintptr_t>(Sym) | static_cast<uintptr_t>(IsDynamic);
234     return DRI;
235   }
236
237   Elf_Shdr_Iter toELFShdrIter(DataRefImpl Sec) const {
238     return Elf_Shdr_Iter(EF.getHeader()->e_shentsize,
239                          reinterpret_cast<const char *>(Sec.p));
240   }
241
242   DataRefImpl toDRI(Elf_Shdr_Iter Sec) const {
243     DataRefImpl DRI;
244     DRI.p = reinterpret_cast<uintptr_t>(Sec.get());
245     return DRI;
246   }
247
248   DataRefImpl toDRI(const Elf_Shdr *Sec) const {
249     DataRefImpl DRI;
250     DRI.p = reinterpret_cast<uintptr_t>(Sec);
251     return DRI;
252   }
253
254   Elf_Dyn_Iter toELFDynIter(DataRefImpl Dyn) const {
255     return Elf_Dyn_Iter(EF.begin_dynamic_table().getEntSize(),
256                         reinterpret_cast<const char *>(Dyn.p));
257   }
258
259   DataRefImpl toDRI(Elf_Dyn_Iter Dyn) const {
260     DataRefImpl DRI;
261     DRI.p = reinterpret_cast<uintptr_t>(Dyn.get());
262     return DRI;
263   }
264
265   bool isExportedToOtherDSO(const Elf_Sym *ESym) const {
266     unsigned char Binding = ESym->getBinding();
267     unsigned char Visibility = ESym->getVisibility();
268
269     // A symbol is exported if its binding is either GLOBAL or WEAK, and its
270     // visibility is either DEFAULT or PROTECTED. All other symbols are not
271     // exported.
272     if ((Binding == ELF::STB_GLOBAL || Binding == ELF::STB_WEAK) &&
273         (Visibility == ELF::STV_DEFAULT || Visibility == ELF::STV_PROTECTED))
274       return true;
275
276     return false;
277   }
278
279   // This flag is used for classof, to distinguish ELFObjectFile from
280   // its subclass. If more subclasses will be created, this flag will
281   // have to become an enum.
282   bool isDyldELFObject;
283
284 public:
285   ELFObjectFile(MemoryBufferRef Object, std::error_code &EC);
286
287   const Elf_Sym *getSymbol(DataRefImpl Symb) const;
288
289   basic_symbol_iterator symbol_begin_impl() const override;
290   basic_symbol_iterator symbol_end_impl() const override;
291
292   elf_symbol_iterator dynamic_symbol_begin() const;
293   elf_symbol_iterator dynamic_symbol_end() const;
294
295   section_iterator section_begin() const override;
296   section_iterator section_end() const override;
297
298   ErrorOr<int64_t> getRelocationAddend(DataRefImpl Rel) const override;
299   bool hasRelocationAddend(DataRefImpl Rel) const override;
300
301   uint8_t getBytesInAddress() const override;
302   StringRef getFileFormatName() const override;
303   unsigned getArch() const override;
304   StringRef getLoadName() const;
305
306   std::error_code getPlatformFlags(unsigned &Result) const override {
307     Result = EF.getHeader()->e_flags;
308     return std::error_code();
309   }
310
311   const ELFFile<ELFT> *getELFFile() const { return &EF; }
312
313   bool isDyldType() const { return isDyldELFObject; }
314   static inline bool classof(const Binary *v) {
315     return v->getType() == getELFType(ELFT::TargetEndianness == support::little,
316                                       ELFT::Is64Bits);
317   }
318
319   elf_symbol_iterator_range getDynamicSymbolIterators() const override;
320
321   bool isRelocatableObject() const override;
322 };
323
324 typedef ELFObjectFile<ELFType<support::little, false>> ELF32LEObjectFile;
325 typedef ELFObjectFile<ELFType<support::little, true>> ELF64LEObjectFile;
326 typedef ELFObjectFile<ELFType<support::big, false>> ELF32BEObjectFile;
327 typedef ELFObjectFile<ELFType<support::big, true>> ELF64BEObjectFile;
328
329 template <class ELFT>
330 void ELFObjectFile<ELFT>::moveSymbolNext(DataRefImpl &Sym) const {
331   const Elf_Sym *S = toELFSymIter(Sym);
332   Sym = toDRI(++S, Sym.p & 1);
333 }
334
335 template <class ELFT>
336 std::error_code ELFObjectFile<ELFT>::getSymbolName(DataRefImpl Sym,
337                                                    StringRef &Result) const {
338   const Elf_Sym *ESym = toELFSymIter(Sym);
339   ErrorOr<StringRef> Name = EF.getSymbolName(ESym, Sym.p & 1);
340   if (!Name)
341     return Name.getError();
342   Result = *Name;
343   return std::error_code();
344 }
345
346 template <class ELFT>
347 uint64_t ELFObjectFile<ELFT>::getSectionFlags(DataRefImpl Sec) const {
348   return toELFShdrIter(Sec)->sh_flags;
349 }
350
351 template <class ELFT>
352 uint32_t ELFObjectFile<ELFT>::getSectionType(DataRefImpl Sec) const {
353   return toELFShdrIter(Sec)->sh_type;
354 }
355
356 template <class ELFT>
357 uint64_t ELFObjectFile<ELFT>::getSymbolValue(DataRefImpl Symb) const {
358   const Elf_Sym *ESym = getSymbol(Symb);
359   switch (ESym->st_shndx) {
360   case ELF::SHN_COMMON:
361   case ELF::SHN_UNDEF:
362     return UnknownAddress;
363   case ELF::SHN_ABS:
364     return ESym->st_value;
365   }
366
367   const Elf_Ehdr *Header = EF.getHeader();
368   uint64_t Ret = ESym->st_value;
369
370   // Clear the ARM/Thumb or microMIPS indicator flag.
371   if ((Header->e_machine == ELF::EM_ARM || Header->e_machine == ELF::EM_MIPS) &&
372       ESym->getType() == ELF::STT_FUNC)
373     Ret &= ~1;
374
375   return Ret;
376 }
377
378 template <class ELFT>
379 std::error_code ELFObjectFile<ELFT>::getSymbolAddress(DataRefImpl Symb,
380                                                       uint64_t &Result) const {
381   Result = getSymbolValue(Symb);
382   const Elf_Sym *ESym = getSymbol(Symb);
383   switch (ESym->st_shndx) {
384   case ELF::SHN_COMMON:
385   case ELF::SHN_UNDEF:
386   case ELF::SHN_ABS:
387     return std::error_code();
388   }
389
390   const Elf_Ehdr *Header = EF.getHeader();
391
392   if (Header->e_type == ELF::ET_REL) {
393     const typename ELFFile<ELFT>::Elf_Shdr * Section = EF.getSection(ESym);
394     if (Section != nullptr)
395       Result += Section->sh_addr;
396   }
397
398   return std::error_code();
399 }
400
401 template <class ELFT>
402 uint32_t ELFObjectFile<ELFT>::getSymbolAlignment(DataRefImpl Symb) const {
403   const Elf_Sym *Sym = toELFSymIter(Symb);
404   if (Sym->st_shndx == ELF::SHN_COMMON)
405     return Sym->st_value;
406   return 0;
407 }
408
409 template <class ELFT>
410 uint64_t ELFObjectFile<ELFT>::getSymbolSize(DataRefImpl Sym) const {
411   return toELFSymIter(Sym)->st_size;
412 }
413
414 template <class ELFT>
415 uint64_t ELFObjectFile<ELFT>::getCommonSymbolSizeImpl(DataRefImpl Symb) const {
416   return toELFSymIter(Symb)->st_size;
417 }
418
419 template <class ELFT>
420 uint8_t ELFObjectFile<ELFT>::getSymbolOther(DataRefImpl Symb) const {
421   return toELFSymIter(Symb)->st_other;
422 }
423
424 template <class ELFT>
425 uint8_t ELFObjectFile<ELFT>::getSymbolELFType(DataRefImpl Symb) const {
426   return toELFSymIter(Symb)->getType();
427 }
428
429 template <class ELFT>
430 SymbolRef::Type ELFObjectFile<ELFT>::getSymbolType(DataRefImpl Symb) const {
431   const Elf_Sym *ESym = getSymbol(Symb);
432
433   switch (ESym->getType()) {
434   case ELF::STT_NOTYPE:
435     return SymbolRef::ST_Unknown;
436   case ELF::STT_SECTION:
437     return SymbolRef::ST_Debug;
438   case ELF::STT_FILE:
439     return SymbolRef::ST_File;
440   case ELF::STT_FUNC:
441     return SymbolRef::ST_Function;
442   case ELF::STT_OBJECT:
443   case ELF::STT_COMMON:
444   case ELF::STT_TLS:
445     return SymbolRef::ST_Data;
446   default:
447     return SymbolRef::ST_Other;
448   }
449 }
450
451 template <class ELFT>
452 uint32_t ELFObjectFile<ELFT>::getSymbolFlags(DataRefImpl Sym) const {
453   const Elf_Sym *ESym = toELFSymIter(Sym);
454
455   uint32_t Result = SymbolRef::SF_None;
456
457   if (ESym->getBinding() != ELF::STB_LOCAL)
458     Result |= SymbolRef::SF_Global;
459
460   if (ESym->getBinding() == ELF::STB_WEAK)
461     Result |= SymbolRef::SF_Weak;
462
463   if (ESym->st_shndx == ELF::SHN_ABS)
464     Result |= SymbolRef::SF_Absolute;
465
466   if (ESym->getType() == ELF::STT_FILE || ESym->getType() == ELF::STT_SECTION ||
467       ESym == EF.begin_symbols() || ESym == EF.begin_dynamic_symbols())
468     Result |= SymbolRef::SF_FormatSpecific;
469
470   if (EF.getHeader()->e_machine == ELF::EM_ARM) {
471     ErrorOr<StringRef> NameOrErr = EF.getSymbolName(ESym, Sym.p & 1);
472     if (NameOrErr) {
473       StringRef Name = *NameOrErr;
474       if (Name.startswith("$d") || Name.startswith("$t") ||
475           Name.startswith("$a"))
476         Result |= SymbolRef::SF_FormatSpecific;
477     }
478   }
479
480   if (ESym->st_shndx == ELF::SHN_UNDEF)
481     Result |= SymbolRef::SF_Undefined;
482
483   if (ESym->getType() == ELF::STT_COMMON || ESym->st_shndx == ELF::SHN_COMMON)
484     Result |= SymbolRef::SF_Common;
485
486   if (isExportedToOtherDSO(ESym))
487     Result |= SymbolRef::SF_Exported;
488
489   if (ESym->getVisibility() == ELF::STV_HIDDEN)
490     Result |= SymbolRef::SF_Hidden;
491
492   return Result;
493 }
494
495 template <class ELFT>
496 section_iterator
497 ELFObjectFile<ELFT>::getSymbolSection(const Elf_Sym *ESym) const {
498   const Elf_Shdr *ESec = EF.getSection(ESym);
499   if (!ESec)
500     return section_end();
501   else {
502     DataRefImpl Sec;
503     Sec.p = reinterpret_cast<intptr_t>(ESec);
504     return section_iterator(SectionRef(Sec, this));
505   }
506 }
507
508 template <class ELFT>
509 std::error_code
510 ELFObjectFile<ELFT>::getSymbolSection(DataRefImpl Symb,
511                                       section_iterator &Res) const {
512   Res = getSymbolSection(getSymbol(Symb));
513   return std::error_code();
514 }
515
516 template <class ELFT>
517 void ELFObjectFile<ELFT>::moveSectionNext(DataRefImpl &Sec) const {
518   Sec = toDRI(++toELFShdrIter(Sec));
519 }
520
521 template <class ELFT>
522 std::error_code ELFObjectFile<ELFT>::getSectionName(DataRefImpl Sec,
523                                                     StringRef &Result) const {
524   ErrorOr<StringRef> Name = EF.getSectionName(&*toELFShdrIter(Sec));
525   if (!Name)
526     return Name.getError();
527   Result = *Name;
528   return std::error_code();
529 }
530
531 template <class ELFT>
532 uint64_t ELFObjectFile<ELFT>::getSectionAddress(DataRefImpl Sec) const {
533   return toELFShdrIter(Sec)->sh_addr;
534 }
535
536 template <class ELFT>
537 uint64_t ELFObjectFile<ELFT>::getSectionSize(DataRefImpl Sec) const {
538   return toELFShdrIter(Sec)->sh_size;
539 }
540
541 template <class ELFT>
542 std::error_code
543 ELFObjectFile<ELFT>::getSectionContents(DataRefImpl Sec,
544                                         StringRef &Result) const {
545   Elf_Shdr_Iter EShdr = toELFShdrIter(Sec);
546   Result = StringRef((const char *)base() + EShdr->sh_offset, EShdr->sh_size);
547   return std::error_code();
548 }
549
550 template <class ELFT>
551 uint64_t ELFObjectFile<ELFT>::getSectionAlignment(DataRefImpl Sec) const {
552   return toELFShdrIter(Sec)->sh_addralign;
553 }
554
555 template <class ELFT>
556 bool ELFObjectFile<ELFT>::isSectionText(DataRefImpl Sec) const {
557   return toELFShdrIter(Sec)->sh_flags & ELF::SHF_EXECINSTR;
558 }
559
560 template <class ELFT>
561 bool ELFObjectFile<ELFT>::isSectionData(DataRefImpl Sec) const {
562   Elf_Shdr_Iter EShdr = toELFShdrIter(Sec);
563   return EShdr->sh_flags & (ELF::SHF_ALLOC | ELF::SHF_WRITE) &&
564          EShdr->sh_type == ELF::SHT_PROGBITS;
565 }
566
567 template <class ELFT>
568 bool ELFObjectFile<ELFT>::isSectionBSS(DataRefImpl Sec) const {
569   Elf_Shdr_Iter EShdr = toELFShdrIter(Sec);
570   return EShdr->sh_flags & (ELF::SHF_ALLOC | ELF::SHF_WRITE) &&
571          EShdr->sh_type == ELF::SHT_NOBITS;
572 }
573
574 template <class ELFT>
575 bool ELFObjectFile<ELFT>::isSectionVirtual(DataRefImpl Sec) const {
576   return toELFShdrIter(Sec)->sh_type == ELF::SHT_NOBITS;
577 }
578
579 template <class ELFT>
580 bool ELFObjectFile<ELFT>::sectionContainsSymbol(DataRefImpl Sec,
581                                                 DataRefImpl Symb) const {
582   const Elf_Sym *ESym = toELFSymIter(Symb);
583
584   uintX_t Index = ESym->st_shndx;
585   bool Reserved = Index >= ELF::SHN_LORESERVE && Index <= ELF::SHN_HIRESERVE;
586
587   return !Reserved && (&*toELFShdrIter(Sec) == EF.getSection(ESym->st_shndx));
588 }
589
590 template <class ELFT>
591 relocation_iterator
592 ELFObjectFile<ELFT>::section_rel_begin(DataRefImpl Sec) const {
593   DataRefImpl RelData;
594   uintptr_t SHT = reinterpret_cast<uintptr_t>(EF.begin_sections().get());
595   RelData.d.a = (Sec.p - SHT) / EF.getHeader()->e_shentsize;
596   RelData.d.b = 0;
597   return relocation_iterator(RelocationRef(RelData, this));
598 }
599
600 template <class ELFT>
601 relocation_iterator
602 ELFObjectFile<ELFT>::section_rel_end(DataRefImpl Sec) const {
603   DataRefImpl RelData;
604   uintptr_t SHT = reinterpret_cast<uintptr_t>(EF.begin_sections().get());
605   const Elf_Shdr *S = reinterpret_cast<const Elf_Shdr *>(Sec.p);
606   RelData.d.a = (Sec.p - SHT) / EF.getHeader()->e_shentsize;
607   if (S->sh_type != ELF::SHT_RELA && S->sh_type != ELF::SHT_REL)
608     RelData.d.b = 0;
609   else
610     RelData.d.b = S->sh_size / S->sh_entsize;
611
612   return relocation_iterator(RelocationRef(RelData, this));
613 }
614
615 template <class ELFT>
616 section_iterator
617 ELFObjectFile<ELFT>::getRelocatedSection(DataRefImpl Sec) const {
618   if (EF.getHeader()->e_type != ELF::ET_REL)
619     return section_end();
620
621   Elf_Shdr_Iter EShdr = toELFShdrIter(Sec);
622   uintX_t Type = EShdr->sh_type;
623   if (Type != ELF::SHT_REL && Type != ELF::SHT_RELA)
624     return section_end();
625
626   const Elf_Shdr *R = EF.getSection(EShdr->sh_info);
627   return section_iterator(SectionRef(toDRI(R), this));
628 }
629
630 // Relocations
631 template <class ELFT>
632 void ELFObjectFile<ELFT>::moveRelocationNext(DataRefImpl &Rel) const {
633   ++Rel.d.b;
634 }
635
636 template <class ELFT>
637 symbol_iterator
638 ELFObjectFile<ELFT>::getRelocationSymbol(DataRefImpl Rel) const {
639   uint32_t symbolIdx;
640   const Elf_Shdr *sec = getRelSection(Rel);
641   switch (sec->sh_type) {
642   default:
643     report_fatal_error("Invalid section type in Rel!");
644   case ELF::SHT_REL: {
645     symbolIdx = getRel(Rel)->getSymbol(EF.isMips64EL());
646     break;
647   }
648   case ELF::SHT_RELA: {
649     symbolIdx = getRela(Rel)->getSymbol(EF.isMips64EL());
650     break;
651   }
652   }
653   if (!symbolIdx)
654     return symbol_end();
655
656   const Elf_Shdr *SymSec = EF.getSection(sec->sh_link);
657
658   DataRefImpl SymbolData;
659   switch (SymSec->sh_type) {
660   default:
661     report_fatal_error("Invalid symbol table section type!");
662   case ELF::SHT_SYMTAB:
663     SymbolData = toDRI(EF.begin_symbols() + symbolIdx, false);
664     break;
665   case ELF::SHT_DYNSYM:
666     SymbolData = toDRI(EF.begin_dynamic_symbols() + symbolIdx, true);
667     break;
668   }
669
670   return symbol_iterator(SymbolRef(SymbolData, this));
671 }
672
673 template <class ELFT>
674 std::error_code
675 ELFObjectFile<ELFT>::getRelocationAddress(DataRefImpl Rel,
676                                           uint64_t &Result) const {
677   uint64_t ROffset = getROffset(Rel);
678   const Elf_Ehdr *Header = EF.getHeader();
679
680   if (Header->e_type == ELF::ET_REL) {
681     const Elf_Shdr *RelocationSec = getRelSection(Rel);
682     const Elf_Shdr *RelocatedSec = EF.getSection(RelocationSec->sh_info);
683     Result = ROffset + RelocatedSec->sh_addr;
684   } else {
685     Result = ROffset;
686   }
687
688   return std::error_code();
689 }
690
691 template <class ELFT>
692 std::error_code
693 ELFObjectFile<ELFT>::getRelocationOffset(DataRefImpl Rel,
694                                          uint64_t &Result) const {
695   assert(EF.getHeader()->e_type == ELF::ET_REL &&
696          "Only relocatable object files have relocation offsets");
697   Result = getROffset(Rel);
698   return std::error_code();
699 }
700
701 template <class ELFT>
702 uint64_t ELFObjectFile<ELFT>::getROffset(DataRefImpl Rel) const {
703   const Elf_Shdr *sec = getRelSection(Rel);
704   switch (sec->sh_type) {
705   default:
706     report_fatal_error("Invalid section type in Rel!");
707   case ELF::SHT_REL:
708     return getRel(Rel)->r_offset;
709   case ELF::SHT_RELA:
710     return getRela(Rel)->r_offset;
711   }
712 }
713
714 template <class ELFT>
715 std::error_code ELFObjectFile<ELFT>::getRelocationType(DataRefImpl Rel,
716                                                        uint64_t &Result) const {
717   const Elf_Shdr *sec = getRelSection(Rel);
718   switch (sec->sh_type) {
719   default:
720     report_fatal_error("Invalid section type in Rel!");
721   case ELF::SHT_REL: {
722     Result = getRel(Rel)->getType(EF.isMips64EL());
723     break;
724   }
725   case ELF::SHT_RELA: {
726     Result = getRela(Rel)->getType(EF.isMips64EL());
727     break;
728   }
729   }
730   return std::error_code();
731 }
732
733 template <class ELFT>
734 StringRef ELFObjectFile<ELFT>::getRelocationTypeName(uint32_t Type) const {
735   return getELFRelocationTypeName(EF.getHeader()->e_machine, Type);
736 }
737
738 template <class ELFT>
739 std::error_code ELFObjectFile<ELFT>::getRelocationTypeName(
740     DataRefImpl Rel, SmallVectorImpl<char> &Result) const {
741   const Elf_Shdr *sec = getRelSection(Rel);
742   uint32_t type;
743   switch (sec->sh_type) {
744   default:
745     return object_error::parse_failed;
746   case ELF::SHT_REL: {
747     type = getRel(Rel)->getType(EF.isMips64EL());
748     break;
749   }
750   case ELF::SHT_RELA: {
751     type = getRela(Rel)->getType(EF.isMips64EL());
752     break;
753   }
754   }
755
756   EF.getRelocationTypeName(type, Result);
757   return std::error_code();
758 }
759
760 template <class ELFT>
761 ErrorOr<int64_t>
762 ELFObjectFile<ELFT>::getRelocationAddend(DataRefImpl Rel) const {
763   if (getRelSection(Rel)->sh_type != ELF::SHT_RELA)
764     return object_error::parse_failed;
765   return (int64_t)getRela(Rel)->r_addend;
766 }
767
768 template <class ELFT>
769 bool ELFObjectFile<ELFT>::hasRelocationAddend(DataRefImpl Rel) const {
770   return getRelSection(Rel)->sh_type == ELF::SHT_RELA;
771 }
772
773 template <class ELFT>
774 const typename ELFFile<ELFT>::Elf_Sym *
775 ELFObjectFile<ELFT>::getSymbol(DataRefImpl Symb) const {
776   return &*toELFSymIter(Symb);
777 }
778
779 template <class ELFT>
780 const typename ELFObjectFile<ELFT>::Elf_Rel *
781 ELFObjectFile<ELFT>::getRel(DataRefImpl Rel) const {
782   return EF.template getEntry<Elf_Rel>(Rel.d.a, Rel.d.b);
783 }
784
785 template <class ELFT>
786 const typename ELFObjectFile<ELFT>::Elf_Rela *
787 ELFObjectFile<ELFT>::getRela(DataRefImpl Rela) const {
788   return EF.template getEntry<Elf_Rela>(Rela.d.a, Rela.d.b);
789 }
790
791 template <class ELFT>
792 ELFObjectFile<ELFT>::ELFObjectFile(MemoryBufferRef Object, std::error_code &EC)
793     : ELFObjectFileBase(
794           getELFType(static_cast<endianness>(ELFT::TargetEndianness) ==
795                          support::little,
796                      ELFT::Is64Bits),
797           Object),
798       EF(Data.getBuffer(), EC) {}
799
800 template <class ELFT>
801 basic_symbol_iterator ELFObjectFile<ELFT>::symbol_begin_impl() const {
802   DataRefImpl Sym = toDRI(EF.begin_symbols(), false);
803   return basic_symbol_iterator(SymbolRef(Sym, this));
804 }
805
806 template <class ELFT>
807 basic_symbol_iterator ELFObjectFile<ELFT>::symbol_end_impl() const {
808   DataRefImpl Sym = toDRI(EF.end_symbols(), false);
809   return basic_symbol_iterator(SymbolRef(Sym, this));
810 }
811
812 template <class ELFT>
813 elf_symbol_iterator ELFObjectFile<ELFT>::dynamic_symbol_begin() const {
814   DataRefImpl Sym = toDRI(EF.begin_dynamic_symbols(), true);
815   return symbol_iterator(SymbolRef(Sym, this));
816 }
817
818 template <class ELFT>
819 elf_symbol_iterator ELFObjectFile<ELFT>::dynamic_symbol_end() const {
820   DataRefImpl Sym = toDRI(EF.end_dynamic_symbols(), true);
821   return symbol_iterator(SymbolRef(Sym, this));
822 }
823
824 template <class ELFT>
825 section_iterator ELFObjectFile<ELFT>::section_begin() const {
826   return section_iterator(SectionRef(toDRI(EF.begin_sections()), this));
827 }
828
829 template <class ELFT>
830 section_iterator ELFObjectFile<ELFT>::section_end() const {
831   return section_iterator(SectionRef(toDRI(EF.end_sections()), this));
832 }
833
834 template <class ELFT>
835 StringRef ELFObjectFile<ELFT>::getLoadName() const {
836   Elf_Dyn_Iter DI = EF.begin_dynamic_table();
837   Elf_Dyn_Iter DE = EF.end_dynamic_table();
838
839   while (DI != DE && DI->getTag() != ELF::DT_SONAME)
840     ++DI;
841
842   if (DI != DE)
843     return EF.getDynamicString(DI->getVal());
844   return "";
845 }
846
847 template <class ELFT>
848 uint8_t ELFObjectFile<ELFT>::getBytesInAddress() const {
849   return ELFT::Is64Bits ? 8 : 4;
850 }
851
852 template <class ELFT>
853 StringRef ELFObjectFile<ELFT>::getFileFormatName() const {
854   bool IsLittleEndian = ELFT::TargetEndianness == support::little;
855   switch (EF.getHeader()->e_ident[ELF::EI_CLASS]) {
856   case ELF::ELFCLASS32:
857     switch (EF.getHeader()->e_machine) {
858     case ELF::EM_386:
859       return "ELF32-i386";
860     case ELF::EM_X86_64:
861       return "ELF32-x86-64";
862     case ELF::EM_ARM:
863       return (IsLittleEndian ? "ELF32-arm-little" : "ELF32-arm-big");
864     case ELF::EM_HEXAGON:
865       return "ELF32-hexagon";
866     case ELF::EM_MIPS:
867       return "ELF32-mips";
868     case ELF::EM_PPC:
869       return "ELF32-ppc";
870     case ELF::EM_SPARC:
871     case ELF::EM_SPARC32PLUS:
872       return "ELF32-sparc";
873     default:
874       return "ELF32-unknown";
875     }
876   case ELF::ELFCLASS64:
877     switch (EF.getHeader()->e_machine) {
878     case ELF::EM_386:
879       return "ELF64-i386";
880     case ELF::EM_X86_64:
881       return "ELF64-x86-64";
882     case ELF::EM_AARCH64:
883       return (IsLittleEndian ? "ELF64-aarch64-little" : "ELF64-aarch64-big");
884     case ELF::EM_PPC64:
885       return "ELF64-ppc64";
886     case ELF::EM_S390:
887       return "ELF64-s390";
888     case ELF::EM_SPARCV9:
889       return "ELF64-sparc";
890     case ELF::EM_MIPS:
891       return "ELF64-mips";
892     default:
893       return "ELF64-unknown";
894     }
895   default:
896     // FIXME: Proper error handling.
897     report_fatal_error("Invalid ELFCLASS!");
898   }
899 }
900
901 template <class ELFT>
902 unsigned ELFObjectFile<ELFT>::getArch() const {
903   bool IsLittleEndian = ELFT::TargetEndianness == support::little;
904   switch (EF.getHeader()->e_machine) {
905   case ELF::EM_386:
906     return Triple::x86;
907   case ELF::EM_X86_64:
908     return Triple::x86_64;
909   case ELF::EM_AARCH64:
910     return Triple::aarch64;
911   case ELF::EM_ARM:
912     return Triple::arm;
913   case ELF::EM_HEXAGON:
914     return Triple::hexagon;
915   case ELF::EM_MIPS:
916     switch (EF.getHeader()->e_ident[ELF::EI_CLASS]) {
917     case ELF::ELFCLASS32:
918       return IsLittleEndian ? Triple::mipsel : Triple::mips;
919     case ELF::ELFCLASS64:
920       return IsLittleEndian ? Triple::mips64el : Triple::mips64;
921     default:
922       report_fatal_error("Invalid ELFCLASS!");
923     }
924   case ELF::EM_PPC:
925     return Triple::ppc;
926   case ELF::EM_PPC64:
927     return IsLittleEndian ? Triple::ppc64le : Triple::ppc64;
928   case ELF::EM_S390:
929     return Triple::systemz;
930
931   case ELF::EM_SPARC:
932   case ELF::EM_SPARC32PLUS:
933     return IsLittleEndian ? Triple::sparcel : Triple::sparc;
934   case ELF::EM_SPARCV9:
935     return Triple::sparcv9;
936
937   default:
938     return Triple::UnknownArch;
939   }
940 }
941
942 template <class ELFT>
943 ELFObjectFileBase::elf_symbol_iterator_range
944 ELFObjectFile<ELFT>::getDynamicSymbolIterators() const {
945   return make_range(dynamic_symbol_begin(), dynamic_symbol_end());
946 }
947
948 template <class ELFT> bool ELFObjectFile<ELFT>::isRelocatableObject() const {
949   return EF.getHeader()->e_type == ELF::ET_REL;
950 }
951
952 }
953 }
954
955 #endif