1 //===- InputSection.cpp ---------------------------------------------------===// 2 // 3 // The LLVM Linker 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #include "InputSection.h" 11 #include "Config.h" 12 #include "Error.h" 13 #include "InputFiles.h" 14 #include "OutputSections.h" 15 #include "Target.h" 16 17 using namespace llvm; 18 using namespace llvm::ELF; 19 using namespace llvm::object; 20 21 using namespace lld; 22 using namespace lld::elf2; 23 24 template <class ELFT> 25 InputSection<ELFT>::InputSection(ObjectFile<ELFT> *F, const Elf_Shdr *Header) 26 : File(F), Header(Header) {} 27 28 template <class ELFT> 29 void InputSection<ELFT>::relocateOne(uint8_t *Buf, uint8_t *BufEnd, 30 const Elf_Rel &Rel, uint32_t Type, 31 uintX_t BaseAddr, uintX_t SymVA) { 32 Target->relocateOne(Buf, BufEnd, reinterpret_cast<const void *>(&Rel), Type, 33 BaseAddr, SymVA); 34 } 35 36 template <class ELFT> 37 void InputSection<ELFT>::relocateOne(uint8_t *Buf, uint8_t *BufEnd, 38 const Elf_Rela &Rel, uint32_t Type, 39 uintX_t BaseAddr, uintX_t SymVA) { 40 Target->relocateOne(Buf, BufEnd, reinterpret_cast<const void *>(&Rel), Type, 41 BaseAddr, SymVA + Rel.r_addend); 42 } 43 44 template <class ELFT> 45 template <bool isRela> 46 void InputSection<ELFT>::relocate( 47 uint8_t *Buf, uint8_t *BufEnd, 48 iterator_range<const Elf_Rel_Impl<ELFT, isRela> *> Rels, 49 const ObjectFile<ELFT> &File, uintX_t BaseAddr) { 50 typedef Elf_Rel_Impl<ELFT, isRela> RelType; 51 bool IsMips64EL = File.getObj().isMips64EL(); 52 for (const RelType &RI : Rels) { 53 uint32_t SymIndex = RI.getSymbol(IsMips64EL); 54 uint32_t Type = RI.getType(IsMips64EL); 55 56 // Handle relocations for local symbols -- they never get 57 // resolved so we don't allocate a SymbolBody. 58 const Elf_Shdr *SymTab = File.getSymbolTable(); 59 if (SymIndex < SymTab->sh_info) { 60 uintX_t SymVA = getLocalRelTarget(File, RI); 61 relocateOne(Buf, BufEnd, RI, Type, BaseAddr, SymVA); 62 continue; 63 } 64 65 SymbolBody &Body = *File.getSymbolBody(SymIndex)->repl(); 66 uintX_t SymVA = getSymVA<ELFT>(Body); 67 if (Target->relocNeedsPlt(Type, Body)) { 68 SymVA = Out<ELFT>::Plt->getEntryAddr(Body); 69 Type = Target->getPLTRefReloc(Type); 70 } else if (Target->relocNeedsGot(Type, Body)) { 71 SymVA = Out<ELFT>::Got->getEntryAddr(Body); 72 Type = Target->getGotRefReloc(); 73 } else if (Target->relocPointsToGot(Type)) { 74 SymVA = Out<ELFT>::Got->getVA(); 75 Type = Target->getPCRelReloc(); 76 } else if (isa<SharedSymbol<ELFT>>(Body)) { 77 continue; 78 } 79 relocateOne(Buf, BufEnd, RI, Type, BaseAddr, SymVA); 80 } 81 } 82 83 template <class ELFT> void InputSection<ELFT>::writeTo(uint8_t *Buf) { 84 if (Header->sh_type == SHT_NOBITS) 85 return; 86 // Copy section contents from source object file to output file. 87 ArrayRef<uint8_t> Data = *File->getObj().getSectionContents(Header); 88 memcpy(Buf + OutSecOff, Data.data(), Data.size()); 89 90 ELFFile<ELFT> &EObj = File->getObj(); 91 uint8_t *Base = Buf + OutSecOff; 92 uintX_t BaseAddr = OutSec->getVA() + OutSecOff; 93 // Iterate over all relocation sections that apply to this section. 94 for (const Elf_Shdr *RelSec : RelocSections) { 95 if (RelSec->sh_type == SHT_RELA) 96 relocate(Base, Base + Data.size(), EObj.relas(RelSec), *File, BaseAddr); 97 else 98 relocate(Base, Base + Data.size(), EObj.rels(RelSec), *File, BaseAddr); 99 } 100 } 101 102 template <class ELFT> StringRef InputSection<ELFT>::getSectionName() const { 103 ErrorOr<StringRef> Name = File->getObj().getSectionName(Header); 104 error(Name); 105 return *Name; 106 } 107 108 namespace lld { 109 namespace elf2 { 110 template class InputSection<object::ELF32LE>; 111 template class InputSection<object::ELF32BE>; 112 template class InputSection<object::ELF64LE>; 113 template class InputSection<object::ELF64BE>; 114 } 115 } 116