Add support for disabling automatic generation of .eh_frame_hdr sections in ELF based...
[deliverable/binutils-gdb.git] / ld / emultempl / armelf.em
index aae45d16b2126c95e937a2297f67f8c0ae342a59..27f95f2a2e40e8e665b5ed1481e6f34e297374f4 100644 (file)
@@ -1,5 +1,5 @@
 # This shell script emits a C file. -*- C -*-
-#   Copyright (C) 1991-2015 Free Software Foundation, Inc.
+#   Copyright (C) 1991-2016 Free Software Foundation, Inc.
 #
 # This file is part of the GNU Binutils.
 #
@@ -28,20 +28,26 @@ fragment <<EOF
 #include "ldctor.h"
 #include "elf/arm.h"
 
-static char * thumb_entry_symbol = NULL;
-static int byteswap_code = 0;
-static int target1_is_rel = 0${TARGET1_IS_REL};
-static char * target2_type = "${TARGET2_TYPE}";
-static int fix_v4bx = 0;
-static int use_blx = 0;
-static bfd_arm_vfp11_fix vfp11_denorm_fix = BFD_ARM_VFP11_FIX_DEFAULT;
-static bfd_arm_stm32l4xx_fix stm32l4xx_fix = BFD_ARM_STM32L4XX_FIX_NONE;
-static int fix_cortex_a8 = -1;
-static int no_enum_size_warning = 0;
-static int no_wchar_size_warning = 0;
-static int pic_veneer = 0;
-static int merge_exidx_entries = -1;
-static int fix_arm1176 = 1;
+static struct elf32_arm_params params =
+{
+  NULL,                                /* thumb_entry_symbol */
+  0,                           /* byteswap_code */
+  0${TARGET1_IS_REL},          /* target1_is_rel */
+  "${TARGET2_TYPE}",           /* target2_type */
+  0,                           /* fix_v4bx */
+  0,                           /* use_blx */
+  BFD_ARM_VFP11_FIX_DEFAULT,   /* vfp11_denorm_fix */
+  BFD_ARM_STM32L4XX_FIX_NONE,  /* stm32l4xx_fix */
+  0,                           /* no_enum_size_warning */
+  0,                           /* no_wchar_size_warning */
+  0,                           /* pic_veneer */
+  -1,                          /* fix_cortex_a8 */
+  1,                           /* fix_arm1176 */
+  -1,                          /* merge_exidx_entries */
+  0,                           /* cmse_implib */
+  NULL                         /* in_implib_bfd */
+};
+static char *in_implib_filename = NULL;
 
 static void
 gld${EMULATION_NAME}_before_parse (void)
@@ -52,6 +58,7 @@ gld${EMULATION_NAME}_before_parse (void)
   input_flags.dynamic = ${DYNAMIC_LINK-TRUE};
   config.has_shared = `if test -n "$GENERATE_SHLIB_SCRIPT" ; then echo TRUE ; else echo FALSE ; fi`;
   config.separate_code = `if test "x${SEPARATE_CODE}" = xyes ; then echo TRUE ; else echo FALSE ; fi`;
+  link_info.relro = DEFAULT_LD_Z_RELRO;
 }
 
 static void
@@ -70,7 +77,7 @@ gld${EMULATION_NAME}_set_symbols (void)
 static void
 arm_elf_before_allocation (void)
 {
-  bfd_elf32_arm_set_byteswap_code (&link_info, byteswap_code);
+  bfd_elf32_arm_set_byteswap_code (&link_info, params.byteswap_code);
 
   /* Choose type of VFP11 erratum fix, or warn if specified fix is unnecessary
      due to architecture version.  */
@@ -83,6 +90,10 @@ arm_elf_before_allocation (void)
   /* Auto-select Cortex-A8 erratum fix if it wasn't explicitly specified.  */
   bfd_elf32_arm_set_cortex_a8_fix (link_info.output_bfd, &link_info);
 
+  /* Ensure the output sections of veneers needing a dedicated one is not
+     removed.  */
+  bfd_elf32_arm_keep_private_stub_output_sections (&link_info);
+
   /* We should be able to set the size of the interworking stub section.  We
      can't do it until later if we have dynamic sections, though.  */
   if (elf_hash_table (&link_info)->dynobj == NULL)
@@ -203,12 +214,12 @@ hook_in_stub (struct hook_stub_info *info, lang_statement_union_type **lp)
 
 static asection *
 elf32_arm_add_stub_section (const char * stub_sec_name,
-                           asection *   input_section,
+                           asection *   output_section,
+                           asection *   after_input_section,
                            unsigned int alignment_power)
 {
   asection *stub_sec;
   flagword flags;
-  asection *output_section;
   lang_output_section_statement_type *os;
   struct hook_stub_info info;
 
@@ -221,18 +232,34 @@ elf32_arm_add_stub_section (const char * stub_sec_name,
 
   bfd_set_section_alignment (stub_file->the_bfd, stub_sec, alignment_power);
 
-  output_section = input_section->output_section;
   os = lang_output_section_get (output_section);
 
-  info.input_section = input_section;
+  info.input_section = after_input_section;
   lang_list_init (&info.add);
   lang_add_section (&info.add, stub_sec, NULL, os);
 
   if (info.add.head == NULL)
     goto err_ret;
 
-  if (hook_in_stub (&info, &os->children.head))
-    return stub_sec;
+  if (after_input_section == NULL)
+    {
+      lang_statement_union_type **lp = &os->children.head;
+      lang_statement_union_type *l, *lprev = NULL;
+
+      for (; (l = *lp) != NULL; lp = &l->header.next, lprev = l);
+
+      if (lprev)
+       lprev->header.next = info.add.head;
+      else
+       os->children.head = info.add.head;
+
+      return stub_sec;
+    }
+  else
+    {
+      if (hook_in_stub (&info, &os->children.head))
+       return stub_sec;
+    }
 
  err_ret:
   einfo ("%X%P: can not make stub section: %E\n");
@@ -335,7 +362,7 @@ gld${EMULATION_NAME}_after_allocation (void)
   qsort (sec_list, sec_count, sizeof (asection *), &compare_output_sec_vma);
 
   if (elf32_arm_fix_exidx_coverage (sec_list, sec_count, &link_info,
-                                   merge_exidx_entries))
+                                   params.merge_exidx_entries))
     need_laying_out = 1;
 
   free (sec_list);
@@ -416,9 +443,9 @@ gld${EMULATION_NAME}_finish (void)
 
   finish_default ();
 
-  if (thumb_entry_symbol)
+  if (params.thumb_entry_symbol)
     {
-      h = bfd_link_hash_lookup (link_info.hash, thumb_entry_symbol,
+      h = bfd_link_hash_lookup (link_info.hash, params.thumb_entry_symbol,
                                FALSE, FALSE, TRUE);
     }
   else
@@ -431,7 +458,8 @@ gld${EMULATION_NAME}_finish (void)
       h = bfd_link_hash_lookup (link_info.hash, entry_symbol.name,
                                FALSE, FALSE, TRUE);
       eh = (struct elf_link_hash_entry *)h;
-      if (!h || eh->target_internal != ST_BRANCH_TO_THUMB)
+      if (!h || ARM_GET_SYM_BRANCH_TYPE (eh->target_internal)
+               != ST_BRANCH_TO_THUMB)
        return;
     }
 
@@ -460,15 +488,15 @@ gld${EMULATION_NAME}_finish (void)
 
       sprintf_vma (buffer + 2, val);
 
-      if (thumb_entry_symbol != NULL && entry_symbol.name != NULL
+      if (params.thumb_entry_symbol != NULL && entry_symbol.name != NULL
          && entry_from_cmdline)
        einfo (_("%P: warning: '--thumb-entry %s' is overriding '-e %s'\n"),
-              thumb_entry_symbol, entry_symbol.name);
+              params.thumb_entry_symbol, entry_symbol.name);
       entry_symbol.name = buffer;
     }
   else
     einfo (_("%P: warning: cannot find thumb start symbol %s\n"),
-          thumb_entry_symbol);
+          params.thumb_entry_symbol);
 }
 
 /* This is a convenient point to tell BFD about target specific flags.
@@ -486,14 +514,19 @@ arm_elf_create_output_section_statements (void)
       return;
     }
 
-  bfd_elf32_arm_set_target_relocs (link_info.output_bfd, &link_info,
-                                  target1_is_rel,
-                                  target2_type, fix_v4bx, use_blx,
-                                  vfp11_denorm_fix, stm32l4xx_fix,
-                                  no_enum_size_warning,
-                                  no_wchar_size_warning,
-                                  pic_veneer, fix_cortex_a8,
-                                  fix_arm1176);
+  if (in_implib_filename)
+    {
+      params.in_implib_bfd = bfd_openr (in_implib_filename,
+                                       bfd_get_target (link_info.output_bfd));
+
+      if (params.in_implib_bfd == NULL)
+       einfo ("%F%s: Can't open: %E\n", in_implib_filename);
+
+      if (!bfd_check_format (params.in_implib_bfd, bfd_object))
+       einfo ("%F%s: Not a relocatable file: %E\n", in_implib_filename);
+    }
+
+  bfd_elf32_arm_set_target_params (link_info.output_bfd, &link_info, &params);
 
   stub_file = lang_add_input_file ("linker stubs",
                                   lang_input_file_is_fake_enum,
@@ -562,6 +595,8 @@ PARSE_AND_LIST_PROLOGUE='
 #define OPTION_NO_FIX_ARM1176          318
 #define OPTION_LONG_PLT                        319
 #define OPTION_STM32L4XX_FIX           320
+#define OPTION_CMSE_IMPLIB             321
+#define OPTION_IN_IMPLIB               322
 '
 
 PARSE_AND_LIST_SHORTOPTS=p
@@ -588,6 +623,8 @@ PARSE_AND_LIST_LONGOPTS='
   { "fix-arm1176", no_argument, NULL, OPTION_FIX_ARM1176 },
   { "no-fix-arm1176", no_argument, NULL, OPTION_NO_FIX_ARM1176 },
   { "long-plt", no_argument, NULL, OPTION_LONG_PLT },
+  { "cmse-implib", no_argument, NULL, OPTION_CMSE_IMPLIB },
+  { "in-implib", required_argument, NULL, OPTION_IN_IMPLIB },
 '
 
 PARSE_AND_LIST_OPTIONS='
@@ -608,6 +645,10 @@ PARSE_AND_LIST_OPTIONS='
   fprintf (file, _("  --pic-veneer                Always generate PIC interworking veneers\n"));
   fprintf (file, _("  --long-plt                  Generate long .plt entries\n"
            "                              to handle large .plt/.got displacements\n"));
+  fprintf (file, _("  --cmse-implib               Make import library to be a secure gateway import\n"
+                   "                                library as per ARMv8-M Security Extensions\n"));
+  fprintf (file, _("  --in-implib                 Import library whose symbols address must\n"
+                   "                                remain stable\n"));
   fprintf (file, _("\
   --stub-group-size=N         Maximum size of a group of input sections that\n\
                                can be handled by one stub section.  A negative\n\
@@ -628,71 +669,71 @@ PARSE_AND_LIST_ARGS_CASES='
       break;
 
     case OPTION_THUMB_ENTRY:
-      thumb_entry_symbol = optarg;
+      params.thumb_entry_symbol = optarg;
       break;
 
     case OPTION_BE8:
-      byteswap_code = 1;
+      params.byteswap_code = 1;
       break;
 
     case OPTION_TARGET1_REL:
-      target1_is_rel = 1;
+      params.target1_is_rel = 1;
       break;
 
     case OPTION_TARGET1_ABS:
-      target1_is_rel = 0;
+      params.target1_is_rel = 0;
       break;
 
     case OPTION_TARGET2:
-      target2_type = optarg;
+      params.target2_type = optarg;
       break;
 
     case OPTION_FIX_V4BX:
-      fix_v4bx = 1;
+      params.fix_v4bx = 1;
       break;
 
     case OPTION_FIX_V4BX_INTERWORKING:
-      fix_v4bx = 2;
+      params.fix_v4bx = 2;
       break;
 
     case OPTION_USE_BLX:
-      use_blx = 1;
+      params.use_blx = 1;
       break;
 
     case OPTION_VFP11_DENORM_FIX:
       if (strcmp (optarg, "none") == 0)
-        vfp11_denorm_fix = BFD_ARM_VFP11_FIX_NONE;
+        params.vfp11_denorm_fix = BFD_ARM_VFP11_FIX_NONE;
       else if (strcmp (optarg, "scalar") == 0)
-        vfp11_denorm_fix = BFD_ARM_VFP11_FIX_SCALAR;
+        params.vfp11_denorm_fix = BFD_ARM_VFP11_FIX_SCALAR;
       else if (strcmp (optarg, "vector") == 0)
-        vfp11_denorm_fix = BFD_ARM_VFP11_FIX_VECTOR;
+        params.vfp11_denorm_fix = BFD_ARM_VFP11_FIX_VECTOR;
       else
         einfo (_("Unrecognized VFP11 fix type '\''%s'\''.\n"), optarg);
       break;
 
     case OPTION_STM32L4XX_FIX:
       if (!optarg)
-        stm32l4xx_fix = BFD_ARM_STM32L4XX_FIX_DEFAULT;
+        params.stm32l4xx_fix = BFD_ARM_STM32L4XX_FIX_DEFAULT;
       else if (strcmp (optarg, "none") == 0)
-        stm32l4xx_fix = BFD_ARM_STM32L4XX_FIX_NONE;
+        params.stm32l4xx_fix = BFD_ARM_STM32L4XX_FIX_NONE;
       else if (strcmp (optarg, "default") == 0)
-        stm32l4xx_fix = BFD_ARM_STM32L4XX_FIX_DEFAULT;
+        params.stm32l4xx_fix = BFD_ARM_STM32L4XX_FIX_DEFAULT;
       else if (strcmp (optarg, "all") == 0)
-        stm32l4xx_fix = BFD_ARM_STM32L4XX_FIX_ALL;
+        params.stm32l4xx_fix = BFD_ARM_STM32L4XX_FIX_ALL;
       else
         einfo (_("Unrecognized STM32L4XX fix type '\''%s'\''.\n"), optarg);
       break;
 
     case OPTION_NO_ENUM_SIZE_WARNING:
-      no_enum_size_warning = 1;
+      params.no_enum_size_warning = 1;
       break;
 
     case OPTION_NO_WCHAR_SIZE_WARNING:
-      no_wchar_size_warning = 1;
+      params.no_wchar_size_warning = 1;
       break;
 
     case OPTION_PIC_VENEER:
-      pic_veneer = 1;
+      params.pic_veneer = 1;
       break;
 
     case OPTION_STUBGROUP_SIZE:
@@ -706,28 +747,36 @@ PARSE_AND_LIST_ARGS_CASES='
       break;
 
     case OPTION_FIX_CORTEX_A8:
-      fix_cortex_a8 = 1;
+      params.fix_cortex_a8 = 1;
       break;
 
     case OPTION_NO_FIX_CORTEX_A8:
-      fix_cortex_a8 = 0;
+      params.fix_cortex_a8 = 0;
       break;
 
    case OPTION_NO_MERGE_EXIDX_ENTRIES:
-      merge_exidx_entries = 0;
+      params.merge_exidx_entries = 0;
       break;
 
    case OPTION_FIX_ARM1176:
-      fix_arm1176 = 1;
+      params.fix_arm1176 = 1;
       break;
 
    case OPTION_NO_FIX_ARM1176:
-      fix_arm1176 = 0;
+      params.fix_arm1176 = 0;
       break;
 
    case OPTION_LONG_PLT:
       bfd_elf32_arm_use_long_plt ();
       break;
+
+   case OPTION_CMSE_IMPLIB:
+      params.cmse_implib = 1;
+      break;
+
+   case OPTION_IN_IMPLIB:
+      in_implib_filename = optarg;
+      break;
 '
 
 # We have our own before_allocation etc. functions, but they call
This page took 0.028764 seconds and 4 git commands to generate.