Fix overflow handling of VLE_SDA21

Alan Modra amodra@gmail.com
Fri Mar 14 04:30:00 GMT 2014


What was I thinking?  "do so with a value that won't modify the insn"
would require
	relocation = ((insn & 0xffff) ^ 0x8000) - 0x8000;
We may as well do this the obvious way.  Also, the overflow test
was wrong when bfd_vma is 64-bit.

bfd/
	* elf32-ppc.c (ppc_elf_relocate_section): Correct overflow
	handling for VLE_SDA21 relocs.
ld/testsuite/
	* ld-powerpc/vle.ld: Place .PPC.EMB.sdata0 within 32k of 0.
	* ld-powerpc/vle-reloc-3.d: Update.

diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c
index 750aa5e..868fe50 100644
--- a/bfd/elf32-ppc.c
+++ b/bfd/elf32-ppc.c
@@ -8859,11 +8859,12 @@ ppc_elf_relocate_section (bfd *output_bfd,
 		/* And the final 11 bits of the value to bits 21 to 31.  */
 		insn |= relocation & 0x7ff;
 
-		/* Use _bfd_final_link_relocate to report overflow,
-		   but do so with a value that won't modify the insn.  */
-		if (relocation + 0x80000 > 0x100000)
-		  addend = 0x100000;
-		relocation = 0;
+		bfd_put_32 (output_bfd, insn, contents + rel->r_offset);
+
+		if (r_type == R_PPC_VLE_SDA21
+		    && ((relocation + 0x80000) & 0xffffffff) > 0x100000)
+		  goto overflow;
+		continue;
 	      }
 	    else if (r_type == R_PPC_EMB_SDA21
 		     || r_type == R_PPC_VLE_SDA21
@@ -9160,6 +9161,7 @@ ppc_elf_relocate_section (bfd *output_bfd,
 	{
 	  if (r == bfd_reloc_overflow)
 	    {
+	    overflow:
 	      if (warned)
 		continue;
 	      if (h != NULL
diff --git a/ld/testsuite/ld-powerpc/vle-reloc-3.d b/ld/testsuite/ld-powerpc/vle-reloc-3.d
index e29f4f0..584c483 100644
--- a/ld/testsuite/ld-powerpc/vle-reloc-3.d
+++ b/ld/testsuite/ld-powerpc/vle-reloc-3.d
@@ -5,4 +5,4 @@ Disassembly of section .text:
 01800094 <sda21_test>:
  1800094:	1c ad 80 08 	e_add16i r5,r13,-32760
  1800098:	1c a2 80 04 	e_add16i r5,r2,-32764
- 180009c:	70 00 00 ac 	e_li    r0,172
+ 180009c:	70 b0 78 04 	e_li    r5,-32764
diff --git a/ld/testsuite/ld-powerpc/vle.ld b/ld/testsuite/ld-powerpc/vle.ld
index 01b6598..ff92a05 100644
--- a/ld/testsuite/ld-powerpc/vle.ld
+++ b/ld/testsuite/ld-powerpc/vle.ld
@@ -2,10 +2,11 @@ SECTIONS
 {
   . = 0x01800000 + SIZEOF_HEADERS;
   .text : { *(.text) }
-  .PPC.EMB.sdata0 : { *(.PPC.EMB.sdata0) }
   .sdata2 : { PROVIDE (_SDA2_BASE_ = 32768); *(.sdata2) }
   . = ALIGN (0x10000) + (. & (0x10000 - 1));
   .data : { *(.data) }
   .sdata : { PROVIDE (_SDA_BASE_ = 32768); *(.sdata) }
+  . = 0xffff8000;
+  .PPC.EMB.sdata0 : { *(.PPC.EMB.sdata0) }
   /DISCARD/ : { *(*) }
 }

-- 
Alan Modra
Australia Development Lab, IBM



More information about the Binutils mailing list