This is the mail archive of the binutils@sourceware.org mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

PATCH: Tidy up code in elf32-arm.c


Hi Guys,

  Whilst looking into the ARM interworking problems I had cause to
  note that the code in elf32-arm.c hand become rather untidy, so I am
  checking in the attached patch to spruce it up.  The patch does not
  fix any bugs (or introduce any new ones!).

Cheers
  Nick

bfd/ChangeLog
2008-08-17  Nick Clifton  <nickc@redhat.com>

	* elf32-arm.c: Tidy up the code.
	(bfd_elf32_arm_allocate_interworking_sections): Move common code
	into...
	(arm_allocate_glue_section_space): ... New function.
	(bfd_elf32_arm_add_glue_sections_to_bfd): Move common code
	into...
	(arm_make_glue_section): ... New function.

Index: bfd/elf32-arm.c
===================================================================
RCS file: /cvs/src/src/bfd/elf32-arm.c,v
retrieving revision 1.154
diff -c -3 -p -r1.154 elf32-arm.c
*** bfd/elf32-arm.c	28 Jul 2008 06:46:31 -0000	1.154
--- bfd/elf32-arm.c	17 Aug 2008 20:43:20 -0000
*************** static struct elf_backend_data elf32_arm
*** 67,73 ****
  
  static reloc_howto_type elf32_arm_howto_table_1[] =
  {
!   /* No relocation */
    HOWTO (R_ARM_NONE,		/* type */
  	 0,			/* rightshift */
  	 0,			/* size (0 = byte, 1 = short, 2 = long) */
--- 67,73 ----
  
  static reloc_howto_type elf32_arm_howto_table_1[] =
  {
!   /* No relocation.  */
    HOWTO (R_ARM_NONE,		/* type */
  	 0,			/* rightshift */
  	 0,			/* size (0 = byte, 1 = short, 2 = long) */
*************** static reloc_howto_type elf32_arm_howto_
*** 1347,1353 ****
  	 0x040f70ff,		/* dst_mask */
  	 FALSE),		/* pcrel_offset */
  
!   EMPTY_HOWTO (90),   /* unallocated */
    EMPTY_HOWTO (91),
    EMPTY_HOWTO (92),
    EMPTY_HOWTO (93),
--- 1347,1353 ----
  	 0x040f70ff,		/* dst_mask */
  	 FALSE),		/* pcrel_offset */
  
!   EMPTY_HOWTO (90),   /* Unallocated.  */
    EMPTY_HOWTO (91),
    EMPTY_HOWTO (92),
    EMPTY_HOWTO (93),
*************** elf32_arm_reloc_type_lookup (bfd *abfd A
*** 1778,1783 ****
--- 1778,1784 ----
  			     bfd_reloc_code_real_type code)
  {
    unsigned int i;
+ 
    for (i = 0; i < ARRAY_SIZE (elf32_arm_reloc_map); i ++)
      if (elf32_arm_reloc_map[i].bfd_reloc_val == code)
        return elf32_arm_howto_from_type (elf32_arm_reloc_map[i].elf_reloc_val);
*************** elf32_arm_nabi_grok_prstatus (bfd *abfd,
*** 1817,1823 ****
        default:
  	return FALSE;
  
!       case 148:		/* Linux/ARM 32-bit*/
  	/* pr_cursig */
  	elf_tdata (abfd)->core_signal = bfd_get_16 (abfd, note->descdata + 12);
  
--- 1818,1824 ----
        default:
  	return FALSE;
  
!       case 148:		/* Linux/ARM 32-bit.  */
  	/* pr_cursig */
  	elf_tdata (abfd)->core_signal = bfd_get_16 (abfd, note->descdata + 12);
  
*************** elf32_arm_nabi_grok_psinfo (bfd *abfd, E
*** 1844,1850 ****
        default:
  	return FALSE;
  
!       case 124:		/* Linux/ARM elf_prpsinfo */
  	elf_tdata (abfd)->core_program
  	 = _bfd_elfcore_strndup (abfd, note->descdata + 28, 16);
  	elf_tdata (abfd)->core_command
--- 1845,1851 ----
        default:
  	return FALSE;
  
!       case 124:		/* Linux/ARM elf_prpsinfo.  */
  	elf_tdata (abfd)->core_program
  	 = _bfd_elfcore_strndup (abfd, note->descdata + 28, 16);
  	elf_tdata (abfd)->core_command
*************** struct elf32_arm_link_hash_entry
*** 2244,2250 ****
      struct elf_link_hash_entry *export_glue;
  
     /* A pointer to the most recently used stub hash entry against this
!      symbol. */
      struct elf32_arm_stub_hash_entry *stub_cache;
    };
  
--- 2245,2251 ----
      struct elf_link_hash_entry *export_glue;
  
     /* A pointer to the most recently used stub hash entry against this
!      symbol.  */
      struct elf32_arm_stub_hash_entry *stub_cache;
    };
  
*************** arm_type_of_stub (struct bfd_link_info *
*** 2766,2772 ****
    enum elf32_arm_stub_type stub_type = arm_stub_none;
  
    /* We don't know the actual type of destination in case it is of
!      type STT_SECTION: give up */
    if (st_type == STT_SECTION)
      return stub_type;
  
--- 2767,2773 ----
    enum elf32_arm_stub_type stub_type = arm_stub_none;
  
    /* We don't know the actual type of destination in case it is of
!      type STT_SECTION: give up.  */
    if (st_type == STT_SECTION)
      return stub_type;
  
*************** elf32_arm_add_stub (const char *stub_nam
*** 3015,3022 ****
     elf32_arm_write_section.  */
  
  static void
! put_arm_insn (struct elf32_arm_link_hash_table *htab,
! 	     bfd * output_bfd, bfd_vma val, void * ptr)
  {
    if (htab->byteswap_code != bfd_little_endian (output_bfd))
      bfd_putl32 (val, ptr);
--- 3016,3023 ----
     elf32_arm_write_section.  */
  
  static void
! put_arm_insn (struct elf32_arm_link_hash_table * htab,
! 	      bfd * output_bfd, bfd_vma val, void * ptr)
  {
    if (htab->byteswap_code != bfd_little_endian (output_bfd))
      bfd_putl32 (val, ptr);
*************** put_arm_insn (struct elf32_arm_link_hash
*** 3028,3035 ****
     elf32_arm_write_section.  */
  
  static void
! put_thumb_insn (struct elf32_arm_link_hash_table *htab,
! 	       bfd * output_bfd, bfd_vma val, void * ptr)
  {
    if (htab->byteswap_code != bfd_little_endian (output_bfd))
      bfd_putl16 (val, ptr);
--- 3029,3036 ----
     elf32_arm_write_section.  */
  
  static void
! put_thumb_insn (struct elf32_arm_link_hash_table * htab,
! 		bfd * output_bfd, bfd_vma val, void * ptr)
  {
    if (htab->byteswap_code != bfd_little_endian (output_bfd))
      bfd_putl16 (val, ptr);
*************** elf32_arm_build_stubs (struct bfd_link_i
*** 3716,3722 ****
      {
        bfd_size_type size;
  
!       /* Ignore non-stub sections */
        if (!strstr (stub_sec->name, STUB_SUFFIX))
  	continue;
  
--- 3717,3723 ----
      {
        bfd_size_type size;
  
!       /* Ignore non-stub sections.  */
        if (!strstr (stub_sec->name, STUB_SUFFIX))
  	continue;
  
*************** find_arm_glue (struct bfd_link_info *lin
*** 3826,3833 ****
     add r12, r12, pc
     bx  r12
     __func_offset:
!    .word func - .
!    */
  
  #define ARM2THUMB_STATIC_GLUE_SIZE 12
  static const insn32 a2t1_ldr_insn = 0xe59fc000;
--- 3827,3833 ----
     add r12, r12, pc
     bx  r12
     __func_offset:
!    .word func - .   */
  
  #define ARM2THUMB_STATIC_GLUE_SIZE 12
  static const insn32 a2t1_ldr_insn = 0xe59fc000;
*************** static const insn32 a2t3p_bx_r12_insn = 
*** 3845,3863 ****
  
  /* Thumb->ARM:                          Thumb->(non-interworking aware) ARM
  
!    .thumb                               .thumb
!    .align 2                             .align 2
!    __func_from_thumb:              __func_from_thumb:
!    bx pc                                push {r6, lr}
!    nop                                  ldr  r6, __func_addr
!    .arm                                         mov  lr, pc
!    __func_change_to_arm:                        bx   r6
!    b func                       .arm
!    __func_back_to_thumb:
!    ldmia r13! {r6, lr}
!    bx    lr
!    __func_addr:
!    .word        func  */
  
  #define THUMB2ARM_GLUE_SIZE 8
  static const insn16 t2a1_bx_pc_insn = 0x4778;
--- 3845,3862 ----
  
  /* Thumb->ARM:                          Thumb->(non-interworking aware) ARM
  
!      .thumb                             .thumb
!      .align 2                           .align 2
!  __func_from_thumb:                 __func_from_thumb:
!      bx pc                              push {r6, lr}
!      nop                                ldr  r6, __func_addr
!      .arm                               mov  lr, pc
!      b func                             bx   r6
!  ;; back_to_thumb                       .arm
!      ldmia r13! {r6, lr}                ldmia r13! {r6, lr}
!      bx    lr  				bx    lr
!                                     __func_addr:
!                                         .word        func  */
  
  #define THUMB2ARM_GLUE_SIZE 8
  static const insn16 t2a1_bx_pc_insn = 0x4778;
*************** static const insn32 armbx2_moveq_insn = 
*** 3872,3949 ****
  static const insn32 armbx3_bx_insn = 0xe12fff10;
  
  #ifndef ELFARM_NABI_C_INCLUDED
! bfd_boolean
! bfd_elf32_arm_allocate_interworking_sections (struct bfd_link_info * info)
  {
    asection * s;
!   bfd_byte * foo;
!   struct elf32_arm_link_hash_table * globals;
! 
!   globals = elf32_arm_hash_table (info);
! 
!   BFD_ASSERT (globals != NULL);
! 
!   if (globals->arm_glue_size != 0)
!     {
!       BFD_ASSERT (globals->bfd_of_glue_owner != NULL);
! 
!       s = bfd_get_section_by_name (globals->bfd_of_glue_owner,
! 				   ARM2THUMB_GLUE_SECTION_NAME);
! 
!       BFD_ASSERT (s != NULL);
  
!       foo = bfd_alloc (globals->bfd_of_glue_owner, globals->arm_glue_size);
! 
!       BFD_ASSERT (s->size == globals->arm_glue_size);
!       s->contents = foo;
!     }
! 
!   if (globals->thumb_glue_size != 0)
!     {
!       BFD_ASSERT (globals->bfd_of_glue_owner != NULL);
! 
!       s = bfd_get_section_by_name
! 	(globals->bfd_of_glue_owner, THUMB2ARM_GLUE_SECTION_NAME);
! 
!       BFD_ASSERT (s != NULL);
  
!       foo = bfd_alloc (globals->bfd_of_glue_owner, globals->thumb_glue_size);
  
!       BFD_ASSERT (s->size == globals->thumb_glue_size);
!       s->contents = foo;
!     }
  
!   if (globals->vfp11_erratum_glue_size != 0)
!     {
!       BFD_ASSERT (globals->bfd_of_glue_owner != NULL);
  
!       s = bfd_get_section_by_name
!         (globals->bfd_of_glue_owner, VFP11_ERRATUM_VENEER_SECTION_NAME);
  
!       BFD_ASSERT (s != NULL);
  
!       foo = bfd_alloc (globals->bfd_of_glue_owner,
! 		       globals->vfp11_erratum_glue_size);
  
!       BFD_ASSERT (s->size == globals->vfp11_erratum_glue_size);
!       s->contents = foo;
!     }
  
!   if (globals->bx_glue_size != 0)
!     {
!       BFD_ASSERT (globals->bfd_of_glue_owner != NULL);
  
!       s = bfd_get_section_by_name (globals->bfd_of_glue_owner,
  				   ARM_BX_GLUE_SECTION_NAME);
  
-       BFD_ASSERT (s != NULL);
- 
-       foo = bfd_alloc (globals->bfd_of_glue_owner, globals->bx_glue_size);
- 
-       BFD_ASSERT (s->size == globals->bx_glue_size);
-       s->contents = foo;
-     }
- 
    return TRUE;
  }
  
--- 3871,3920 ----
  static const insn32 armbx3_bx_insn = 0xe12fff10;
  
  #ifndef ELFARM_NABI_C_INCLUDED
! static void
! arm_allocate_glue_section_space (bfd * abfd, bfd_size_type size, const char * name)
  {
    asection * s;
!   bfd_byte * contents;
  
!   if (size == 0)
!     return;
  
!   BFD_ASSERT (abfd != NULL);
  
!   s = bfd_get_section_by_name (abfd, name);
!   BFD_ASSERT (s != NULL);
  
!   contents = bfd_alloc (abfd, size);
  
!   BFD_ASSERT (s->size == size);
!   s->contents = contents;
! }
  
! bfd_boolean
! bfd_elf32_arm_allocate_interworking_sections (struct bfd_link_info * info)
! {
!   struct elf32_arm_link_hash_table * globals;
  
!   globals = elf32_arm_hash_table (info);
!   BFD_ASSERT (globals != NULL);
  
!   arm_allocate_glue_section_space (globals->bfd_of_glue_owner,
! 				   globals->arm_glue_size,
! 				   ARM2THUMB_GLUE_SECTION_NAME);
  
!   arm_allocate_glue_section_space (globals->bfd_of_glue_owner,
! 				   globals->thumb_glue_size,
! 				   THUMB2ARM_GLUE_SECTION_NAME);
! 
!   arm_allocate_glue_section_space (globals->bfd_of_glue_owner,
! 				   globals->vfp11_erratum_glue_size,
! 				   VFP11_ERRATUM_VENEER_SECTION_NAME);
  
!   arm_allocate_glue_section_space (globals->bfd_of_glue_owner,
! 				   globals->bx_glue_size,
  				   ARM_BX_GLUE_SECTION_NAME);
  
    return TRUE;
  }
  
*************** record_thumb_to_arm_glue (struct bfd_lin
*** 4096,4103 ****
  
    s->size += THUMB2ARM_GLUE_SIZE;
    hash_table->thumb_glue_size += THUMB2ARM_GLUE_SIZE;
- 
-   return;
  }
  
  
--- 4067,4072 ----
*************** record_vfp11_erratum_veneer (struct bfd_
*** 4311,4316 ****
--- 4280,4316 ----
    return val;
  }
  
+ /* Note: we do not include the flag SEC_LINKER_CREATED, as that
+    would prevent elf_link_input_bfd() from processing the contents
+    of the section.  */
+ #define ARM_GLUE_SECTION_FLAGS \
+   (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY | SEC_CODE | SEC_READONLY)
+ 
+ /* Create a fake section for use by the ARM backend of the linker.  */
+ 
+ static bfd_boolean
+ arm_make_glue_section (bfd * abfd, const char * name)
+ {
+   asection * sec;
+ 
+   sec = bfd_get_section_by_name (abfd, name);
+   if (sec != NULL)
+     /* Already made.  */
+     return TRUE;
+ 
+   sec = bfd_make_section_with_flags (abfd, name, ARM_GLUE_SECTION_FLAGS);
+ 
+   if (sec == NULL
+       || !bfd_set_section_alignment (abfd, sec, 2))
+     return FALSE;
+ 
+   /* Set the gc mark to prevent the section from being removed by garbage
+      collection, despite the fact that no relocs refer to this section.  */
+   sec->gc_mark = 1;
+ 
+   return TRUE;
+ }
+ 
  /* Add the glue sections to ABFD.  This function is called from the
     linker scripts in ld/emultempl/{armelf}.em.  */
  
*************** bfd_boolean
*** 4318,4418 ****
  bfd_elf32_arm_add_glue_sections_to_bfd (bfd *abfd,
  					struct bfd_link_info *info)
  {
-   flagword flags;
-   asection *sec;
- 
    /* If we are only performing a partial
       link do not bother adding the glue.  */
    if (info->relocatable)
      return TRUE;
  
!   /* linker stubs don't need glue */
    if (!strcmp (abfd->filename, "linker stubs"))
      return TRUE;
  
!   sec = bfd_get_section_by_name (abfd, ARM2THUMB_GLUE_SECTION_NAME);
! 
!   if (sec == NULL)
!     {
!       /* Note: we do not include the flag SEC_LINKER_CREATED, as this
! 	 will prevent elf_link_input_bfd() from processing the contents
! 	 of this section.  */
!       flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
! 	       | SEC_CODE | SEC_READONLY);
! 
!       sec = bfd_make_section_with_flags (abfd,
! 					 ARM2THUMB_GLUE_SECTION_NAME,
! 					 flags);
! 
!       if (sec == NULL
! 	  || !bfd_set_section_alignment (abfd, sec, 2))
! 	return FALSE;
! 
!       /* Set the gc mark to prevent the section from being removed by garbage
! 	 collection, despite the fact that no relocs refer to this section.  */
!       sec->gc_mark = 1;
!     }
! 
!   sec = bfd_get_section_by_name (abfd, THUMB2ARM_GLUE_SECTION_NAME);
! 
!   if (sec == NULL)
!     {
!       flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
! 	       | SEC_CODE | SEC_READONLY);
! 
!       sec = bfd_make_section_with_flags (abfd,
! 					 THUMB2ARM_GLUE_SECTION_NAME,
! 					 flags);
! 
!       if (sec == NULL
! 	  || !bfd_set_section_alignment (abfd, sec, 2))
! 	return FALSE;
! 
!       sec->gc_mark = 1;
!     }
! 
!   sec = bfd_get_section_by_name (abfd, VFP11_ERRATUM_VENEER_SECTION_NAME);
! 
!   if (sec == NULL)
!     {
!       flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
! 	       | SEC_CODE | SEC_READONLY);
! 
!       sec = bfd_make_section_with_flags (abfd,
! 					 VFP11_ERRATUM_VENEER_SECTION_NAME,
!                                          flags);
! 
!       if (sec == NULL
! 	  || !bfd_set_section_alignment (abfd, sec, 2))
! 	return FALSE;
! 
!       sec->gc_mark = 1;
!     }
! 
!   sec = bfd_get_section_by_name (abfd, ARM_BX_GLUE_SECTION_NAME);
! 
!   if (sec == NULL)
!     {
!       flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
! 	       | SEC_CODE | SEC_READONLY);
! 
!       sec = bfd_make_section_with_flags (abfd,
! 					 ARM_BX_GLUE_SECTION_NAME,
!                                          flags);
! 
!       if (sec == NULL
! 	  || !bfd_set_section_alignment (abfd, sec, 2))
! 	return FALSE;
! 
!       sec->gc_mark = 1;
!     }
! 
!   return TRUE;
  }
  
  /* Select a BFD to be used to hold the sections used by the glue code.
     This function is called from the linker scripts in ld/emultempl/
!    {armelf/pe}.em  */
  
  bfd_boolean
  bfd_elf32_arm_get_bfd_for_interworking (bfd *abfd, struct bfd_link_info *info)
--- 4318,4341 ----
  bfd_elf32_arm_add_glue_sections_to_bfd (bfd *abfd,
  					struct bfd_link_info *info)
  {
    /* If we are only performing a partial
       link do not bother adding the glue.  */
    if (info->relocatable)
      return TRUE;
  
!   /* Linker stubs don't need glue.  */
    if (!strcmp (abfd->filename, "linker stubs"))
      return TRUE;
  
!   return arm_make_glue_section (abfd, ARM2THUMB_GLUE_SECTION_NAME)
!     && arm_make_glue_section (abfd, THUMB2ARM_GLUE_SECTION_NAME)
!     && arm_make_glue_section (abfd, VFP11_ERRATUM_VENEER_SECTION_NAME)
!     && arm_make_glue_section (abfd, ARM_BX_GLUE_SECTION_NAME);
  }
  
  /* Select a BFD to be used to hold the sections used by the glue code.
     This function is called from the linker scripts in ld/emultempl/
!    {armelf/pe}.em.  */
  
  bfd_boolean
  bfd_elf32_arm_get_bfd_for_interworking (bfd *abfd, struct bfd_link_info *info)
*************** elf32_arm_create_thumb_stub (struct bfd_
*** 5439,5446 ****
  			     bfd *                  output_bfd,
  			     asection *             sym_sec,
  			     bfd_vma                val,
! 			     asection		    *s,
! 			     char **error_message)
  {
    bfd_vma my_offset;
    long int ret_offset;
--- 5362,5369 ----
  			     bfd *                  output_bfd,
  			     asection *             sym_sec,
  			     bfd_vma                val,
! 			     asection *             s,
! 			     char **                error_message)
  {
    bfd_vma my_offset;
    long int ret_offset;
*************** elf32_arm_create_thumb_stub (struct bfd_
*** 5515,5520 ****
--- 5438,5445 ----
  	  /* It's a thumb address.  Add the low order bit.  */
  	  bfd_put_32 (output_bfd, val | a2t3_func_addr_insn,
  		      s->contents + my_offset + 8);
+ 
+ 	  my_offset += 12;
  	}
      }
  
*************** elf32_arm_to_thumb_export_stub (struct e
*** 5617,5622 ****
--- 5542,5548 ----
  
    val = eh->export_glue->root.u.def.value + sec->output_offset
  	+ sec->output_section->vma;
+ 
    myh = elf32_arm_create_thumb_stub (info, h->root.root.string,
  				     h->root.u.def.section->owner,
  				     globals->obfd, sec, val, s,
*************** elf32_arm_begin_write_processing (bfd *a
*** 5669,5675 ****
  {
    struct elf32_arm_link_hash_table * globals;
  
!   if (!link_info)
      return;
  
    globals = elf32_arm_hash_table (link_info);
--- 5595,5602 ----
  {
    struct elf32_arm_link_hash_table * globals;
  
!   if (link_info == NULL)
!     /* Ignore this if we are not called by the ELF backend linker.  */
      return;
  
    globals = elf32_arm_hash_table (link_info);
*************** elf32_arm_begin_write_processing (bfd *a
*** 5684,5689 ****
--- 5611,5617 ----
  
  /* Some relocations map to different relocations depending on the
     target.  Return the real relocation.  */
+ 
  static int
  arm_real_reloc_type (struct elf32_arm_link_hash_table * globals,
  		     int r_type)
*************** elf32_arm_final_link_relocate (reloc_how
*** 5832,5838 ****
  			       int		            sym_flags,
  			       struct elf_link_hash_entry * h,
  			       bfd_boolean *                unresolved_reloc_p,
! 			       char **error_message)
  {
    unsigned long                 r_type = howto->type;
    unsigned long                 r_symndx;
--- 5760,5766 ----
  			       int		            sym_flags,
  			       struct elf_link_hash_entry * h,
  			       bfd_boolean *                unresolved_reloc_p,
! 			       char **                      error_message)
  {
    unsigned long                 r_type = howto->type;
    unsigned long                 r_symndx;
*************** elf32_arm_final_link_relocate (reloc_how
*** 6082,6088 ****
  	case R_ARM_XPC25:	  /* Arm BLX instruction.  */
  	case R_ARM_CALL:
  	case R_ARM_JUMP24:
! 	case R_ARM_PC24:	  /* Arm B/BL instruction */
  	case R_ARM_PLT32:
  	  {
  	  bfd_vma from;
--- 6010,6016 ----
  	case R_ARM_XPC25:	  /* Arm BLX instruction.  */
  	case R_ARM_CALL:
  	case R_ARM_JUMP24:
! 	case R_ARM_PC24:	  /* Arm B/BL instruction.  */
  	case R_ARM_PLT32:
  	  {
  	  bfd_vma from;
*************** elf32_arm_final_link_relocate (reloc_how
*** 6122,6128 ****
  	    }
  
  	  /* Check if a stub has to be inserted because the
! 	     destination is too far or we are changing mode */
  	  if (r_type == R_ARM_CALL)
  	    {
  	      if (branch_offset > ARM_MAX_FWD_BRANCH_OFFSET
--- 6050,6056 ----
  	    }
  
  	  /* Check if a stub has to be inserted because the
! 	     destination is too far or we are changing mode.  */
  	  if (r_type == R_ARM_CALL)
  	    {
  	      if (branch_offset > ARM_MAX_FWD_BRANCH_OFFSET
*************** elf32_arm_final_link_relocate (reloc_how
*** 6204,6210 ****
  		{
  		  /* Select the correct instruction (BL or BLX).  */
  		  /* Only if we are not handling a BL to a stub. In this
! 		     case, mode switching is performed by the stub. */
  		  if (sym_flags == STT_ARM_TFUNC && !stub_entry)
  		    value |= (1 << 28);
  		  else
--- 6132,6138 ----
  		{
  		  /* Select the correct instruction (BL or BLX).  */
  		  /* Only if we are not handling a BL to a stub. In this
! 		     case, mode switching is performed by the stub.  */
  		  if (sym_flags == STT_ARM_TFUNC && !stub_entry)
  		    value |= (1 << 28);
  		  else
*************** elf32_arm_final_link_relocate (reloc_how
*** 6247,6253 ****
  	  value += signed_addend;
  	  if (! h || h->root.type != bfd_link_hash_undefweak)
  	    {
! 	      /* Check for overflow */
  	      if ((value ^ (value >> 1)) & (1 << 30))
  		return bfd_reloc_overflow;
  	    }
--- 6175,6181 ----
  	  value += signed_addend;
  	  if (! h || h->root.type != bfd_link_hash_undefweak)
  	    {
! 	      /* Check for overflow.  */
  	      if ((value ^ (value >> 1)) & (1 << 30))
  		return bfd_reloc_overflow;
  	    }
*************** elf32_arm_final_link_relocate (reloc_how
*** 6444,6458 ****
  		    /* Convert BL to BLX.  */
  		    lower_insn = (lower_insn & ~0x1000) | 0x0800;
  		  }
! 		else if (r_type != R_ARM_THM_CALL) {
! 		  if (elf32_thumb_to_arm_stub
! 		    (info, sym_name, input_bfd, output_bfd, input_section,
! 		     hit_data, sym_sec, rel->r_offset, signed_addend, value,
! 		     error_message))
! 		  return bfd_reloc_ok;
! 		else
! 		  return bfd_reloc_dangerous;
! 	      }
  	      }
  	    else if (sym_flags == STT_ARM_TFUNC && globals->use_blx
  		     && r_type == R_ARM_THM_CALL)
--- 6372,6387 ----
  		    /* Convert BL to BLX.  */
  		    lower_insn = (lower_insn & ~0x1000) | 0x0800;
  		  }
! 		else if (r_type != R_ARM_THM_CALL)
! 		  {
! 		    if (elf32_thumb_to_arm_stub
! 			(info, sym_name, input_bfd, output_bfd, input_section,
! 			 hit_data, sym_sec, rel->r_offset, signed_addend, value,
! 			 error_message))
! 		      return bfd_reloc_ok;
! 		    else
! 		      return bfd_reloc_dangerous;
! 		  }
  	      }
  	    else if (sym_flags == STT_ARM_TFUNC && globals->use_blx
  		     && r_type == R_ARM_THM_CALL)
*************** elf32_arm_final_link_relocate (reloc_how
*** 6483,6489 ****
  	if (r_type == R_ARM_THM_CALL)
  	  {
  	    /* Check if a stub has to be inserted because the destination
! 	       is too far. */
  	    bfd_vma from;
  	    bfd_signed_vma branch_offset;
  	    struct elf32_arm_stub_hash_entry *stub_entry = NULL;
--- 6412,6418 ----
  	if (r_type == R_ARM_THM_CALL)
  	  {
  	    /* Check if a stub has to be inserted because the destination
! 	       is too far.  */
  	    bfd_vma from;
  	    bfd_signed_vma branch_offset;
  	    struct elf32_arm_stub_hash_entry *stub_entry = NULL;
*************** elf32_arm_relocate_section (bfd *       
*** 8007,8013 ****
  
  	    default:
  	      error_message = _("unknown error");
! 	      /* fall through */
  
  	    common_error:
  	      BFD_ASSERT (error_message != NULL);
--- 7936,7942 ----
  
  	    default:
  	      error_message = _("unknown error");
! 	      /* Fall through.  */
  
  	    common_error:
  	      BFD_ASSERT (error_message != NULL);
*************** elf32_arm_merge_private_bfd_data (bfd * 
*** 8466,8472 ****
        && !(ibfd->flags & DYNAMIC)
        && (in_flags & EF_ARM_BE8))
      {
!       _bfd_error_handler (_("ERROR: %B is already in final BE8 format"), 
  			  ibfd);
        return FALSE;
      }
--- 8395,8401 ----
        && !(ibfd->flags & DYNAMIC)
        && (in_flags & EF_ARM_BE8))
      {
!       _bfd_error_handler (_("ERROR: %B is already in final BE8 format"),
  			  ibfd);
        return FALSE;
      }
*************** elf32_arm_check_relocs (bfd *abfd, struc
*** 9097,9108 ****
  		    elf32_arm_local_got_tls_type (abfd) [r_symndx] = tls_type;
  		}
  	    }
! 	    /* Fall through */
  
  	  case R_ARM_TLS_LDM32:
  	    if (r_type == R_ARM_TLS_LDM32)
  		htab->tls_ldm_got.refcount++;
! 	    /* Fall through */
  
  	  case R_ARM_GOTOFF32:
  	  case R_ARM_GOTPC:
--- 9026,9037 ----
  		    elf32_arm_local_got_tls_type (abfd) [r_symndx] = tls_type;
  		}
  	    }
! 	    /* Fall through.  */
  
  	  case R_ARM_TLS_LDM32:
  	    if (r_type == R_ARM_TLS_LDM32)
  		htab->tls_ldm_got.refcount++;
! 	    /* Fall through.  */
  
  	  case R_ARM_GOTOFF32:
  	  case R_ARM_GOTPC:
*************** elf32_arm_check_relocs (bfd *abfd, struc
*** 9120,9126 ****
  	       ldr __GOTT_INDEX__ offsets.  */
  	    if (!htab->vxworks_p)
  	      break;
! 	    /* Fall through */
  
  	  case R_ARM_PC24:
  	  case R_ARM_PLT32:
--- 9049,9055 ----
  	       ldr __GOTT_INDEX__ offsets.  */
  	    if (!htab->vxworks_p)
  	      break;
! 	    /* Fall through.  */
  
  	  case R_ARM_PC24:
  	  case R_ARM_PLT32:
*************** allocate_dynrelocs (struct elf_link_hash
*** 9960,9969 ****
  /* Find any dynamic relocs that apply to read-only sections.  */
  
  static bfd_boolean
! elf32_arm_readonly_dynrelocs (struct elf_link_hash_entry *h, PTR inf)
  {
!   struct elf32_arm_link_hash_entry *eh;
!   struct elf32_arm_relocs_copied *p;
  
    if (h->root.type == bfd_link_hash_warning)
      h = (struct elf_link_hash_entry *) h->root.u.i.link;
--- 9889,9898 ----
  /* Find any dynamic relocs that apply to read-only sections.  */
  
  static bfd_boolean
! elf32_arm_readonly_dynrelocs (struct elf_link_hash_entry * h, void * inf)
  {
!   struct elf32_arm_link_hash_entry * eh;
!   struct elf32_arm_relocs_copied * p;
  
    if (h->root.type == bfd_link_hash_warning)
      h = (struct elf_link_hash_entry *) h->root.u.i.link;
*************** elf32_arm_size_dynamic_sections (bfd * o
*** 10248,10255 ****
        /* If any dynamic relocs apply to a read-only section,
  	 then we need a DT_TEXTREL entry.  */
        if ((info->flags & DF_TEXTREL) == 0)
! 	elf_link_hash_traverse (&htab->root, elf32_arm_readonly_dynrelocs,
! 				(PTR) info);
  
        if ((info->flags & DF_TEXTREL) != 0)
  	{
--- 10177,10184 ----
        /* If any dynamic relocs apply to a read-only section,
  	 then we need a DT_TEXTREL entry.  */
        if ((info->flags & DF_TEXTREL) == 0)
! 	elf_link_hash_traverse (& htab->root, elf32_arm_readonly_dynrelocs,
! 				info);
  
        if ((info->flags & DF_TEXTREL) != 0)
  	{
*************** elf32_arm_finish_dynamic_sections (bfd *
*** 10678,10684 ****
  		  bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
  		  break;
  		}
! 	      /* Fall through */
  
  	    case DT_REL:
  	    case DT_RELA:
--- 10607,10613 ----
  		  bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
  		  break;
  		}
! 	      /* Fall through.  */
  
  	    case DT_REL:
  	    case DT_RELA:
*************** elf32_arm_finish_dynamic_sections (bfd *
*** 10767,10773 ****
  			    splt->contents + 8);
  	      bfd_put_32 (output_bfd, got_address, splt->contents + 12);
  
! 	      /* Generate a relocation for _GLOBAL_OFFSET_TABLE_. */
  	      rel.r_offset = plt_address + 12;
  	      rel.r_info = ELF32_R_INFO (htab->root.hgot->indx, R_ARM_ABS32);
  	      rel.r_addend = 0;
--- 10696,10702 ----
  			    splt->contents + 8);
  	      bfd_put_32 (output_bfd, got_address, splt->contents + 12);
  
! 	      /* Generate a relocation for _GLOBAL_OFFSET_TABLE_.  */
  	      rel.r_offset = plt_address + 12;
  	      rel.r_info = ELF32_R_INFO (htab->root.hgot->indx, R_ARM_ABS32);
  	      rel.r_addend = 0;
*************** elf32_arm_output_stub_sym (output_arch_s
*** 11212,11219 ****
  }
  
  static bfd_boolean
! arm_map_one_stub (struct bfd_hash_entry *gen_entry,
! 		  PTR in_arg)
  {
    struct elf32_arm_stub_hash_entry *stub_entry;
    struct bfd_link_info *info;
--- 11141,11148 ----
  }
  
  static bfd_boolean
! arm_map_one_stub (struct bfd_hash_entry * gen_entry,
! 		  void * in_arg)
  {
    struct elf32_arm_stub_hash_entry *stub_entry;
    struct bfd_link_info *info;
*************** elf32_arm_output_arch_local_syms (bfd *o
*** 11366,11397 ****
        elf32_arm_output_map_sym (&osi, ARM_MAP_ARM, 0);
      }
  
!   /* Long calls stubs. */
!   if (htab->stub_bfd && htab->stub_bfd->sections) {
        asection* stub_sec;
        for (stub_sec = htab->stub_bfd->sections;
  	   stub_sec != NULL;
! 	   stub_sec = stub_sec->next) {
! 
! 	/* Ignore non-stub sections */
! 	if (!strstr(stub_sec->name, STUB_SUFFIX))
! 	  continue;
  
! 	osi.sec = stub_sec;
  
! 	osi.sec_shndx = _bfd_elf_section_from_bfd_section
! 	  (output_bfd, osi.sec->output_section);
  
! 	bfd_hash_traverse (&htab->stub_hash_table, arm_map_one_stub, &osi);
!       }
!   }
  
    /* Finally, output mapping symbols for the PLT.  */
    if (!htab->splt || htab->splt->size == 0)
      return TRUE;
  
    osi.sec_shndx = _bfd_elf_section_from_bfd_section (output_bfd,
!       htab->splt->output_section);
    osi.sec = htab->splt;
    /* Output mapping symbols for the plt header.  SymbianOS does not have a
       plt header.  */
--- 11295,11328 ----
        elf32_arm_output_map_sym (&osi, ARM_MAP_ARM, 0);
      }
  
!   /* Long calls stubs.  */
!   if (htab->stub_bfd && htab->stub_bfd->sections)
!     {
        asection* stub_sec;
+ 
        for (stub_sec = htab->stub_bfd->sections;
  	   stub_sec != NULL;
! 	   stub_sec = stub_sec->next)
! 	{
! 	  /* Ignore non-stub sections.  */
! 	  if (!strstr (stub_sec->name, STUB_SUFFIX))
! 	    continue;
  
! 	  osi.sec = stub_sec;
  
! 	  osi.sec_shndx = _bfd_elf_section_from_bfd_section
! 	    (output_bfd, osi.sec->output_section);
  
! 	  bfd_hash_traverse (&htab->stub_hash_table, arm_map_one_stub, &osi);
! 	}
!     }
  
    /* Finally, output mapping symbols for the PLT.  */
    if (!htab->splt || htab->splt->size == 0)
      return TRUE;
  
    osi.sec_shndx = _bfd_elf_section_from_bfd_section (output_bfd,
! 						     htab->splt->output_section);
    osi.sec = htab->splt;
    /* Output mapping symbols for the plt header.  SymbianOS does not have a
       plt header.  */
*************** elf32_arm_compare_mapping (const void * 
*** 11471,11477 ****
  
  static bfd_boolean
  elf32_arm_write_section (bfd *output_bfd,
! 			 struct bfd_link_info *link_info, asection *sec,
  			 bfd_byte *contents)
  {
    int mapcount, errcount;
--- 11402,11409 ----
  
  static bfd_boolean
  elf32_arm_write_section (bfd *output_bfd,
! 			 struct bfd_link_info *link_info,
! 			 asection *sec,
  			 bfd_byte *contents)
  {
    int mapcount, errcount;
*************** elf32_arm_symbian_plt_sym_val (bfd_vma i
*** 12075,12081 ****
  }
  
  
! #undef elf32_bed
  #define elf32_bed elf32_arm_symbian_bed
  
  /* The dynamic sections are not allocated on SymbianOS; the postlinker
--- 12007,12013 ----
  }
  
  
! #undef  elf32_bed
  #define elf32_bed elf32_arm_symbian_bed
  
  /* The dynamic sections are not allocated on SymbianOS; the postlinker

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]