ld: Add --enable-separate-code
authorH.J. Lu <hjl.tools@gmail.com>
Tue, 27 Feb 2018 19:34:20 +0000 (11:34 -0800)
committerH.J. Lu <hjl.tools@gmail.com>
Tue, 27 Feb 2018 19:34:29 +0000 (11:34 -0800)
This patch adds --enable-separate-code to ld configure to turn on
-z separate-code by default and enables it by default for Linux/x86.
This avoids mixing code pages with data to improve cache performance
as well as security.

To reduce x86-64 executable and shared object sizes, the maximum page
size is reduced from 2MB to 4KB when -z separate-code is turned on by
default.  Note: -z max-page-size= can be used to set the maximum page
size.

We compared SPEC CPU 2017 performance before and after this change on
Skylake server.  There are no any significant performance changes.
Everything is mostly below +/-1%.

bfd/

* config.in: Regenerated.
* configure: Likewise.
* configure.ac: Add --enable-separate-code.
(DEFAULT_LD_Z_SEPARATE_CODE): New AC_DEFINE_UNQUOTED.  Default
to 1 for Linux/x86 targets,
* elf64-x86-64.c (ELF_MAXPAGESIZE): Set to 0x1000 if
DEFAULT_LD_Z_SEPARATE_CODE is 1.

ld/

* NEWS: Mention --enable-separate-code.
* configure.ac: Add --enable-separate-code.
(DEFAULT_LD_Z_SEPARATE_CODE): New AC_DEFINE_UNQUOTED.
* configure.tgt: Default ac_default_ld_z_separate_code to 1 for
Linux/x86 targets.
* config.in: Regenerated.
* configure: Likewise.
* emultempl/elf32.em (gld${EMULATION_NAME}_before_parse): Set
link_info.separate_code DEFAULT_LD_Z_SEPARATE_CODE.

12 files changed:
bfd/ChangeLog
bfd/config.in
bfd/configure
bfd/configure.ac
bfd/elf64-x86-64.c
ld/ChangeLog
ld/NEWS
ld/config.in
ld/configure
ld/configure.ac
ld/configure.tgt
ld/emultempl/elf32.em

index 5c2a888cd00723c9409461acca8762357937d566..59f7c9cfd4888bd6c874f472322f7705a21de4cd 100644 (file)
@@ -1,3 +1,13 @@
+2018-02-27  H.J. Lu  <hongjiu.lu@intel.com>
+
+       * config.in: Regenerated.
+       * configure: Likewise.
+       * configure.ac: Add --enable-separate-code.
+       (DEFAULT_LD_Z_SEPARATE_CODE): New AC_DEFINE_UNQUOTED.  Default
+       to 1 for Linux/x86 targets,
+       * elf64-x86-64.c (ELF_MAXPAGESIZE): Set to 0x1000 if
+       DEFAULT_LD_Z_SEPARATE_CODE is 1.
+
 2018-02-27  Nick Clifton  <nickc@redhat.com>
 
        * aout-cris.c (swap_ext_reloc_out): Standadize error/warning
index 75a5ff015ed2a701d596ffb941c13d423f6d8b32..186741d6128df2fe2afd3f166d30587a48c12824 100644 (file)
 /* Name of host specific core header file to include in elf.c. */
 #undef CORE_HEADER
 
+/* Define to 1 if you want to enable -z separate-code in ELF linker by
+   default. */
+#undef DEFAULT_LD_Z_SEPARATE_CODE
+
 /* Define to 1 if translation of program messages to the user's native
    language is requested. */
 #undef ENABLE_NLS
index 6c2b24ebe3d20b34d032a574dfaa8351eaa1a5d6..d1fe335530c8378766db4bba0ea7e8b4db73b0de 100755 (executable)
@@ -793,6 +793,7 @@ enable_targets
 enable_64_bit_archive
 with_mmap
 enable_secureplt
+enable_separate_code
 enable_leading_mingw64_underscores
 with_separate_debug_dir
 with_pkgversion
@@ -1446,6 +1447,7 @@ Optional Features:
   --enable-targets        alternative target configurations
   --enable-64-bit-archive force 64-bit archives
   --enable-secureplt      Default to creating read-only plt entries
+  --enable-separate-code  enable -z separate-code in ELF linker by default
   --enable-leading-mingw64-underscores
                           Enable leading underscores on 64 bit mingw targets
   --enable-werror         treat compile warnings as errors
@@ -11428,7 +11430,7 @@ else
   lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
   lt_status=$lt_dlunknown
   cat > conftest.$ac_ext <<_LT_EOF
-#line 11431 "configure"
+#line 11433 "configure"
 #include "confdefs.h"
 
 #if HAVE_DLFCN_H
@@ -11534,7 +11536,7 @@ else
   lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
   lt_status=$lt_dlunknown
   cat > conftest.$ac_ext <<_LT_EOF
-#line 11537 "configure"
+#line 11539 "configure"
 #include "confdefs.h"
 
 #if HAVE_DLFCN_H
@@ -12171,6 +12173,33 @@ $as_echo "#define USE_SECUREPLT 1" >>confdefs.h
 
 fi
 
+# Decide if -z separate-code should be enabled in ELF linker by default.
+ac_default_ld_z_separate_code=unset
+# Check whether --enable-separate-code was given.
+if test "${enable_separate_code+set}" = set; then :
+  enableval=$enable_separate_code; case "${enableval}" in
+  yes) ac_default_ld_z_separate_code=1 ;;
+  no) ac_default_ld_z_separate_code=0 ;;
+esac
+fi
+
+# Enable -z separate-code by default for Linux/x86.
+case "${target}" in
+i3-786-*-linux-* | x86_64-*-linux-*)
+  if test ${ac_default_ld_z_separate_code} = unset; then
+    ac_default_ld_z_separate_code=1
+  fi
+  ;;
+esac
+if test "${ac_default_ld_z_separate_code}" = unset; then
+  ac_default_ld_z_separate_code=0
+fi
+
+cat >>confdefs.h <<_ACEOF
+#define DEFAULT_LD_Z_SEPARATE_CODE $ac_default_ld_z_separate_code
+_ACEOF
+
+
 # Check whether --enable-leading-mingw64-underscores was given.
 if test "${enable_leading_mingw64_underscores+set}" = set; then :
   enableval=$enable_leading_mingw64_underscores;
index 2342f3faeacbaf2d2353c55cfea0d2b91f24ccda..20e2c022e8a5d76853dd1e5dc0564fcecef5578f 100644 (file)
@@ -97,6 +97,30 @@ if test $use_secureplt = true; then
     [Define if we should default to creating read-only plt entries])
 fi
 
+# Decide if -z separate-code should be enabled in ELF linker by default.
+ac_default_ld_z_separate_code=unset
+AC_ARG_ENABLE(separate-code,
+             AS_HELP_STRING([--enable-separate-code],
+             [enable -z separate-code in ELF linker by default]),
+[case "${enableval}" in
+  yes) ac_default_ld_z_separate_code=1 ;;
+  no) ac_default_ld_z_separate_code=0 ;;
+esac])
+# Enable -z separate-code by default for Linux/x86.
+case "${target}" in
+i[3-7]86-*-linux-* | x86_64-*-linux-*)
+  if test ${ac_default_ld_z_separate_code} = unset; then
+    ac_default_ld_z_separate_code=1
+  fi
+  ;;
+esac
+if test "${ac_default_ld_z_separate_code}" = unset; then
+  ac_default_ld_z_separate_code=0
+fi
+AC_DEFINE_UNQUOTED(DEFAULT_LD_Z_SEPARATE_CODE,
+  $ac_default_ld_z_separate_code,
+  [Define to 1 if you want to enable -z separate-code in ELF linker by default.])
+
 AC_ARG_ENABLE(leading-mingw64-underscores,
   AS_HELP_STRING([--enable-leading-mingw64-underscores],
                  [Enable leading underscores on 64 bit mingw targets]),
index 02a3d37e43c0b9df6bff9973fba3de391d6d42d7..7016964aceb38c439c222a447e0db3c00e3996f7 100644 (file)
@@ -4942,7 +4942,11 @@ elf_x86_64_special_sections[]=
 #define ELF_ARCH                           bfd_arch_i386
 #define ELF_TARGET_ID                      X86_64_ELF_DATA
 #define ELF_MACHINE_CODE                   EM_X86_64
-#define ELF_MAXPAGESIZE                            0x200000
+#if DEFAULT_LD_Z_SEPARATE_CODE
+# define ELF_MAXPAGESIZE                   0x1000
+#else
+# define ELF_MAXPAGESIZE                   0x200000
+#endif
 #define ELF_MINPAGESIZE                            0x1000
 #define ELF_COMMONPAGESIZE                 0x1000
 
@@ -5335,7 +5339,11 @@ elf64_l1om_elf_object_p (bfd *abfd)
 #undef ELF_MAXPAGESIZE
 #undef ELF_MINPAGESIZE
 #undef ELF_COMMONPAGESIZE
-#define ELF_MAXPAGESIZE                        0x200000
+#if DEFAULT_LD_Z_SEPARATE_CODE
+# define ELF_MAXPAGESIZE               0x1000
+#else
+# define ELF_MAXPAGESIZE               0x200000
+#endif
 #define ELF_MINPAGESIZE                        0x1000
 #define ELF_COMMONPAGESIZE             0x1000
 #undef elf_backend_plt_alignment
index d117b7e4741f783bd01d3e2f7020807d622fba30..07c86efc061db91d38ffabeb2ecf66a41c052f21 100644 (file)
@@ -1,3 +1,15 @@
+2018-02-27  H.J. Lu  <hongjiu.lu@intel.com>
+
+       * NEWS: Mention --enable-separate-code.
+       * configure.ac: Add --enable-separate-code.
+       (DEFAULT_LD_Z_SEPARATE_CODE): New AC_DEFINE_UNQUOTED.
+       * configure.tgt: Default ac_default_ld_z_separate_code to 1 for
+       Linux/x86 targets.
+       * config.in: Regenerated.
+       * configure: Likewise.
+       * emultempl/elf32.em (gld${EMULATION_NAME}_before_parse): Set
+       link_info.separate_code DEFAULT_LD_Z_SEPARATE_CODE.
+
 2018-02-26  Alan Modra  <amodra@gmail.com>
 
        * emulparams/call_nop.sh, * emulparams/cet.sh,
diff --git a/ld/NEWS b/ld/NEWS
index eafcaf33cb7b50b5bacbe1e21a92b1d27584f537..75f8100f87afd72bbda0b2d37b2e5c5dc84c6be4 100644 (file)
--- a/ld/NEWS
+++ b/ld/NEWS
@@ -1,5 +1,10 @@
 -*- text -*-
 
+* Add a configure option --enable-separate-code to decide whether
+  -z separate-code should be enabled in ELF linker by default.  Default
+  to yes for Linux/x86 targets.  Note that -z separate-code can increase
+  disk and memory size.
+
 Changes in 2.30:
 
 * Add -z separate-code to generate separate code PT_LOAD segment.
index a846743da6b9989c875403554bbe3a3425a636b4..b227a53984663925bfe04a22f414fa0e7b285379 100644 (file)
 /* Define to 1 if you want to enable -z relro in ELF linker by default. */
 #undef DEFAULT_LD_Z_RELRO
 
+/* Define to 1 if you want to enable -z separate-code in ELF linker by
+   default. */
+#undef DEFAULT_LD_Z_SEPARATE_CODE
+
 /* Define to 1 if you want to set DT_RUNPATH instead of DT_RPATH by default.
    */
 #undef DEFAULT_NEW_DTAGS
index 17604bb91bee36ad59239b39a5f0d2481d85febf..38f9739126f49a0771327494f3ae30edd135ace9 100755 (executable)
@@ -790,6 +790,7 @@ enable_got
 enable_compressed_debug_sections
 enable_new_dtags
 enable_relro
+enable_separate_code
 enable_default_hash_style
 enable_werror
 enable_build_warnings
@@ -1451,6 +1452,7 @@ Optional Features:
                           compress debug sections by default]
   --enable-new-dtags      set DT_RUNPATH instead of DT_RPATH by default]
   --enable-relro          enable -z relro in ELF linker by default
+  --enable-separate-code  enable -z separate-code in ELF linker by default
   --enable-default-hash-style={sysv,gnu,both}
                           use this default hash style
   --enable-werror         treat compile warnings as errors
@@ -11725,7 +11727,7 @@ else
   lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
   lt_status=$lt_dlunknown
   cat > conftest.$ac_ext <<_LT_EOF
-#line 11728 "configure"
+#line 11730 "configure"
 #include "confdefs.h"
 
 #if HAVE_DLFCN_H
@@ -11831,7 +11833,7 @@ else
   lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
   lt_status=$lt_dlunknown
   cat > conftest.$ac_ext <<_LT_EOF
-#line 11834 "configure"
+#line 11836 "configure"
 #include "confdefs.h"
 
 #if HAVE_DLFCN_H
@@ -15567,6 +15569,17 @@ if test "${enable_relro+set}" = set; then :
 esac
 fi
 
+# Decide if -z separate-code should be enabled in ELF linker by default.
+ac_default_ld_z_separate_code=unset
+# Check whether --enable-separate-code was given.
+if test "${enable_separate_code+set}" = set; then :
+  enableval=$enable_separate_code; case "${enableval}" in
+  yes) ac_default_ld_z_separate_code=1 ;;
+  no) ac_default_ld_z_separate_code=0 ;;
+esac
+fi
+
+
 # Decide which "--hash-style" to use by default
 # Provide a configure time option to override our default.
 # Check whether --enable-default-hash-style was given.
@@ -17258,6 +17271,15 @@ cat >>confdefs.h <<_ACEOF
 _ACEOF
 
 
+if test "${ac_default_ld_z_separate_code}" = unset; then
+  ac_default_ld_z_separate_code=0
+fi
+
+cat >>confdefs.h <<_ACEOF
+#define DEFAULT_LD_Z_SEPARATE_CODE $ac_default_ld_z_separate_code
+_ACEOF
+
+
 
 cat >>confdefs.h <<_ACEOF
 #define DEFAULT_EMIT_SYSV_HASH $ac_default_emit_sysv_hash
index 6da8c8e50f1de149eec066b1aa0ab3486f567faf..35529268db81d4a3cf228c0ebff468bf32042c89 100644 (file)
@@ -177,6 +177,16 @@ AC_ARG_ENABLE(relro,
   no)  ac_default_ld_z_relro=0 ;;
 esac])dnl
 
+# Decide if -z separate-code should be enabled in ELF linker by default.
+ac_default_ld_z_separate_code=unset
+AC_ARG_ENABLE(separate-code,
+             AS_HELP_STRING([--enable-separate-code],
+             [enable -z separate-code in ELF linker by default]),
+[case "${enableval}" in
+  yes) ac_default_ld_z_separate_code=1 ;;
+  no) ac_default_ld_z_separate_code=0 ;;
+esac])
+
 # Decide which "--hash-style" to use by default
 # Provide a configure time option to override our default.
 AC_ARG_ENABLE([default-hash-style],
@@ -434,6 +444,13 @@ AC_DEFINE_UNQUOTED(DEFAULT_LD_Z_RELRO,
   $ac_default_ld_z_relro,
   [Define to 1 if you want to enable -z relro in ELF linker by default.])
 
+if test "${ac_default_ld_z_separate_code}" = unset; then
+  ac_default_ld_z_separate_code=0
+fi
+AC_DEFINE_UNQUOTED(DEFAULT_LD_Z_SEPARATE_CODE,
+  $ac_default_ld_z_separate_code,
+  [Define to 1 if you want to enable -z separate-code in ELF linker by default.])
+
 AC_DEFINE_UNQUOTED([DEFAULT_EMIT_SYSV_HASH],
   [$ac_default_emit_sysv_hash],
   [Define to 1 if you want to emit sysv hash in the ELF linker by default.])
index 6183a85b3d14ff4f52a529517af26f6460704aaa..7897448e6438bada02eb88244dfb1336621511b0 100644 (file)
@@ -968,3 +968,12 @@ frv-*-* | hppa*-*-* | ia64-*-* | mips*-*-*)
   fi
   ;;
 esac
+
+# Enable -z separate-code by default for Linux/x86.
+case "${target}" in
+i[3-7]86-*-linux-* | x86_64-*-linux-*)
+  if test ${ac_default_ld_z_separate_code} = unset; then
+    ac_default_ld_z_separate_code=1
+  fi
+  ;;
+esac
index aae9d1f6259f17c069961b00a2101c42fd876398..9b8971eac486898322c7dd4cfd64777a12b28f01 100644 (file)
@@ -106,6 +106,7 @@ gld${EMULATION_NAME}_before_parse (void)
   `if test -n "$CALL_NOP_BYTE" ; then echo link_info.call_nop_byte = $CALL_NOP_BYTE; fi`;
   link_info.check_relocs_after_open_input = TRUE;
   link_info.relro = DEFAULT_LD_Z_RELRO;
+  link_info.separate_code = DEFAULT_LD_Z_SEPARATE_CODE;
 }
 
 EOF