[lld] r246517 - Remember the maximum alignment used to refer to a common symbol.

Rafael Espindola via llvm-commits llvm-commits at lists.llvm.org
Mon Aug 31 18:19:12 PDT 2015


Author: rafael
Date: Mon Aug 31 20:19:12 2015
New Revision: 246517

URL: http://llvm.org/viewvc/llvm-project?rev=246517&view=rev
Log:
Remember the maximum alignment used to refer to a common symbol.

Modified:
    lld/trunk/ELF/Symbols.cpp
    lld/trunk/ELF/Symbols.h
    lld/trunk/ELF/Writer.cpp
    lld/trunk/test/elf2/Inputs/common.s
    lld/trunk/test/elf2/common.s

Modified: lld/trunk/ELF/Symbols.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Symbols.cpp?rev=246517&r1=246516&r2=246517&view=diff
==============================================================================
--- lld/trunk/ELF/Symbols.cpp (original)
+++ lld/trunk/ELF/Symbols.cpp Mon Aug 31 20:19:12 2015
@@ -33,10 +33,15 @@ template <class ELFT> int SymbolBody::co
   if (L.first && L.second) {
     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)
+        auto *ThisC = cast<DefinedCommon<ELFT>>(this);
+        auto *OtherC = cast<DefinedCommon<ELFT>>(Other);
+        typename DefinedCommon<ELFT>::uintX_t MaxAlign =
+            std::max(ThisC->MaxAlignment, OtherC->MaxAlignment);
+        if (ThisC->Sym.st_size >= OtherC->Sym.st_size) {
+          ThisC->MaxAlignment = MaxAlign;
           return 1;
+        }
+        OtherC->MaxAlignment = MaxAlign;
         return -1;
       }
       return -1;

Modified: lld/trunk/ELF/Symbols.h
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Symbols.h?rev=246517&r1=246516&r2=246517&view=diff
==============================================================================
--- lld/trunk/ELF/Symbols.h (original)
+++ lld/trunk/ELF/Symbols.h Mon Aug 31 20:19:12 2015
@@ -141,7 +141,9 @@ public:
   typedef typename std::conditional<ELFT::Is64Bits, uint64_t, uint32_t>::type
       uintX_t;
   explicit DefinedCommon(StringRef N, const Elf_Sym &Sym)
-      : Defined<ELFT>(Base::DefinedCommonKind, N, Sym) {}
+      : Defined<ELFT>(Base::DefinedCommonKind, N, Sym) {
+    MaxAlignment = Sym.st_value;
+  }
 
   static bool classof(const SymbolBody *S) {
     return S->kind() == Base::DefinedCommonKind;
@@ -150,6 +152,9 @@ public:
   // The output offset of this common symbol in the output bss. Computed by the
   // writer.
   uintX_t OffsetInBSS;
+
+  // The maximum alignment we have seen for this symbol.
+  uintX_t MaxAlignment;
 };
 
 // Regular defined symbols read from object file symbol tables.

Modified: lld/trunk/ELF/Writer.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Writer.cpp?rev=246517&r1=246516&r2=246517&view=diff
==============================================================================
--- lld/trunk/ELF/Writer.cpp (original)
+++ lld/trunk/ELF/Writer.cpp Mon Aug 31 20:19:12 2015
@@ -411,7 +411,7 @@ template <bool Is64Bits> struct DenseMap
 template <class ELFT>
 static bool cmpAlign(const DefinedCommon<ELFT> *A,
                      const DefinedCommon<ELFT> *B) {
-  return A->Sym.st_value > B->Sym.st_value;
+  return A->MaxAlignment > B->MaxAlignment;
 }
 
 // Create output section objects and add them to OutputSections.
@@ -457,7 +457,7 @@ template <class ELFT> void Writer<ELFT>:
   uintX_t Off = BSSSec->getSize();
   for (DefinedCommon<ELFT> *C : CommonSymbols) {
     const Elf_Sym &Sym = C->Sym;
-    uintX_t Align = Sym.st_value;
+    uintX_t Align = C->MaxAlignment;
     Off = RoundUpToAlignment(Off, Align);
     C->OffsetInBSS = Off;
     Off += Sym.st_size;

Modified: lld/trunk/test/elf2/Inputs/common.s
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/elf2/Inputs/common.s?rev=246517&r1=246516&r2=246517&view=diff
==============================================================================
--- lld/trunk/test/elf2/Inputs/common.s (original)
+++ lld/trunk/test/elf2/Inputs/common.s Mon Aug 31 20:19:12 2015
@@ -1,2 +1,3 @@
 .comm sym1,8,4
 .comm sym2,4,4
+.comm sym4,4,16

Modified: lld/trunk/test/elf2/common.s
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/elf2/common.s?rev=246517&r1=246516&r2=246517&view=diff
==============================================================================
--- lld/trunk/test/elf2/common.s (original)
+++ lld/trunk/test/elf2/common.s Mon Aug 31 20:19:12 2015
@@ -12,11 +12,19 @@
 // CHECK-NEXT: ]
 // CHECK-NEXT: Address: 0x1000
 // CHECK-NEXT: Offset:
-// CHECK-NEXT: Size: 18
+// CHECK-NEXT: Size: 22
 
 
+// CHECK:      Name: sym4
+// CHECK-NEXT: Value: 0x1000
+// CHECK-NEXT: Size: 4
+// CHECK-NEXT: Binding: Global
+// CHECK-NEXT: Type: Object
+// CHECK-NEXT: Other: 0
+// CHECK-NEXT: Section: .bss
+
 // CHECK:      Name: sym3
-// CHECK-NEXT: Value: 0x1010
+// CHECK-NEXT: Value: 0x1014
 // CHECK-NEXT: Size: 2
 // CHECK-NEXT: Binding: Global
 // CHECK-NEXT: Type: Object
@@ -24,7 +32,7 @@
 // CHECK-NEXT: Section: .bss
 
 // CHECK:      Name: sym2
-// CHECK-NEXT: Value: 0x1008
+// CHECK-NEXT: Value: 0x100C
 // CHECK-NEXT: Size: 8
 // CHECK-NEXT: Binding: Global
 // CHECK-NEXT: Type: Object
@@ -32,7 +40,7 @@
 // CHECK-NEXT: Section: .bss
 
 // CHECK:      Name: sym1
-// CHECK-NEXT: Value: 0x1000
+// CHECK-NEXT: Value: 0x1004
 // CHECK-NEXT: Size: 8
 // CHECK-NEXT: Binding: Global
 // CHECK-NEXT: Type: Object
@@ -46,3 +54,4 @@ _start:
 .comm sym1,4,4
 .comm sym2,8,4
 .comm sym3,2,2
+.comm sym4,4,2




More information about the llvm-commits mailing list