PR ld/24709 [arm] linker crash and assertion failure with CMSE

Message ID CAKdteOaQwnue=W5i9xqdXg3vc9qhD6U8W5ndwkbWL17+GjS6Xw@mail.gmail.com
State New
Headers show
Series
  • PR ld/24709 [arm] linker crash and assertion failure with CMSE
Related show

Commit Message

Christophe Lyon July 2, 2019, 9:04 a.m.
Hi,

As discussed in the PR, we do not support the case where CMSE stubs
are inserted too far from their destination. This would require an
intermediate long-branch stub, which is tricky in this context.

Instead of crashing, this patch emit an error message and exits.

I will send a GCC testsuite patch separately to avoid placing the CMSE
stubs too far.

OK?

Christophe

2019-07-02  Christophe Lyon  <christophe.lyon@linaro.org>

        * bfd/elf32-arm.c (CMSE_STUB_NAME): New define.
        (elf32_arm_get_stub_entry): Do not try to emit long-branch stubs
        for CMSE stubs.
        (arm_dedicated_stub_output_section_name): Use CMSE_STUB_NAME.
commit a1c05db5efe1b430ad465199bbe53fa3cf7cd434
Author: Christophe Lyon <christophe.lyon@linaro.org>
Date:   Tue Jul 2 08:57:06 2019 +0000

    PR ld/24709 [arm] linker crash and assertion failure with CMSE
    
    As discussed in the PR, we do not support the case where CMSE stubs
    are inserted too far from their destination. This would require an
    intermediate long-branch stub, which is tricky in this context.
    
    Instead of crashing, this patch emit an error message and exits.
    
    2019-07-02  Christophe Lyon  <christophe.lyon@linaro.org>
    
    	* bfd/elf32-arm.c (CMSE_STUB_NAME): New define.
    	(elf32_arm_get_stub_entry): Do not try to emit long-branch stubs
    	for CMSE stubs.
    	(arm_dedicated_stub_output_section_name): Use CMSE_STUB_NAME.

Comments

Nick Clifton July 2, 2019, 11:57 a.m. | #1
Hi Christophe,

> 2019-07-02  Christophe Lyon  <christophe.lyon@linaro.org>

> 

>         * bfd/elf32-arm.c (CMSE_STUB_NAME): New define.

>         (elf32_arm_get_stub_entry): Do not try to emit long-branch stubs

>         for CMSE stubs.

>         (arm_dedicated_stub_output_section_name): Use CMSE_STUB_NAME.


Approved - please apply.

Cheers
  Nick
Christophe Lyon July 2, 2019, 1:26 p.m. | #2
On Tue, 2 Jul 2019 at 13:57, Nick Clifton <nickc@redhat.com> wrote:
>

> Hi Christophe,

>

> > 2019-07-02  Christophe Lyon  <christophe.lyon@linaro.org>

> >

> >         * bfd/elf32-arm.c (CMSE_STUB_NAME): New define.

> >         (elf32_arm_get_stub_entry): Do not try to emit long-branch stubs

> >         for CMSE stubs.

> >         (arm_dedicated_stub_output_section_name): Use CMSE_STUB_NAME.

>

> Approved - please apply.

>


Thanks, committed.

What about 2.32 branch? Is that suitable for it?

Thanks,

Christophe

> Cheers

>   Nick

>

>

Patch

diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c
index 52fd48f..275b603 100644
--- a/bfd/elf32-arm.c
+++ b/bfd/elf32-arm.c
@@ -2300,6 +2300,8 @@  typedef unsigned short int insn16;
 
 #define CMSE_PREFIX "__acle_se_"
 
+#define CMSE_STUB_NAME ".gnu.sgstubs"
+
 /* The name of the dynamic interpreter.  This is put in the .interp
    section.  */
 #define ELF_DYNAMIC_INTERPRETER     "/usr/lib/ld.so.1"
@@ -4583,6 +4585,27 @@  elf32_arm_get_stub_entry (const asection *input_section,
   if ((input_section->flags & SEC_CODE) == 0)
     return NULL;
 
+  /* If the input section is the CMSE stubs one and it needs a long
+     branch stub to reach it's final destination, give up with an
+     error message: this is not supported.  See PR ld/24709.  */
+  if (!strncmp (input_section->name, CMSE_STUB_NAME, strlen(CMSE_STUB_NAME)))
+    {
+      bfd *output_bfd = htab->obfd;
+      asection *out_sec = bfd_get_section_by_name (output_bfd, CMSE_STUB_NAME);
+
+      _bfd_error_handler (_("ERROR: CMSE stub (%s section) too far "
+			    "(%#" PRIx64 ") from destination (%#" PRIx64 ")"),
+			  CMSE_STUB_NAME,
+			  (uint64_t)out_sec->output_section->vma
+			    + out_sec->output_offset,
+			  (uint64_t)sym_sec->output_section->vma
+			    + sym_sec->output_offset
+			    + h->root.root.u.def.value);
+      /* Exit, rather than leave incompletely processed
+	 relocations.  */
+      xexit(1);
+    }
+
   /* If this input section is part of a group of sections sharing one
      stub section, then use the id of the first section in the group.
      Stub names need to include a section id, as there may well be
@@ -4676,7 +4699,7 @@  arm_dedicated_stub_output_section_name (enum elf32_arm_stub_type stub_type)
   switch (stub_type)
     {
     case arm_stub_cmse_branch_thumb_only:
-      return ".gnu.sgstubs";
+      return CMSE_STUB_NAME;
 
     default:
       BFD_ASSERT (!arm_dedicated_stub_output_section_required (stub_type));