xref: /llvm-project-15.0.7/lld/ELF/Symbols.cpp (revision fcef3e46)
1 //===- Symbols.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 "Symbols.h"
11 #include "Error.h"
12 #include "InputFiles.h"
13 #include "InputSection.h"
14 #include "OutputSections.h"
15 #include "Target.h"
16 
17 #include "llvm/ADT/STLExtras.h"
18 #include "llvm/Config/config.h"
19 
20 #ifdef HAVE_CXXABI_H
21 #include <cxxabi.h>
22 #endif
23 
24 using namespace llvm;
25 using namespace llvm::object;
26 using namespace llvm::ELF;
27 
28 using namespace lld;
29 using namespace lld::elf;
30 
31 template <class ELFT>
32 static typename ELFT::uint getSymVA(const SymbolBody &Body,
33                                     typename ELFT::uint &Addend) {
34   typedef typename ELFT::Sym Elf_Sym;
35   typedef typename ELFT::uint uintX_t;
36 
37   switch (Body.kind()) {
38   case SymbolBody::DefinedSyntheticKind: {
39     auto &D = cast<DefinedSynthetic<ELFT>>(Body);
40     return D.Section.getVA() + D.Value;
41   }
42   case SymbolBody::DefinedRegularKind: {
43     auto &D = cast<DefinedRegular<ELFT>>(Body);
44     InputSectionBase<ELFT> *SC = D.Section;
45 
46     // This is an absolute symbol.
47     if (!SC)
48       return D.Sym.st_value;
49 
50     const Elf_Sym &Sym = D.Sym;
51     uintX_t Offset = Sym.st_value;
52     if (Sym.getType() == STT_SECTION) {
53       Offset += Addend;
54       Addend = 0;
55     }
56     uintX_t VA = SC->OutSec->getVA() + SC->getOffset(Offset);
57     if (Sym.getType() == STT_TLS)
58       return VA - Out<ELFT>::TlsPhdr->p_vaddr;
59     return VA;
60   }
61   case SymbolBody::DefinedCommonKind:
62     return Out<ELFT>::Bss->getVA() + cast<DefinedCommon>(Body).OffsetInBss;
63   case SymbolBody::SharedKind: {
64     auto &SS = cast<SharedSymbol<ELFT>>(Body);
65     if (!SS.NeedsCopyOrPltAddr)
66       return 0;
67     if (SS.IsFunc)
68       return Body.getPltVA<ELFT>();
69     return Out<ELFT>::Bss->getVA() + SS.OffsetInBss;
70   }
71   case SymbolBody::UndefinedElfKind:
72   case SymbolBody::UndefinedKind:
73     return 0;
74   case SymbolBody::LazyKind:
75     assert(Body.isUsedInRegularObj() && "lazy symbol reached writer");
76     return 0;
77   case SymbolBody::DefinedBitcodeKind:
78     llvm_unreachable("should have been replaced");
79   }
80   llvm_unreachable("invalid symbol kind");
81 }
82 
83 // Returns true if a symbol can be replaced at load-time by a symbol
84 // with the same name defined in other ELF executable or DSO.
85 bool SymbolBody::isPreemptible() const {
86   if (isLocal())
87     return false;
88 
89   if (isShared())
90     return true;
91 
92   if (isUndefined()) {
93     if (!isWeak())
94       return true;
95 
96     // Ideally the static linker should see a definition for every symbol, but
97     // shared object are normally allowed to have undefined references that the
98     // static linker never sees a definition for.
99     if (Config->Shared)
100       return true;
101 
102     // Otherwise, just resolve to 0.
103     return false;
104   }
105 
106   if (!Config->Shared)
107     return false;
108   if (getVisibility() != STV_DEFAULT)
109     return false;
110   if (Config->Bsymbolic || (Config->BsymbolicFunctions && IsFunc))
111     return false;
112   return true;
113 }
114 
115 template <class ELFT>
116 typename ELFT::uint SymbolBody::getVA(typename ELFT::uint Addend) const {
117   typename ELFT::uint OutVA = getSymVA<ELFT>(*this, Addend);
118   return OutVA + Addend;
119 }
120 
121 template <class ELFT> typename ELFT::uint SymbolBody::getGotVA() const {
122   return Out<ELFT>::Got->getVA() +
123          (Out<ELFT>::Got->getMipsLocalEntriesNum() + GotIndex) *
124              sizeof(typename ELFT::uint);
125 }
126 
127 template <class ELFT> typename ELFT::uint SymbolBody::getGotPltVA() const {
128   return Out<ELFT>::GotPlt->getVA() + GotPltIndex * sizeof(typename ELFT::uint);
129 }
130 
131 template <class ELFT> typename ELFT::uint SymbolBody::getPltVA() const {
132   return Out<ELFT>::Plt->getVA() + Target->PltZeroSize +
133          PltIndex * Target->PltEntrySize;
134 }
135 
136 template <class ELFT> typename ELFT::uint SymbolBody::getSize() const {
137   if (auto *B = dyn_cast<DefinedElf<ELFT>>(this))
138     return B->Sym.st_size;
139   return 0;
140 }
141 
142 static uint8_t getMinVisibility(uint8_t VA, uint8_t VB) {
143   if (VA == STV_DEFAULT)
144     return VB;
145   if (VB == STV_DEFAULT)
146     return VA;
147   return std::min(VA, VB);
148 }
149 
150 static int compareCommons(DefinedCommon *A, DefinedCommon *B) {
151   if (Config->WarnCommon)
152     warning("multiple common of " + A->getName());
153   A->Alignment = B->Alignment = std::max(A->Alignment, B->Alignment);
154   return A->Size < B->Size ? -1 : 1;
155 }
156 
157 // Returns 1, 0 or -1 if this symbol should take precedence
158 // over the Other, tie or lose, respectively.
159 template <class ELFT> int SymbolBody::compare(SymbolBody *Other) {
160   assert(!isLazy() && !Other->isLazy());
161   std::tuple<bool, bool, bool> L(isDefined(), !isShared(), !isWeak());
162   std::tuple<bool, bool, bool> R(Other->isDefined(), !Other->isShared(),
163                                  !Other->isWeak());
164 
165   // Normalize
166   if (L > R)
167     return -Other->compare<ELFT>(this);
168 
169   Visibility = Other->Visibility =
170       getMinVisibility(Visibility, Other->Visibility);
171 
172   if (IsUsedInRegularObj || Other->IsUsedInRegularObj)
173     IsUsedInRegularObj = Other->IsUsedInRegularObj = true;
174 
175   // We want to export all symbols that exist both in the executable
176   // and in DSOs, so that the symbols in the executable can interrupt
177   // symbols in the DSO at runtime.
178   if (isShared() != Other->isShared())
179     if (isa<DefinedRegular<ELFT>>(isShared() ? Other : this))
180       MustBeInDynSym = Other->MustBeInDynSym = true;
181 
182   if (L != R)
183     return -1;
184   if (!isDefined() || isShared() || isWeak())
185     return 1;
186   if (!isCommon() && !Other->isCommon())
187     return 0;
188   if (isCommon() && Other->isCommon())
189     return compareCommons(cast<DefinedCommon>(this),
190                           cast<DefinedCommon>(Other));
191   if (Config->WarnCommon)
192     warning("common " + this->getName() + " is overridden");
193   return isCommon() ? -1 : 1;
194 }
195 
196 Defined::Defined(Kind K, StringRef Name, bool IsWeak, bool IsLocal,
197                  uint8_t Visibility, uint8_t Type)
198     : SymbolBody(K, Name, IsWeak, IsLocal, Visibility, Type) {}
199 
200 DefinedBitcode::DefinedBitcode(StringRef Name, bool IsWeak, uint8_t Visibility)
201     : Defined(DefinedBitcodeKind, Name, IsWeak, false, Visibility,
202               0 /* Type */) {}
203 
204 bool DefinedBitcode::classof(const SymbolBody *S) {
205   return S->kind() == DefinedBitcodeKind;
206 }
207 
208 Undefined::Undefined(SymbolBody::Kind K, StringRef N, bool IsWeak,
209                      uint8_t Visibility, uint8_t Type)
210     : SymbolBody(K, N, IsWeak, false, Visibility, Type),
211       CanKeepUndefined(false) {}
212 
213 Undefined::Undefined(StringRef N, bool IsWeak, uint8_t Visibility,
214                      bool CanKeepUndefined)
215     : Undefined(SymbolBody::UndefinedKind, N, IsWeak, Visibility, 0 /* Type */) {
216   this->CanKeepUndefined = CanKeepUndefined;
217 }
218 
219 template <typename ELFT>
220 UndefinedElf<ELFT>::UndefinedElf(StringRef N, const Elf_Sym &Sym)
221     : Undefined(SymbolBody::UndefinedElfKind, N,
222                 Sym.getBinding() == llvm::ELF::STB_WEAK, Sym.getVisibility(),
223                 Sym.getType()),
224       Sym(Sym) {}
225 
226 template <typename ELFT>
227 DefinedSynthetic<ELFT>::DefinedSynthetic(StringRef N, uintX_t Value,
228                                          OutputSectionBase<ELFT> &Section,
229                                          uint8_t Visibility)
230     : Defined(SymbolBody::DefinedSyntheticKind, N, false, false, Visibility,
231               0 /* Type */),
232       Value(Value), Section(Section) {}
233 
234 DefinedCommon::DefinedCommon(StringRef N, uint64_t Size, uint64_t Alignment,
235                              bool IsWeak, uint8_t Visibility)
236     : Defined(SymbolBody::DefinedCommonKind, N, IsWeak, false, Visibility,
237               0 /* Type */),
238       Alignment(Alignment), Size(Size) {}
239 
240 std::unique_ptr<InputFile> Lazy::getMember() {
241   MemoryBufferRef MBRef = File->getMember(&Sym);
242 
243   // getMember returns an empty buffer if the member was already
244   // read from the library.
245   if (MBRef.getBuffer().empty())
246     return std::unique_ptr<InputFile>(nullptr);
247   return createObjectFile(MBRef, File->getName());
248 }
249 
250 // Returns the demangled C++ symbol name for Name.
251 std::string elf::demangle(StringRef Name) {
252 #if !defined(HAVE_CXXABI_H)
253   return Name;
254 #else
255   if (!Config->Demangle)
256     return Name;
257 
258   // __cxa_demangle can be used to demangle strings other than symbol
259   // names which do not necessarily start with "_Z". Name can be
260   // either a C or C++ symbol. Don't call __cxa_demangle if the name
261   // does not look like a C++ symbol name to avoid getting unexpected
262   // result for a C symbol that happens to match a mangled type name.
263   if (!Name.startswith("_Z"))
264     return Name;
265 
266   char *Buf =
267       abi::__cxa_demangle(Name.str().c_str(), nullptr, nullptr, nullptr);
268   if (!Buf)
269     return Name;
270   std::string S(Buf);
271   free(Buf);
272   return S;
273 #endif
274 }
275 
276 template uint32_t SymbolBody::template getVA<ELF32LE>(uint32_t) const;
277 template uint32_t SymbolBody::template getVA<ELF32BE>(uint32_t) const;
278 template uint64_t SymbolBody::template getVA<ELF64LE>(uint64_t) const;
279 template uint64_t SymbolBody::template getVA<ELF64BE>(uint64_t) const;
280 
281 template uint32_t SymbolBody::template getGotVA<ELF32LE>() const;
282 template uint32_t SymbolBody::template getGotVA<ELF32BE>() const;
283 template uint64_t SymbolBody::template getGotVA<ELF64LE>() const;
284 template uint64_t SymbolBody::template getGotVA<ELF64BE>() const;
285 
286 template uint32_t SymbolBody::template getGotPltVA<ELF32LE>() const;
287 template uint32_t SymbolBody::template getGotPltVA<ELF32BE>() const;
288 template uint64_t SymbolBody::template getGotPltVA<ELF64LE>() const;
289 template uint64_t SymbolBody::template getGotPltVA<ELF64BE>() const;
290 
291 template uint32_t SymbolBody::template getPltVA<ELF32LE>() const;
292 template uint32_t SymbolBody::template getPltVA<ELF32BE>() const;
293 template uint64_t SymbolBody::template getPltVA<ELF64LE>() const;
294 template uint64_t SymbolBody::template getPltVA<ELF64BE>() const;
295 
296 template uint32_t SymbolBody::template getSize<ELF32LE>() const;
297 template uint32_t SymbolBody::template getSize<ELF32BE>() const;
298 template uint64_t SymbolBody::template getSize<ELF64LE>() const;
299 template uint64_t SymbolBody::template getSize<ELF64BE>() const;
300 
301 template int SymbolBody::compare<ELF32LE>(SymbolBody *Other);
302 template int SymbolBody::compare<ELF32BE>(SymbolBody *Other);
303 template int SymbolBody::compare<ELF64LE>(SymbolBody *Other);
304 template int SymbolBody::compare<ELF64BE>(SymbolBody *Other);
305 
306 template class elf::UndefinedElf<ELF32LE>;
307 template class elf::UndefinedElf<ELF32BE>;
308 template class elf::UndefinedElf<ELF64LE>;
309 template class elf::UndefinedElf<ELF64BE>;
310 
311 template class elf::DefinedSynthetic<ELF32LE>;
312 template class elf::DefinedSynthetic<ELF32BE>;
313 template class elf::DefinedSynthetic<ELF64LE>;
314 template class elf::DefinedSynthetic<ELF64BE>;
315