Blame SOURCES/gdb-rhbz1125820-ppc64le-enablement-14of37.patch

2c2fa1
commit 52a82034ac9a288d2d8e60efa880623288b5d228
2c2fa1
Author: Alan Modra <amodra@gmail.com>
2c2fa1
Date:   Fri Nov 1 19:25:56 2013 +1030
2c2fa1
2c2fa1
    Edit ELFv2 global entry prologue to non-PIC
2c2fa1
    
2c2fa1
    Changing addis r2,r12,..; addi r2,r2,.. to lis r2,..; addi r2,r2..
2c2fa1
    in non-PIC executables has the benefit of removing a dependency on r12.
2c2fa1
    
2c2fa1
    bfd/
2c2fa1
    	* elf64-ppc.c (ppc64_elf_relocate_section): Edit global entry
2c2fa1
    	prologue to non-PIC in non-PIC executables.
2c2fa1
    ld/testsuite/
2c2fa1
    	* ld-powerpc/elfv2exe.d: Adjust for non-PIC global entry.
2c2fa1
2c2fa1
Index: gdb-7.6.1/bfd/elf64-ppc.c
2c2fa1
===================================================================
2c2fa1
--- gdb-7.6.1.orig/bfd/elf64-ppc.c
2c2fa1
+++ gdb-7.6.1/bfd/elf64-ppc.c
2c2fa1
@@ -13280,6 +13280,39 @@ ppc64_elf_relocate_section (bfd *output_
2c2fa1
 	      rel->r_info = ELF64_R_INFO (r_symndx, r_type);
2c2fa1
 	    }
2c2fa1
 	  break;
2c2fa1
+
2c2fa1
+	case R_PPC64_REL16_HA:
2c2fa1
+	  /* If we are generating a non-PIC executable, edit
2c2fa1
+	     .	0:	addis 2,12,.TOC.-0b@ha
2c2fa1
+	     .		addi 2,2,.TOC.-0b@l
2c2fa1
+	     used by ELFv2 global entry points to set up r2, to
2c2fa1
+	     .		lis 2,.TOC.@ha
2c2fa1
+	     .		addi 2,2,.TOC.@l
2c2fa1
+	     if .TOC. is in range.  */
2c2fa1
+	  if (!info->shared
2c2fa1
+	      && h != NULL && &h->elf == htab->elf.hgot
2c2fa1
+	      && rel + 1 < relend
2c2fa1
+	      && rel[1].r_info == ELF64_R_INFO (r_symndx, R_PPC64_REL16_LO)
2c2fa1
+	      && rel[1].r_offset == rel->r_offset + 4
2c2fa1
+	      && rel[1].r_addend == rel->r_addend + 4
2c2fa1
+	      && relocation + 0x80008000 <= 0xffffffff)
2c2fa1
+	    {
2c2fa1
+	      unsigned int insn1, insn2;
2c2fa1
+	      bfd_vma offset = rel->r_offset - d_offset;
2c2fa1
+	      insn1 = bfd_get_32 (output_bfd, contents + offset);
2c2fa1
+	      insn2 = bfd_get_32 (output_bfd, contents + offset + 4);
2c2fa1
+	      if ((insn1 & 0xffff0000) == 0x3c4c0000 /* addis 2,12 */
2c2fa1
+		  && (insn2 & 0xffff0000) == 0x38420000 /* addi 2,2 */)
2c2fa1
+		{
2c2fa1
+		  r_type = R_PPC64_ADDR16_HA;
2c2fa1
+		  rel->r_info = ELF64_R_INFO (r_symndx, r_type);
2c2fa1
+		  rel->r_addend -= d_offset;
2c2fa1
+		  rel[1].r_info = ELF64_R_INFO (r_symndx, R_PPC64_ADDR16_LO);
2c2fa1
+		  rel[1].r_addend -= d_offset + 4;
2c2fa1
+		  bfd_put_32 (output_bfd, 0x3c400000, contents + offset);
2c2fa1
+		}
2c2fa1
+	    }
2c2fa1
+	  break;
2c2fa1
 	}
2c2fa1
 
2c2fa1
       /* Handle other relocations that tweak non-addend part of insn.  */