Keep the largest common symbol.
This requires templating some functions over ELFT, but that opens other cleanup
opportunities for future patches.
llvm-svn: 246405
diff --git a/lld/ELF/Symbols.cpp b/lld/ELF/Symbols.cpp
index d12db27..7eb7dda 100644
--- a/lld/ELF/Symbols.cpp
+++ b/lld/ELF/Symbols.cpp
@@ -19,25 +19,36 @@
// Returns 1, 0 or -1 if this symbol should take precedence
// over the Other, tie or lose, respectively.
-int SymbolBody::compare(SymbolBody *Other) {
+template <class ELFT> int SymbolBody::compare(SymbolBody *Other) {
std::pair<bool, bool> L(isDefined(), !isWeak());
std::pair<bool, bool> R(Other->isDefined(), !Other->isWeak());
// Normalize
if (L > R)
- return -Other->compare(this);
+ return -Other->compare<ELFT>(this);
if (L != R)
return -1;
if (L.first && L.second) {
- // FIXME: In the case where both are common we need to pick the largest
- // and remember the alignment restriction.
- if (isCommon())
+ if (isCommon()) {
+ if (Other->isCommon()) {
+ // FIXME: We also need to remember the alignment restriction.
+ if (cast<DefinedCommon<ELFT>>(this)->Sym.st_size >=
+ cast<DefinedCommon<ELFT>>(Other)->Sym.st_size)
+ return 1;
+ return -1;
+ }
return -1;
+ }
if (Other->isCommon())
return 1;
return 0;
}
return 1;
}
+
+template int SymbolBody::compare<ELF32LE>(SymbolBody *Other);
+template int SymbolBody::compare<ELF32BE>(SymbolBody *Other);
+template int SymbolBody::compare<ELF64LE>(SymbolBody *Other);
+template int SymbolBody::compare<ELF64BE>(SymbolBody *Other);