<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">On Mon, Oct 12, 2015 at 1:51 PM, Hal Finkel via llvm-commits <span dir="ltr"><<a href="mailto:llvm-commits@lists.llvm.org" target="_blank">llvm-commits@lists.llvm.org</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">Author: hfinkel<br>
Date: Mon Oct 12 15:51:48 2015<br>
New Revision: 250100<br>
<br>
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=250100&view=rev" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project?rev=250100&view=rev</a><br>
Log:<br>
[ELF2] Sort PPC64 special sections<br>
<br>
PPC64 has several special sections that are intended to be accessed from the<br>
TOC base pointer. When a .got is present, the TOC base pointer is .got + 0x8000<br>
(as specified by the ABI). Furthermore, the glibc startup code contains an<br>
assumption that a 16-bit relocation can hold the offset from the TOC base value<br>
to the beginning of the .toc section. Thus, we need to make sure that .toc<br>
appears after .got. This much, at least, is required in practice. The other<br>
PPC64 special sections (.toc, .toc1, .opd, etc.) should also be close by to<br>
optimize access by smaller TOC-base-pointer offsets.<br>
<br>
Modified:<br>
    lld/trunk/ELF/Writer.cpp<br>
    lld/trunk/test/elf2/basic64be.s<br>
<br>
Modified: lld/trunk/ELF/Writer.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Writer.cpp?rev=250100&r1=250099&r2=250100&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Writer.cpp?rev=250100&r1=250099&r2=250100&view=diff</a><br>
==============================================================================<br>
--- lld/trunk/ELF/Writer.cpp (original)<br>
+++ lld/trunk/ELF/Writer.cpp Mon Oct 12 15:51:48 2015<br>
@@ -14,6 +14,7 @@<br>
 #include "Target.h"<br>
<br>
 #include "llvm/ADT/SmallPtrSet.h"<br>
+#include "llvm/ADT/StringSwitch.h"<br>
 #include "llvm/Support/FileOutputBuffer.h"<br>
<br>
 using namespace llvm;<br>
@@ -261,6 +262,22 @@ template <class ELFT> void Writer<ELFT>:<br>
   }<br>
 }<br>
<br>
+// PPC64 has a number of special SHT_PROGBITS+SHF_ALLOC+SHF_WRITE sections that<br>
+// we would like to make sure appear is a specific order to maximize their<br>
+// coverage by a single signed 16-bit offset from the TOC base pointer.<br>
+// Conversely, the special .tocbss section should be first among all SHT_NOBITS<br>
+// sections. This will put it next to the loaded special PPC64 sections (and,<br>
+// thus, within reach of the TOC base pointer).<br>
+static int getPPC64SectionRank(StringRef SectionName) {<br>
+  return StringSwitch<int>(SectionName)<br>
+           .Case(".tocbss", 0)<br>
+           .Case(".branch_lt", 2)<br>
+           .Case(".toc", 3)<br>
+           .Case(".toc1", 4)<br>
+           .Case(".opd", 5)<br>
+           .Default(1);<br>
+}<br>
+<br>
 // Output section ordering is determined by this function.<br>
 template <class ELFT><br>
 static bool compareOutputSections(OutputSectionBase<ELFT::Is64Bits> *A,<br>
@@ -302,7 +319,10 @@ static bool compareOutputSections(Output<br>
   // them is a p_memsz that is larger than p_filesz. Seeing that it<br>
   // zeros the end of the PT_LOAD, so that has to correspond to the<br>
   // nobits sections.<br>
-  return A->getType() != SHT_NOBITS && B->getType() == SHT_NOBITS;<br>
+  if (A->getType() != SHT_NOBITS && B->getType() == SHT_NOBITS)<br>
+    return true;<br></blockquote><div><br></div><div>This should be </div><div><br></div><div><span style="color:rgb(0,0,0)">  if (A->getType() != B->getType())</span></div><div><span style="color:rgb(0,0,0)">    </span>return A->getType() != SHT_NOBITS && B->getType() == SHT_NOBITS;</div><div><br></div><div>or otherwise this function does not guarantee weak strict ordering. Sorry for not noticing earlier.</div><div><br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">
+<br>
+  return getPPC64SectionRank(A->getName()) < getPPC64SectionRank(B->getName());<br>
 }<br>
<br>
 // Until this function is called, common symbols do not belong to any section.<br>
<br>
Modified: lld/trunk/test/elf2/basic64be.s<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/lld/trunk/test/elf2/basic64be.s?rev=250100&r1=250099&r2=250100&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/lld/trunk/test/elf2/basic64be.s?rev=250100&r1=250099&r2=250100&view=diff</a><br>
==============================================================================<br>
--- lld/trunk/test/elf2/basic64be.s (original)<br>
+++ lld/trunk/test/elf2/basic64be.s Mon Oct 12 15:51:48 2015<br>
@@ -9,6 +9,14 @@<br>
 _start:<br>
 .quad   .Lfoo,.TOC.@tocbase,0<br>
<br>
+# generate .toc and .toc1 sections to make sure that the ordering is as<br>
+# intended (.toc before .toc1, and both before .opd).<br>
+.section        ".toc1","aw"<br>
+.quad          22, 37, 89, 47<br>
+<br>
+.section        ".toc","aw"<br>
+.quad          45, 86, 72, 24<br>
+<br>
 .text<br>
 .Lfoo:<br>
        li      0,1<br>
@@ -28,17 +36,17 @@ _start:<br>
 # CHECK-NEXT:   Type: Executable (0x2)<br>
 # CHECK-NEXT:   Machine: EM_PPC64 (0x15)<br>
 # CHECK-NEXT:   Version: 1<br>
-# CHECK-NEXT:   Entry: 0x10020000<br>
+# CHECK-NEXT:   Entry: 0x10020040<br>
 # CHECK-NEXT:   ProgramHeaderOffset: 0x40<br>
-# CHECK-NEXT:   SectionHeaderOffset: 0x20078<br>
+# CHECK-NEXT:   SectionHeaderOffset: 0x200C8<br>
 # CHECK-NEXT:   Flags [ (0x0)<br>
 # CHECK-NEXT:   ]<br>
 # CHECK-NEXT:   HeaderSize: 64<br>
 # CHECK-NEXT:   ProgramHeaderEntrySize: 56<br>
 # CHECK-NEXT:   ProgramHeaderCount: 4<br>
 # CHECK-NEXT:   SectionHeaderEntrySize: 64<br>
-# CHECK-NEXT:   SectionHeaderCount: 7<br>
-# CHECK-NEXT:    StringTableSectionIndex: 6<br>
+# CHECK-NEXT:   SectionHeaderCount: 9<br>
+# CHECK-NEXT:   StringTableSectionIndex: 8<br>
 # CHECK-NEXT: }<br>
 # CHECK-NEXT: Sections [<br>
 # CHECK-NEXT:   Section {<br>
@@ -55,18 +63,18 @@ _start:<br>
 # CHECK-NEXT:     AddressAlignment: 0<br>
 # CHECK-NEXT:     EntrySize: 0<br>
 # CHECK-NEXT:     SectionData (<br>
-# CHECK:          )<br>
+# CHECK-NEXT:     )<br>
 # CHECK-NEXT:   }<br>
 # CHECK-NEXT:   Section {<br>
 # CHECK-NEXT:     Index: 1<br>
-# CHECK-NEXT:     Name: .text<br>
+# CHECK-NEXT:     Name: .text (1)<br>
 # CHECK-NEXT:     Type: SHT_PROGBITS (0x1)<br>
 # CHECK-NEXT:     Flags [ (0x6)<br>
 # CHECK-NEXT:       SHF_ALLOC (0x2)<br>
 # CHECK-NEXT:       SHF_EXECINSTR (0x4)<br>
 # CHECK-NEXT:     ]<br>
 # CHECK-NEXT:     Address: 0x10010000<br>
-# CHECK-NEXT:     Offset: 0x1000<br>
+# CHECK-NEXT:     Offset: 0x10000<br>
 # CHECK-NEXT:     Size: 12<br>
 # CHECK-NEXT:     Link: 0<br>
 # CHECK-NEXT:     Info: 0<br>
@@ -77,7 +85,7 @@ _start:<br>
 # CHECK-NEXT:   }<br>
 # CHECK-NEXT:   Section {<br>
 # CHECK-NEXT:     Index: 2<br>
-# CHECK-NEXT:     Name: .data<br>
+# CHECK-NEXT:     Name: .data (45)<br>
 # CHECK-NEXT:     Type: SHT_PROGBITS (0x1)<br>
 # CHECK-NEXT:     Flags [ (0x3)<br>
 # CHECK-NEXT:       SHF_ALLOC (0x2)<br>
@@ -95,34 +103,74 @@ _start:<br>
 # CHECK-NEXT:   }<br>
 # CHECK-NEXT:   Section {<br>
 # CHECK-NEXT:     Index: 3<br>
-# CHECK-NEXT:     Name: .opd<br>
+# CHECK-NEXT:     Name: .toc (24)<br>
 # CHECK-NEXT:     Type: SHT_PROGBITS (0x1)<br>
 # CHECK-NEXT:     Flags [ (0x3)<br>
 # CHECK-NEXT:       SHF_ALLOC (0x2)<br>
 # CHECK-NEXT:       SHF_WRITE (0x1)<br>
 # CHECK-NEXT:     ]<br>
 # CHECK-NEXT:     Address: 0x10020000<br>
-# CHECK-NEXT:     Offset: 0x2000<br>
-# CHECK-NEXT:     Size: 24<br>
+# CHECK-NEXT:     Offset: 0x20000<br>
+# CHECK-NEXT:     Size: 32<br>
 # CHECK-NEXT:     Link: 0<br>
 # CHECK-NEXT:     Info: 0<br>
 # CHECK-NEXT:     AddressAlignment: 1<br>
 # CHECK-NEXT:     EntrySize: 0<br>
 # CHECK-NEXT:     SectionData (<br>
-# CHECK-NEXT:      0000: 00000000 10010000 00000000 00000000  |................|<br>
-# CHECK-NEXT:      0010: 00000000 00000000                    |........|<br>
+# CHECK-NEXT:      0000: 00000000 0000002D 00000000 00000056 |.......-.......V|<br>
+# CHECK-NEXT:      0010: 00000000 00000048 00000000 00000018 |.......H........|<br>
 # CHECK-NEXT:     )<br>
 # CHECK-NEXT:   }<br>
 # CHECK-NEXT:   Section {<br>
 # CHECK-NEXT:     Index: 4<br>
-# CHECK-NEXT:     Name: .bss<br>
+# CHECK-NEXT:     Name: .toc1 (51)<br>
+# CHECK-NEXT:     Type: SHT_PROGBITS (0x1)<br>
+# CHECK-NEXT:     Flags [ (0x3)<br>
+# CHECK-NEXT:       SHF_ALLOC (0x2)<br>
+# CHECK-NEXT:       SHF_WRITE (0x1)<br>
+# CHECK-NEXT:     ]<br>
+# CHECK-NEXT:     Address: 0x10020020<br>
+# CHECK-NEXT:     Offset: 0x20020<br>
+# CHECK-NEXT:     Size: 32<br>
+# CHECK-NEXT:     Link: 0<br>
+# CHECK-NEXT:     Info: 0<br>
+# CHECK-NEXT:     AddressAlignment: 1<br>
+# CHECK-NEXT:     EntrySize: 0<br>
+# CHECK-NEXT:     SectionData (<br>
+# CHECK-NEXT:       0000: 00000000 00000016 00000000 00000025  |...............%|<br>
+# CHECK-NEXT:       0010: 00000000 00000059 00000000 0000002F  |.......Y......./|<br>
+# CHECK-NEXT:     )<br>
+# CHECK-NEXT:   }<br>
+# CHECK-NEXT:   Section {<br>
+# CHECK-NEXT:     Index: 5<br>
+# CHECK-NEXT:     Name: .opd (19)<br>
+# CHECK-NEXT:     Type: SHT_PROGBITS (0x1)<br>
+# CHECK-NEXT:     Flags [ (0x3)<br>
+# CHECK-NEXT:       SHF_ALLOC (0x2)<br>
+# CHECK-NEXT:       SHF_WRITE (0x1)<br>
+# CHECK-NEXT:     ]<br>
+# CHECK-NEXT:     Address: 0x10020040<br>
+# CHECK-NEXT:     Offset: 0x20040<br>
+# CHECK-NEXT:     Size: 24<br>
+# CHECK-NEXT:     Link: 0<br>
+# CHECK-NEXT:     Info: 0<br>
+# CHECK-NEXT:     AddressAlignment: 1<br>
+# CHECK-NEXT:     EntrySize: 0<br>
+# CHECK-NEXT:     SectionData (<br>
+# CHECK-NEXT:       0000: 00000000 10010000 00000000 00000000 |................|<br>
+# CHECK-NEXT:       0010: 00000000 00000000                    |........|<br>
+# CHECK-NEXT:     )<br>
+# CHECK-NEXT:   }<br>
+# CHECK-NEXT:   Section {<br>
+# CHECK-NEXT:     Index: 6<br>
+# CHECK-NEXT:     Name: .bss (14)<br>
 # CHECK-NEXT:     Type: SHT_NOBITS (0x8)<br>
 # CHECK-NEXT:     Flags [ (0x3)<br>
 # CHECK-NEXT:       SHF_ALLOC (0x2)<br>
 # CHECK-NEXT:       SHF_WRITE (0x1)<br>
 # CHECK-NEXT:     ]<br>
-# CHECK-NEXT:     Address: 0x10020018<br>
-# CHECK-NEXT:     Offset: 0x20018<br>
+# CHECK-NEXT:     Address: 0x10020058<br>
+# CHECK-NEXT:     Offset: 0x20058<br>
 # CHECK-NEXT:     Size: 0<br>
 # CHECK-NEXT:     Link: 0<br>
 # CHECK-NEXT:     Info: 0<br>
@@ -130,15 +178,15 @@ _start:<br>
 # CHECK-NEXT:     EntrySize: 0<br>
 # CHECK-NEXT:   }<br>
 # CHECK-NEXT:   Section {<br>
-# CHECK-NEXT:     Index: 5<br>
-# CHECK-NEXT:     Name: .symtab<br>
-# CHECK-NEXT:     Type: SHT_SYMTAB<br>
-# CHECK-NEXT:     Flags [<br>
+# CHECK-NEXT:     Index: 7<br>
+# CHECK-NEXT:     Name: .symtab (37)<br>
+# CHECK-NEXT:     Type: SHT_SYMTAB (0x2)<br>
+# CHECK-NEXT:     Flags [ (0x0)<br>
 # CHECK-NEXT:     ]<br>
 # CHECK-NEXT:     Address: 0x0<br>
-# CHECK-NEXT:     Offset: 0x20018<br>
+# CHECK-NEXT:     Offset: 0x20058<br>
 # CHECK-NEXT:     Size: 48<br>
-# CHECK-NEXT:     Link: 6<br>
+# CHECK-NEXT:     Link: 8<br>
 # CHECK-NEXT:     Info: 1<br>
 # CHECK-NEXT:     AddressAlignment: 8<br>
 # CHECK-NEXT:     EntrySize: 24<br>
@@ -146,14 +194,14 @@ _start:<br>
 # CHECK:          )<br>
 # CHECK-NEXT:   }<br>
 # CHECK-NEXT:   Section {<br>
-# CHECK-NEXT:     Index: 6<br>
-# CHECK-NEXT:     Name: .strtab<br>
+# CHECK-NEXT:     Index: 8<br>
+# CHECK-NEXT:     Name: .strtab (29)<br>
 # CHECK-NEXT:     Type: SHT_STRTAB (0x3)<br>
 # CHECK-NEXT:     Flags [ (0x0)<br>
 # CHECK-NEXT:     ]<br>
 # CHECK-NEXT:     Address: 0x0<br>
-# CHECK-NEXT:     Offset: 0x20048<br>
-# CHECK-NEXT:     Size: 46<br>
+# CHECK-NEXT:     Offset: 0x20088<br>
+# CHECK-NEXT:     Size: 57<br>
 # CHECK-NEXT:     Link: 0<br>
 # CHECK-NEXT:     Info: 0<br>
 # CHECK-NEXT:     AddressAlignment: 1<br>
@@ -205,8 +253,8 @@ _start:<br>
 # CHECK-NEXT:    Offset: 0x2000<br>
 # CHECK-NEXT:    VirtualAddress: 0x10020000<br>
 # CHECK-NEXT:    PhysicalAddress: 0x10020000<br>
-# CHECK-NEXT:    FileSize: 24<br>
-# CHECK-NEXT:    MemSize: 24<br>
+# CHECK-NEXT:    FileSize: 88<br>
+# CHECK-NEXT:    MemSize: 88<br>
 # CHECK-NEXT:    Flags [ (0x6)<br>
 # CHECK-NEXT:      PF_R (0x4)<br>
 # CHECK-NEXT:      PF_W (0x2)<br>
<br>
<br>
_______________________________________________<br>
llvm-commits mailing list<br>
<a href="mailto:llvm-commits@lists.llvm.org">llvm-commits@lists.llvm.org</a><br>
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits</a><br>
</blockquote></div><br></div></div>