1 //===- OutputSections.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 "OutputSections.h" 11 #include "Config.h" 12 #include "SymbolTable.h" 13 #include "Target.h" 14 15 using namespace llvm; 16 using namespace llvm::object; 17 using namespace llvm::ELF; 18 19 using namespace lld; 20 using namespace lld::elf2; 21 22 template <bool Is64Bits> 23 OutputSectionBase<Is64Bits>::OutputSectionBase(StringRef Name, uint32_t sh_type, 24 uintX_t sh_flags) 25 : Name(Name) { 26 memset(&Header, 0, sizeof(HeaderT)); 27 Header.sh_type = sh_type; 28 Header.sh_flags = sh_flags; 29 } 30 31 template <class ELFT> 32 GotSection<ELFT>::GotSection() 33 : OutputSectionBase<ELFT::Is64Bits>(".got", llvm::ELF::SHT_PROGBITS, 34 llvm::ELF::SHF_ALLOC | 35 llvm::ELF::SHF_WRITE) { 36 this->Header.sh_addralign = this->getAddrSize(); 37 } 38 39 template <class ELFT> void GotSection<ELFT>::addEntry(SymbolBody *Sym) { 40 Sym->setGotIndex(Entries.size()); 41 Entries.push_back(Sym); 42 } 43 44 template <class ELFT> 45 typename GotSection<ELFT>::uintX_t 46 GotSection<ELFT>::getEntryAddr(const SymbolBody &B) const { 47 return this->getVA() + B.getGotIndex() * this->getAddrSize(); 48 } 49 50 template <class ELFT> 51 PltSection<ELFT>::PltSection(const GotSection<ELFT> &GotSec) 52 : OutputSectionBase<ELFT::Is64Bits>(".plt", llvm::ELF::SHT_PROGBITS, 53 llvm::ELF::SHF_ALLOC | 54 llvm::ELF::SHF_EXECINSTR), 55 GotSec(GotSec) { 56 this->Header.sh_addralign = 16; 57 } 58 59 template <class ELFT> void PltSection<ELFT>::writeTo(uint8_t *Buf) { 60 uintptr_t Start = reinterpret_cast<uintptr_t>(Buf); 61 for (const SymbolBody *E : Entries) { 62 uint64_t GotEntryAddr = GotSec.getEntryAddr(*E); 63 uintptr_t InstPos = reinterpret_cast<uintptr_t>(Buf); 64 uint64_t PltEntryAddr = (InstPos - Start) + this->getVA(); 65 Target->writePltEntry(Buf, GotEntryAddr, PltEntryAddr); 66 Buf += 8; 67 } 68 } 69 70 template <class ELFT> void PltSection<ELFT>::addEntry(SymbolBody *Sym) { 71 Sym->setPltIndex(Entries.size()); 72 Entries.push_back(Sym); 73 } 74 75 template <class ELFT> 76 typename PltSection<ELFT>::uintX_t 77 PltSection<ELFT>::getEntryAddr(const SymbolBody &B) const { 78 return this->getVA() + B.getPltIndex() * EntrySize; 79 } 80 81 template <class ELFT> 82 RelocationSection<ELFT>::RelocationSection(SymbolTableSection<ELFT> &DynSymSec, 83 const GotSection<ELFT> &GotSec, 84 const OutputSection<ELFT> &BssSec, 85 bool IsRela) 86 : OutputSectionBase<ELFT::Is64Bits>(IsRela ? ".rela.dyn" : ".rel.dyn", 87 IsRela ? llvm::ELF::SHT_RELA 88 : llvm::ELF::SHT_REL, 89 llvm::ELF::SHF_ALLOC), 90 DynSymSec(DynSymSec), GotSec(GotSec), BssSec(BssSec), IsRela(IsRela) { 91 this->Header.sh_entsize = IsRela ? sizeof(Elf_Rela) : sizeof(Elf_Rel); 92 this->Header.sh_addralign = ELFT::Is64Bits ? 8 : 4; 93 } 94 95 template <class ELFT> void RelocationSection<ELFT>::writeTo(uint8_t *Buf) { 96 const unsigned EntrySize = IsRela ? sizeof(Elf_Rela) : sizeof(Elf_Rel); 97 bool IsMips64EL = Relocs[0].C.getFile()->getObj().isMips64EL(); 98 for (const DynamicReloc<ELFT> &Rel : Relocs) { 99 auto *P = reinterpret_cast<Elf_Rel *>(Buf); 100 Buf += EntrySize; 101 102 const InputSection<ELFT> &C = Rel.C; 103 const Elf_Rel &RI = Rel.RI; 104 OutputSection<ELFT> *Out = C.getOutputSection(); 105 uint32_t SymIndex = RI.getSymbol(IsMips64EL); 106 const ObjectFile<ELFT> &File = *C.getFile(); 107 const SymbolBody *Body = File.getSymbolBody(SymIndex); 108 const ELFFile<ELFT> &Obj = File.getObj(); 109 110 uint32_t Type = RI.getType(IsMips64EL); 111 if (Body && Target->relocNeedsGot(Type, *Body)) { 112 P->r_offset = GotSec.getEntryAddr(*Body); 113 P->setSymbolAndType(Body->getDynamicSymbolTableIndex(), 114 Target->getGotReloc(), IsMips64EL); 115 } else { 116 P->r_offset = RI.r_offset + C.getOutputSectionOff() + Out->getVA(); 117 uintX_t Addent = 0; 118 if (IsRela) 119 Addent = static_cast<const Elf_Rela &>(RI).r_addend; 120 121 if (Body && Body->isShared()) { 122 P->setSymbolAndType(Body->getDynamicSymbolTableIndex(), Type, 123 IsMips64EL); 124 } else { 125 P->setSymbolAndType(0, Target->getRelativeReloc(), IsMips64EL); 126 if (IsRela) { 127 if (Body) 128 Addent += getSymVA(cast<ELFSymbolBody<ELFT>>(*Body), BssSec); 129 else 130 Addent += getLocalSymVA( 131 Obj.getRelocationSymbol(&RI, File.getSymbolTable()), File); 132 } 133 } 134 if (IsRela) 135 static_cast<Elf_Rela *>(P)->r_addend = Addent; 136 } 137 } 138 } 139 140 template <class ELFT> void RelocationSection<ELFT>::finalize() { 141 this->Header.sh_link = DynSymSec.getSectionIndex(); 142 this->Header.sh_size = Relocs.size() * this->Header.sh_entsize; 143 } 144 145 template <bool Is64Bits> 146 InterpSection<Is64Bits>::InterpSection() 147 : OutputSectionBase<Is64Bits>(".interp", llvm::ELF::SHT_PROGBITS, 148 llvm::ELF::SHF_ALLOC) { 149 this->Header.sh_size = Config->DynamicLinker.size() + 1; 150 this->Header.sh_addralign = 1; 151 } 152 153 template <bool Is64Bits> 154 template <endianness E> 155 void OutputSectionBase<Is64Bits>::writeHeaderTo( 156 typename ELFFile<ELFType<E, Is64Bits>>::Elf_Shdr *SHdr) { 157 SHdr->sh_name = Header.sh_name; 158 SHdr->sh_type = Header.sh_type; 159 SHdr->sh_flags = Header.sh_flags; 160 SHdr->sh_addr = Header.sh_addr; 161 SHdr->sh_offset = Header.sh_offset; 162 SHdr->sh_size = Header.sh_size; 163 SHdr->sh_link = Header.sh_link; 164 SHdr->sh_info = Header.sh_info; 165 SHdr->sh_addralign = Header.sh_addralign; 166 SHdr->sh_entsize = Header.sh_entsize; 167 } 168 169 template <bool Is64Bits> void InterpSection<Is64Bits>::writeTo(uint8_t *Buf) { 170 memcpy(Buf, Config->DynamicLinker.data(), Config->DynamicLinker.size()); 171 } 172 173 template <class ELFT> 174 HashTableSection<ELFT>::HashTableSection(SymbolTableSection<ELFT> &DynSymSec) 175 : OutputSectionBase<ELFT::Is64Bits>(".hash", llvm::ELF::SHT_HASH, 176 llvm::ELF::SHF_ALLOC), 177 DynSymSec(DynSymSec) { 178 this->Header.sh_entsize = sizeof(Elf_Word); 179 this->Header.sh_addralign = sizeof(Elf_Word); 180 } 181 182 template <class ELFT> void HashTableSection<ELFT>::addSymbol(SymbolBody *S) { 183 StringRef Name = S->getName(); 184 DynSymSec.addSymbol(Name); 185 Hashes.push_back(hash(Name)); 186 S->setDynamicSymbolTableIndex(Hashes.size()); 187 } 188 189 template <class ELFT> 190 DynamicSection<ELFT>::DynamicSection(SymbolTable &SymTab, 191 HashTableSection<ELFT> &HashSec, 192 RelocationSection<ELFT> &RelaDynSec, 193 const OutputSection<ELFT> &BssSec) 194 : OutputSectionBase<ELFT::Is64Bits>(".dynamic", llvm::ELF::SHT_DYNAMIC, 195 llvm::ELF::SHF_ALLOC | 196 llvm::ELF::SHF_WRITE), 197 HashSec(HashSec), DynSymSec(HashSec.getDynSymSec()), 198 DynStrSec(DynSymSec.getStrTabSec()), RelaDynSec(RelaDynSec), 199 BssSec(BssSec), SymTab(SymTab) { 200 typename Base::HeaderT &Header = this->Header; 201 Header.sh_addralign = ELFT::Is64Bits ? 8 : 4; 202 Header.sh_entsize = ELFT::Is64Bits ? 16 : 8; 203 } 204 205 template <class ELFT> void DynamicSection<ELFT>::finalize() { 206 if (this->Header.sh_size) 207 return; // Already finalized. 208 209 typename Base::HeaderT &Header = this->Header; 210 Header.sh_link = DynStrSec.getSectionIndex(); 211 212 unsigned NumEntries = 0; 213 if (RelaDynSec.hasRelocs()) { 214 ++NumEntries; // DT_RELA / DT_REL 215 ++NumEntries; // DT_RELASZ / DT_RELSZ 216 ++NumEntries; // DT_RELAENT / DT_RELENT 217 } 218 ++NumEntries; // DT_SYMTAB 219 ++NumEntries; // DT_SYMENT 220 ++NumEntries; // DT_STRTAB 221 ++NumEntries; // DT_STRSZ 222 ++NumEntries; // DT_HASH 223 224 if (!Config->RPath.empty()) { 225 ++NumEntries; // DT_RUNPATH 226 DynStrSec.add(Config->RPath); 227 } 228 229 if (!Config->SoName.empty()) { 230 ++NumEntries; // DT_SONAME 231 DynStrSec.add(Config->SoName); 232 } 233 234 if (PreInitArraySec) 235 NumEntries += 2; 236 if (InitArraySec) 237 NumEntries += 2; 238 if (FiniArraySec) 239 NumEntries += 2; 240 241 const std::vector<std::unique_ptr<SharedFileBase>> &SharedFiles = 242 SymTab.getSharedFiles(); 243 for (const std::unique_ptr<SharedFileBase> &File : SharedFiles) 244 DynStrSec.add(File->getSoName()); 245 NumEntries += SharedFiles.size(); 246 247 if (Symbol *S = SymTab.getSymbols().lookup(Config->Init)) 248 InitSym = dyn_cast<ELFSymbolBody<ELFT>>(S->Body); 249 if (Symbol *S = SymTab.getSymbols().lookup(Config->Fini)) 250 FiniSym = dyn_cast<ELFSymbolBody<ELFT>>(S->Body); 251 if (InitSym) 252 ++NumEntries; // DT_INIT 253 if (FiniSym) 254 ++NumEntries; // DT_FINI 255 256 ++NumEntries; // DT_NULL 257 258 Header.sh_size = NumEntries * Header.sh_entsize; 259 } 260 261 template <class ELFT> void DynamicSection<ELFT>::writeTo(uint8_t *Buf) { 262 auto *P = reinterpret_cast<Elf_Dyn *>(Buf); 263 264 auto WritePtr = [&](int32_t Tag, uint64_t Val) { 265 P->d_tag = Tag; 266 P->d_un.d_ptr = Val; 267 ++P; 268 }; 269 270 auto WriteVal = [&](int32_t Tag, uint32_t Val) { 271 P->d_tag = Tag; 272 P->d_un.d_val = Val; 273 ++P; 274 }; 275 276 if (RelaDynSec.hasRelocs()) { 277 bool IsRela = RelaDynSec.isRela(); 278 WritePtr(IsRela ? DT_RELA : DT_REL, RelaDynSec.getVA()); 279 WriteVal(IsRela ? DT_RELASZ : DT_RELSZ, RelaDynSec.getSize()); 280 WriteVal(IsRela ? DT_RELAENT : DT_RELENT, 281 IsRela ? sizeof(Elf_Rela) : sizeof(Elf_Rel)); 282 } 283 284 WritePtr(DT_SYMTAB, DynSymSec.getVA()); 285 WritePtr(DT_SYMENT, sizeof(Elf_Sym)); 286 WritePtr(DT_STRTAB, DynStrSec.getVA()); 287 WriteVal(DT_STRSZ, DynStrSec.data().size()); 288 WritePtr(DT_HASH, HashSec.getVA()); 289 290 if (!Config->RPath.empty()) 291 WriteVal(DT_RUNPATH, DynStrSec.getFileOff(Config->RPath)); 292 293 if (!Config->SoName.empty()) 294 WriteVal(DT_SONAME, DynStrSec.getFileOff(Config->SoName)); 295 296 auto WriteArray = [&](int32_t T1, int32_t T2, 297 const OutputSection<ELFT> *Sec) { 298 if (!Sec) 299 return; 300 WritePtr(T1, Sec->getVA()); 301 WriteVal(T2, Sec->getSize()); 302 }; 303 WriteArray(DT_PREINIT_ARRAY, DT_PREINIT_ARRAYSZ, PreInitArraySec); 304 WriteArray(DT_INIT_ARRAY, DT_INIT_ARRAYSZ, InitArraySec); 305 WriteArray(DT_FINI_ARRAY, DT_FINI_ARRAYSZ, FiniArraySec); 306 307 const std::vector<std::unique_ptr<SharedFileBase>> &SharedFiles = 308 SymTab.getSharedFiles(); 309 for (const std::unique_ptr<SharedFileBase> &File : SharedFiles) 310 WriteVal(DT_NEEDED, DynStrSec.getFileOff(File->getSoName())); 311 312 if (InitSym) 313 WritePtr(DT_INIT, getSymVA(*InitSym, BssSec)); 314 if (FiniSym) 315 WritePtr(DT_FINI, getSymVA(*FiniSym, BssSec)); 316 317 WriteVal(DT_NULL, 0); 318 } 319 320 template <class ELFT> 321 OutputSection<ELFT>::OutputSection(const PltSection<ELFT> &PltSec, 322 const GotSection<ELFT> &GotSec, 323 const OutputSection<ELFT> &BssSec, 324 StringRef Name, uint32_t sh_type, 325 uintX_t sh_flags) 326 : OutputSectionBase<ELFT::Is64Bits>(Name, sh_type, sh_flags), 327 PltSec(PltSec), GotSec(GotSec), BssSec(BssSec) {} 328 329 template <class ELFT> 330 void OutputSection<ELFT>::addSection(InputSection<ELFT> *C) { 331 Sections.push_back(C); 332 C->setOutputSection(this); 333 uint32_t Align = C->getAlign(); 334 if (Align > this->Header.sh_addralign) 335 this->Header.sh_addralign = Align; 336 337 uintX_t Off = this->Header.sh_size; 338 Off = RoundUpToAlignment(Off, Align); 339 C->setOutputSectionOff(Off); 340 Off += C->getSize(); 341 this->Header.sh_size = Off; 342 } 343 344 template <class ELFT> 345 typename ELFFile<ELFT>::uintX_t 346 lld::elf2::getSymVA(const ELFSymbolBody<ELFT> &S, 347 const OutputSection<ELFT> &BssSec) { 348 switch (S.kind()) { 349 case SymbolBody::DefinedSyntheticKind: 350 return cast<DefinedSynthetic<ELFT>>(S).Section.getVA() + S.Sym.st_value; 351 case SymbolBody::DefinedAbsoluteKind: 352 return S.Sym.st_value; 353 case SymbolBody::DefinedRegularKind: { 354 const auto &DR = cast<DefinedRegular<ELFT>>(S); 355 const InputSection<ELFT> *SC = &DR.Section; 356 OutputSection<ELFT> *OS = SC->getOutputSection(); 357 return OS->getVA() + SC->getOutputSectionOff() + DR.Sym.st_value; 358 } 359 case SymbolBody::DefinedCommonKind: 360 return BssSec.getVA() + cast<DefinedCommon<ELFT>>(S).OffsetInBSS; 361 case SymbolBody::SharedKind: 362 case SymbolBody::UndefinedKind: 363 return 0; 364 case SymbolBody::LazyKind: 365 break; 366 } 367 llvm_unreachable("Lazy symbol reached writer"); 368 } 369 370 template <class ELFT> 371 typename ELFFile<ELFT>::uintX_t 372 lld::elf2::getLocalSymVA(const typename ELFFile<ELFT>::Elf_Sym *Sym, 373 const ObjectFile<ELFT> &File) { 374 uint32_t SecIndex = Sym->st_shndx; 375 376 if (SecIndex == SHN_XINDEX) 377 SecIndex = File.getObj().getExtendedSymbolTableIndex( 378 Sym, File.getSymbolTable(), File.getSymbolTableShndx()); 379 ArrayRef<InputSection<ELFT> *> Sections = File.getSections(); 380 InputSection<ELFT> *Section = Sections[SecIndex]; 381 OutputSection<ELFT> *Out = Section->getOutputSection(); 382 return Out->getVA() + Section->getOutputSectionOff() + Sym->st_value; 383 } 384 385 template <class ELFT> void OutputSection<ELFT>::writeTo(uint8_t *Buf) { 386 for (InputSection<ELFT> *C : Sections) 387 C->writeTo(Buf, BssSec, PltSec, GotSec); 388 } 389 390 template <bool Is64Bits> 391 StringTableSection<Is64Bits>::StringTableSection(bool Dynamic) 392 : OutputSectionBase<Is64Bits>(Dynamic ? ".dynstr" : ".strtab", 393 llvm::ELF::SHT_STRTAB, 394 Dynamic ? (uintX_t)llvm::ELF::SHF_ALLOC : 0), 395 Dynamic(Dynamic) { 396 this->Header.sh_addralign = 1; 397 } 398 399 template <bool Is64Bits> 400 void StringTableSection<Is64Bits>::writeTo(uint8_t *Buf) { 401 StringRef Data = StrTabBuilder.data(); 402 memcpy(Buf, Data.data(), Data.size()); 403 } 404 405 template <class ELFT> bool lld::elf2::includeInSymtab(const SymbolBody &B) { 406 if (B.isLazy()) 407 return false; 408 if (!B.isUsedInRegularObj()) 409 return false; 410 411 // Don't include synthetic symbols like __init_array_start in every output. 412 if (auto *U = dyn_cast<DefinedAbsolute<ELFT>>(&B)) 413 if (&U->Sym == &DefinedAbsolute<ELFT>::IgnoreUndef) 414 return false; 415 416 return true; 417 } 418 419 bool lld::elf2::includeInDynamicSymtab(const SymbolBody &B) { 420 uint8_t V = B.getMostConstrainingVisibility(); 421 if (V != STV_DEFAULT && V != STV_PROTECTED) 422 return false; 423 424 if (Config->ExportDynamic || Config->Shared) 425 return true; 426 return B.isUsedInDynamicReloc(); 427 } 428 429 template <class ELFT> 430 bool lld::elf2::shouldKeepInSymtab(StringRef SymName, 431 const typename ELFFile<ELFT>::Elf_Sym &Sym) { 432 if (Sym.getType() == STT_SECTION) 433 return false; 434 435 if (Config->DiscardNone) 436 return true; 437 438 // ELF defines dynamic locals as symbols which name starts with ".L". 439 return !(Config->DiscardLocals && SymName.startswith(".L")); 440 } 441 442 template <class ELFT> 443 SymbolTableSection<ELFT>::SymbolTableSection( 444 SymbolTable &Table, StringTableSection<ELFT::Is64Bits> &StrTabSec, 445 const OutputSection<ELFT> &BssSec) 446 : OutputSectionBase<ELFT::Is64Bits>( 447 StrTabSec.isDynamic() ? ".dynsym" : ".symtab", 448 StrTabSec.isDynamic() ? llvm::ELF::SHT_DYNSYM : llvm::ELF::SHT_SYMTAB, 449 StrTabSec.isDynamic() ? (uintX_t)llvm::ELF::SHF_ALLOC : 0), 450 Table(Table), StrTabSec(StrTabSec), BssSec(BssSec) { 451 typedef OutputSectionBase<ELFT::Is64Bits> Base; 452 typename Base::HeaderT &Header = this->Header; 453 454 Header.sh_entsize = sizeof(Elf_Sym); 455 Header.sh_addralign = ELFT::Is64Bits ? 8 : 4; 456 } 457 458 template <class ELFT> void SymbolTableSection<ELFT>::writeTo(uint8_t *Buf) { 459 Buf += sizeof(Elf_Sym); 460 461 // All symbols with STB_LOCAL binding precede the weak and global symbols. 462 // .dynsym only contains global symbols. 463 if (!Config->DiscardAll && !StrTabSec.isDynamic()) 464 writeLocalSymbols(Buf); 465 466 writeGlobalSymbols(Buf); 467 } 468 469 template <class ELFT> 470 void SymbolTableSection<ELFT>::writeLocalSymbols(uint8_t *&Buf) { 471 // Iterate over all input object files to copy their local symbols 472 // to the output symbol table pointed by Buf. 473 for (const std::unique_ptr<ObjectFileBase> &FileB : Table.getObjectFiles()) { 474 auto &File = cast<ObjectFile<ELFT>>(*FileB); 475 Elf_Sym_Range Syms = File.getLocalSymbols(); 476 for (const Elf_Sym &Sym : Syms) { 477 ErrorOr<StringRef> SymName = Sym.getName(File.getStringTable()); 478 if (SymName && !shouldKeepInSymtab<ELFT>(*SymName, Sym)) 479 continue; 480 auto *ESym = reinterpret_cast<Elf_Sym *>(Buf); 481 Buf += sizeof(*ESym); 482 ESym->st_name = (SymName) ? StrTabSec.getFileOff(*SymName) : 0; 483 ESym->st_size = Sym.st_size; 484 ESym->setBindingAndType(Sym.getBinding(), Sym.getType()); 485 uint32_t SecIndex = Sym.st_shndx; 486 uintX_t VA = Sym.st_value; 487 if (SecIndex == SHN_ABS) { 488 ESym->st_shndx = SHN_ABS; 489 } else { 490 if (SecIndex == SHN_XINDEX) 491 SecIndex = File.getObj().getExtendedSymbolTableIndex( 492 &Sym, File.getSymbolTable(), File.getSymbolTableShndx()); 493 ArrayRef<InputSection<ELFT> *> Sections = File.getSections(); 494 const InputSection<ELFT> *Section = Sections[SecIndex]; 495 const OutputSection<ELFT> *Out = Section->getOutputSection(); 496 ESym->st_shndx = Out->getSectionIndex(); 497 VA += Out->getVA() + Section->getOutputSectionOff(); 498 } 499 ESym->st_value = VA; 500 } 501 } 502 } 503 504 template <class ELFT> 505 void SymbolTableSection<ELFT>::writeGlobalSymbols(uint8_t *&Buf) { 506 // Write the internal symbol table contents to the output symbol table 507 // pointed by Buf. 508 uint8_t *Start = Buf; 509 for (const std::pair<StringRef, Symbol *> &P : Table.getSymbols()) { 510 StringRef Name = P.first; 511 Symbol *Sym = P.second; 512 SymbolBody *Body = Sym->Body; 513 if (!includeInSymtab<ELFT>(*Body)) 514 continue; 515 if (StrTabSec.isDynamic() && !includeInDynamicSymtab(*Body)) 516 continue; 517 518 const auto &EBody = *cast<ELFSymbolBody<ELFT>>(Body); 519 const Elf_Sym &InputSym = EBody.Sym; 520 auto *ESym = reinterpret_cast<Elf_Sym *>(Buf); 521 Buf += sizeof(*ESym); 522 ESym->st_name = StrTabSec.getFileOff(Name); 523 524 const OutputSection<ELFT> *Out = nullptr; 525 const InputSection<ELFT> *Section = nullptr; 526 527 switch (EBody.kind()) { 528 case SymbolBody::DefinedSyntheticKind: 529 Out = &cast<DefinedSynthetic<ELFT>>(Body)->Section; 530 break; 531 case SymbolBody::DefinedRegularKind: 532 Section = &cast<DefinedRegular<ELFT>>(EBody).Section; 533 break; 534 case SymbolBody::DefinedCommonKind: 535 Out = &BssSec; 536 break; 537 case SymbolBody::UndefinedKind: 538 case SymbolBody::DefinedAbsoluteKind: 539 case SymbolBody::SharedKind: 540 break; 541 case SymbolBody::LazyKind: 542 llvm_unreachable("Lazy symbol got to output symbol table!"); 543 } 544 545 unsigned char Binding = InputSym.getBinding(); 546 unsigned char Visibility = EBody.getMostConstrainingVisibility(); 547 if (Visibility != STV_DEFAULT && Visibility != STV_PROTECTED) 548 Binding = STB_LOCAL; 549 550 ESym->setBindingAndType(Binding, InputSym.getType()); 551 ESym->st_size = InputSym.st_size; 552 ESym->setVisibility(Visibility); 553 if (InputSym.isAbsolute()) { 554 ESym->st_shndx = SHN_ABS; 555 ESym->st_value = InputSym.st_value; 556 } 557 558 if (Section) 559 Out = Section->getOutputSection(); 560 561 ESym->st_value = getSymVA(EBody, BssSec); 562 563 if (Out) 564 ESym->st_shndx = Out->getSectionIndex(); 565 } 566 if (!StrTabSec.isDynamic()) 567 std::stable_sort( 568 reinterpret_cast<Elf_Sym *>(Start), reinterpret_cast<Elf_Sym *>(Buf), 569 [](const Elf_Sym &A, const Elf_Sym &B) -> bool { 570 return A.getBinding() == STB_LOCAL && B.getBinding() != STB_LOCAL; 571 }); 572 } 573 574 namespace lld { 575 namespace elf2 { 576 template class OutputSectionBase<false>; 577 template class OutputSectionBase<true>; 578 579 template void OutputSectionBase<false>::writeHeaderTo<support::little>( 580 ELFFile<ELFType<support::little, false>>::Elf_Shdr *SHdr); 581 template void OutputSectionBase<true>::writeHeaderTo<support::little>( 582 ELFFile<ELFType<support::little, true>>::Elf_Shdr *SHdr); 583 template void OutputSectionBase<false>::writeHeaderTo<support::big>( 584 ELFFile<ELFType<support::big, false>>::Elf_Shdr *SHdr); 585 template void OutputSectionBase<true>::writeHeaderTo<support::big>( 586 ELFFile<ELFType<support::big, true>>::Elf_Shdr *SHdr); 587 588 template class GotSection<ELF32LE>; 589 template class GotSection<ELF32BE>; 590 template class GotSection<ELF64LE>; 591 template class GotSection<ELF64BE>; 592 593 template class PltSection<ELF32LE>; 594 template class PltSection<ELF32BE>; 595 template class PltSection<ELF64LE>; 596 template class PltSection<ELF64BE>; 597 598 template class RelocationSection<ELF32LE>; 599 template class RelocationSection<ELF32BE>; 600 template class RelocationSection<ELF64LE>; 601 template class RelocationSection<ELF64BE>; 602 603 template class InterpSection<false>; 604 template class InterpSection<true>; 605 606 template class HashTableSection<ELF32LE>; 607 template class HashTableSection<ELF32BE>; 608 template class HashTableSection<ELF64LE>; 609 template class HashTableSection<ELF64BE>; 610 611 template class DynamicSection<ELF32LE>; 612 template class DynamicSection<ELF32BE>; 613 template class DynamicSection<ELF64LE>; 614 template class DynamicSection<ELF64BE>; 615 616 template class OutputSection<ELF32LE>; 617 template class OutputSection<ELF32BE>; 618 template class OutputSection<ELF64LE>; 619 template class OutputSection<ELF64BE>; 620 621 template class StringTableSection<false>; 622 template class StringTableSection<true>; 623 624 template class SymbolTableSection<ELF32LE>; 625 template class SymbolTableSection<ELF32BE>; 626 template class SymbolTableSection<ELF64LE>; 627 template class SymbolTableSection<ELF64BE>; 628 629 template ELFFile<ELF32LE>::uintX_t 630 getSymVA(const ELFSymbolBody<ELF32LE> &, const OutputSection<ELF32LE> &); 631 632 template ELFFile<ELF32BE>::uintX_t 633 getSymVA(const ELFSymbolBody<ELF32BE> &, const OutputSection<ELF32BE> &); 634 635 template ELFFile<ELF64LE>::uintX_t 636 getSymVA(const ELFSymbolBody<ELF64LE> &, const OutputSection<ELF64LE> &); 637 638 template ELFFile<ELF64BE>::uintX_t 639 getSymVA(const ELFSymbolBody<ELF64BE> &, const OutputSection<ELF64BE> &); 640 641 template ELFFile<ELF32LE>::uintX_t 642 getLocalSymVA(const ELFFile<ELF32LE>::Elf_Sym *, const ObjectFile<ELF32LE> &); 643 644 template ELFFile<ELF32BE>::uintX_t 645 getLocalSymVA(const ELFFile<ELF32BE>::Elf_Sym *, const ObjectFile<ELF32BE> &); 646 647 template ELFFile<ELF64LE>::uintX_t 648 getLocalSymVA(const ELFFile<ELF64LE>::Elf_Sym *, const ObjectFile<ELF64LE> &); 649 650 template ELFFile<ELF64BE>::uintX_t 651 getLocalSymVA(const ELFFile<ELF64BE>::Elf_Sym *, const ObjectFile<ELF64BE> &); 652 653 template bool includeInSymtab<ELF32LE>(const SymbolBody &); 654 template bool includeInSymtab<ELF32BE>(const SymbolBody &); 655 template bool includeInSymtab<ELF64LE>(const SymbolBody &); 656 template bool includeInSymtab<ELF64BE>(const SymbolBody &); 657 658 template bool shouldKeepInSymtab<ELF32LE>(StringRef, 659 const ELFFile<ELF32LE>::Elf_Sym &); 660 template bool shouldKeepInSymtab<ELF32BE>(StringRef, 661 const ELFFile<ELF32BE>::Elf_Sym &); 662 template bool shouldKeepInSymtab<ELF64LE>(StringRef, 663 const ELFFile<ELF64LE>::Elf_Sym &); 664 template bool shouldKeepInSymtab<ELF64BE>(StringRef, 665 const ELFFile<ELF64BE>::Elf_Sym &); 666 } 667 } 668