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]

[Xtensa Patch] Fixup the bits during a relocatable link


The Xtensa version of ld does extensive link-time relaxation. Until now, when it modified a section, it would only change the relevant relocations, but not actual bits in the relevant instructions. Normally a final link would do that part of the work.

However, linux-kernel loadable modules never go through final links, so linker-relaxation didn't work with kernel loadable modules because the instructions were stale vs the relocations describing them.

I have committed the attached patch which fixes this problem. It is now possible to use linker relaxation on kernel loadable modules for Xtensa.

Sterling
sterling@tensilica.com

2010-05-28 Sterling Augustine <sterling@tensilica.com>

        * elf32-xtensa.c (elf_xtensa_relocate_section): Add a
	large amount of code to change the bits in the
        instructions to match the changes in the relocations.
	Declare dest_addr and sym_sec to help.

Index: elf32-xtensa.c
===================================================================
RCS file: /cvs/src/src/bfd/elf32-xtensa.c,v
retrieving revision 1.121
diff -u -p -c -r1.121 elf32-xtensa.c
cvs diff: conflicting specifications of output style
*** elf32-xtensa.c	8 Feb 2010 13:16:24 -0000	1.121
--- elf32-xtensa.c	28 May 2010 18:03:57 -0000
*************** elf_xtensa_relocate_section (bfd *output
*** 2672,2677 ****
--- 2672,2680 ----
  
        if (info->relocatable)
  	{
+ 	  bfd_vma dest_addr;
+ 	  asection * sym_sec = get_elf_r_symndx_section (input_bfd, r_symndx);
+ 
  	  /* This is a relocatable link.
  	     1) If the reloc is against a section symbol, adjust
  	     according to the output section.
*************** elf_xtensa_relocate_section (bfd *output
*** 2688,2693 ****
--- 2691,2699 ----
  		return FALSE;
  	    }
  
+ 	  dest_addr = sym_sec->output_section->vma + sym_sec->output_offset
+ 	    + get_elf_r_symndx_offset (input_bfd, r_symndx) + rel->r_addend;
+ 
  	  if (r_type == R_XTENSA_ASM_SIMPLIFY)
  	    {
  	      error_message = NULL;
*************** elf_xtensa_relocate_section (bfd *output
*** 2724,2748 ****
  	     to work around problems with DWARF in relocatable links
  	     with some previous version of BFD.  Now we can't easily get
  	     rid of the hack without breaking backward compatibility.... */
! 	  if (rel->r_addend)
  	    {
! 	      howto = &elf_howto_table[r_type];
! 	      if (howto->partial_inplace)
  		{
  		  r = elf_xtensa_do_reloc (howto, input_bfd, input_section,
! 					   rel->r_addend, contents,
  					   rel->r_offset, FALSE,
  					   &error_message);
- 		  if (r != bfd_reloc_ok)
- 		    {
- 		      if (!((*info->callbacks->reloc_dangerous)
- 			    (info, error_message, input_bfd, input_section,
- 			     rel->r_offset)))
- 			return FALSE;
- 		    }
- 		  rel->r_addend = 0;
  		}
  	    }
  
  	  /* Done with work for relocatable link; continue with next reloc.  */
  	  continue;
--- 2730,2770 ----
  	     to work around problems with DWARF in relocatable links
  	     with some previous version of BFD.  Now we can't easily get
  	     rid of the hack without breaking backward compatibility.... */
! 	  r = bfd_reloc_ok;
! 	  howto = &elf_howto_table[r_type];
! 	  if (howto->partial_inplace && rel->r_addend)
! 	    {
! 	      r = elf_xtensa_do_reloc (howto, input_bfd, input_section,
! 				       rel->r_addend, contents,
! 				       rel->r_offset, FALSE,
! 				       &error_message);
! 	      rel->r_addend = 0;
! 	    }
! 	  else
  	    {
! 	      /* Put the correct bits in the target instruction, even
! 		 though the relocation will still be present in the output
! 		 file.  This makes disassembly clearer, as well as
! 		 allowing loadable kernel modules to work without needing
! 		 relocations on anything other than calls and l32r's.  */
! 
! 	      /* If it is not in the same section, there is nothing we can do.  */
! 	      if (r_type >= R_XTENSA_SLOT0_OP && r_type <= R_XTENSA_SLOT14_OP &&
! 		  sym_sec->output_section == input_section->output_section)
  		{
  		  r = elf_xtensa_do_reloc (howto, input_bfd, input_section,
! 					   dest_addr, contents,
  					   rel->r_offset, FALSE,
  					   &error_message);
  		}
  	    }
+ 	  if (r != bfd_reloc_ok)
+ 	    {
+ 	      if (!((*info->callbacks->reloc_dangerous)
+ 		    (info, error_message, input_bfd, input_section,
+ 		     rel->r_offset)))
+ 		return FALSE;
+ 	    }
  
  	  /* Done with work for relocatable link; continue with next reloc.  */
  	  continue;

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