[lld] r318920 - [ELF] Give error message when relro sections are not contiguous.

Peter Smith via llvm-commits llvm-commits at lists.llvm.org
Thu Nov 23 06:53:10 PST 2017


Author: psmith
Date: Thu Nov 23 06:53:10 2017
New Revision: 318920

URL: http://llvm.org/viewvc/llvm-project?rev=318920&view=rev
Log:
[ELF] Give error message when relro sections are not contiguous.

If a linker script is used that names linker generated synthetic sections
it is possible that the OutputSections for which isRelroSection() is true
are not contiguous. When the relro sections are not contiguous we cannot
describe them with a single PT_GNU_RELRO PHDR. Unfortunately at least one
contemporary dynamic loader only supports one PT_GNU_RELRO PHDR so we
cannot output more than one of these PHDRs. As not including relro
sections in the PHDR will lead to security sensitive sections being
writeable we choose to give an error message instead.

Differential Revision: https://reviews.llvm.org/D40359

[ELF] Skip over empty sections when checking for contiguous relro


Added:
    lld/trunk/test/ELF/relro-non-contiguous.s
Modified:
    lld/trunk/ELF/Writer.cpp

Modified: lld/trunk/ELF/Writer.cpp
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/ELF/Writer.cpp?rev=318920&r1=318919&r2=318920&view=diff
==============================================================================
--- lld/trunk/ELF/Writer.cpp (original)
+++ lld/trunk/ELF/Writer.cpp Thu Nov 23 06:53:10 2017
@@ -1511,10 +1511,26 @@ template <class ELFT> std::vector<PhdrEn
 
   // PT_GNU_RELRO includes all sections that should be marked as
   // read-only by dynamic linker after proccessing relocations.
+  // Current dynamic loaders only support one PT_GNU_RELRO PHDR, give
+  // an error message if more than one PT_GNU_RELRO PHDR is required.
   PhdrEntry *RelRo = make<PhdrEntry>(PT_GNU_RELRO, PF_R);
-  for (OutputSection *Sec : OutputSections)
-    if (needsPtLoad(Sec) && isRelroSection(Sec))
-      RelRo->add(Sec);
+  bool InRelroPhdr = false;
+  bool IsRelroFinished = false;
+  for (OutputSection *Sec : OutputSections) {
+    if (!needsPtLoad(Sec))
+      continue;
+    if (isRelroSection(Sec)) {
+      InRelroPhdr = true;
+      if (!IsRelroFinished)
+        RelRo->add(Sec);
+      else
+        error("section: " + Sec->Name + " is not contiguous with other relro" +
+              " sections");
+    } else if (InRelroPhdr) {
+      InRelroPhdr = false;
+      IsRelroFinished = true;
+    }
+  }
   if (RelRo->FirstSec)
     Ret.push_back(RelRo);
 

Added: lld/trunk/test/ELF/relro-non-contiguous.s
URL: http://llvm.org/viewvc/llvm-project/lld/trunk/test/ELF/relro-non-contiguous.s?rev=318920&view=auto
==============================================================================
--- lld/trunk/test/ELF/relro-non-contiguous.s (added)
+++ lld/trunk/test/ELF/relro-non-contiguous.s Thu Nov 23 06:53:10 2017
@@ -0,0 +1,28 @@
+// RUN: llvm-mc -filetype=obj -triple=x86_64-unknown-linux %p/Inputs/shared.s -o %t.o
+// RUN: llvm-mc -filetype=obj -triple=x86_64-unknown-linux %p/Inputs/copy-in-shared.s -o %t2.o
+// RUN: ld.lld -shared %t.o %t2.o -o %t.so
+
+// Place the .got.plt (non relro) immediately after .dynamic. This is the
+// reverse order of the non-linker script case. The linker created .bss.rel.ro
+// section will be placed after .got.plt causing the relro to be non-contiguous.
+// RUN: echo "SECTIONS { \
+// RUN: .dynamic : { *(.dynamic) } \
+// RUN: .got.plt : { *(.got.plt) } \
+// RUN: } " > %t.script
+// RUN: llvm-mc -filetype=obj -triple=x86_64-unknown-linux %s -o %t3.o
+
+// Expect error for non-contiguous relro
+// RUN: not ld.lld %t3.o %t.so -z relro -o %t --script=%t.script 2>&1 | FileCheck %s
+// No error when we do not request relro.
+// RUN: ld.lld %t3.o %t.so -z norelro -o %t --script=%t.script
+// REQUIRES: x86
+
+// CHECK: error: section: .bss.rel.ro is not contiguous with other relro sections
+        .section .text, "ax", @progbits
+        .global _start
+        .global bar
+        .global foo
+_start:
+        .quad bar
+        .quad foo
+




More information about the llvm-commits mailing list