diff options
-rw-r--r-- | bfd/ChangeLog | 7 | ||||
-rw-r--r-- | bfd/elf32-ppc.c | 22 | ||||
-rw-r--r-- | bfd/elf64-ppc.c | 21 | ||||
-rw-r--r-- | ld/testsuite/ChangeLog | 5 | ||||
-rw-r--r-- | ld/testsuite/ld-powerpc/tlsso.r | 4 | ||||
-rw-r--r-- | ld/testsuite/ld-powerpc/tlsso32.r | 2 |
6 files changed, 45 insertions, 16 deletions
diff --git a/bfd/ChangeLog b/bfd/ChangeLog index aca51b8..d061625 100644 --- a/bfd/ChangeLog +++ b/bfd/ChangeLog @@ -1,3 +1,10 @@ +2003-03-11 Alan Modra <amodra@bigpond.net.au> + + * elf32-ppc.c (ppc_elf_relocate_section): Subtract tls seg vma from + zero index dynamic tls relocs generated for the GOT. Tidy code. + Set "relocation" to 1 on DTPMOD32 relocs. Optimize HA adjustment. + * elf64-ppc.c (ppc64_elf_relocate_section): Likewise. + 2003-03-07 Alan Modra <amodra@bigpond.net.au> * elf32-ppc.c (ppc_elf_relocate_section): Don't look for a nop after diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c index b7b09dc..6d54419 100644 --- a/bfd/elf32-ppc.c +++ b/bfd/elf32-ppc.c @@ -4779,10 +4779,10 @@ ppc_elf_relocate_section (output_bfd, info, input_bfd, input_section, outrel.r_offset = (htab->got->output_section->vma + htab->got->output_offset + off); + outrel.r_addend = 0; if (tls_ty & (TLS_LD | TLS_GD)) { outrel.r_info = ELF32_R_INFO (indx, R_PPC_DTPMOD32); - outrel.r_addend = 0; if (tls_ty == (TLS_TLS | TLS_GD)) { loc = htab->relgot->contents; @@ -4790,9 +4790,9 @@ ppc_elf_relocate_section (output_bfd, info, input_bfd, input_section, * sizeof (Elf32_External_Rela)); bfd_elf32_swap_reloca_out (output_bfd, &outrel, loc); + outrel.r_offset += 4; outrel.r_info = ELF32_R_INFO (indx, R_PPC_DTPREL32); - outrel.r_offset += 4; } } else if (tls_ty == (TLS_TLS | TLS_DTPREL)) @@ -4803,9 +4803,12 @@ ppc_elf_relocate_section (output_bfd, info, input_bfd, input_section, outrel.r_info = ELF32_R_INFO (indx, R_PPC_RELATIVE); else outrel.r_info = ELF32_R_INFO (indx, R_PPC_GLOB_DAT); - outrel.r_addend = 0; if (indx == 0) - outrel.r_addend += relocation; + { + outrel.r_addend += relocation; + if (tls_ty & (TLS_GD | TLS_DTPREL | TLS_TPREL)) + outrel.r_addend -= htab->tls_sec->vma; + } loc = htab->relgot->contents; loc += (htab->relgot->reloc_count++ * sizeof (Elf32_External_Rela)); @@ -4933,6 +4936,11 @@ ppc_elf_relocate_section (output_bfd, info, input_bfd, input_section, addend -= htab->tls_sec->vma + DTP_OFFSET; goto dodyn; + case R_PPC_DTPMOD32: + relocation = 1; + addend = 0; + goto dodyn; + case R_PPC_REL24: case R_PPC_REL32: case R_PPC_REL14: @@ -4959,7 +4967,6 @@ ppc_elf_relocate_section (output_bfd, info, input_bfd, input_section, case R_PPC_ADDR14_BRNTAKEN: case R_PPC_UADDR32: case R_PPC_UADDR16: - case R_PPC_DTPMOD32: /* r_symndx will be zero only for relocs against symbols from removed linkonce sections, or sections discarded by a linker script. */ @@ -5332,8 +5339,9 @@ ppc_elf_relocate_section (output_bfd, info, input_bfd, input_section, 'sec' would be NULL, and we should leave the symbol alone (it will be set to zero elsewhere in the link). */ if (sec != NULL) - /* Add 0x10000 if sign bit in 0:15 is set. */ - addend += ((relocation + addend) & 0x8000) << 1; + /* Add 0x10000 if sign bit in 0:15 is set. + Bits 0:15 are not used. */ + addend += 0x8000; break; } diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c index 1030e69..29c90fe 100644 --- a/bfd/elf64-ppc.c +++ b/bfd/elf64-ppc.c @@ -7638,8 +7638,8 @@ ppc64_elf_relocate_section (output_bfd, info, input_bfd, input_section, + off); if (tls_type & (TLS_LD | TLS_GD)) { - outrel.r_info = ELF64_R_INFO (indx, R_PPC64_DTPMOD64); outrel.r_addend = 0; + outrel.r_info = ELF64_R_INFO (indx, R_PPC64_DTPMOD64); if (tls_type == (TLS_TLS | TLS_GD)) { loc = htab->srelgot->contents; @@ -7647,9 +7647,9 @@ ppc64_elf_relocate_section (output_bfd, info, input_bfd, input_section, * sizeof (Elf64_External_Rela)); bfd_elf64_swap_reloca_out (output_bfd, &outrel, loc); + outrel.r_offset += 8; outrel.r_info = ELF64_R_INFO (indx, R_PPC64_DTPREL64); - outrel.r_offset += 8; } } else if (tls_type == (TLS_TLS | TLS_DTPREL)) @@ -7662,7 +7662,11 @@ ppc64_elf_relocate_section (output_bfd, info, input_bfd, input_section, outrel.r_info = ELF64_R_INFO (indx, R_PPC64_GLOB_DAT); outrel.r_addend = rel->r_addend; if (indx == 0) - outrel.r_addend += relocation; + { + outrel.r_addend += relocation; + if (tls_type & (TLS_GD | TLS_DTPREL | TLS_TPREL)) + outrel.r_addend -= htab->tls_sec->vma; + } loc = htab->srelgot->contents; loc += (htab->srelgot->reloc_count++ * sizeof (Elf64_External_Rela)); @@ -7798,6 +7802,11 @@ ppc64_elf_relocate_section (output_bfd, info, input_bfd, input_section, addend -= htab->tls_sec->vma + DTP_OFFSET; break; + case R_PPC64_DTPMOD64: + relocation = 1; + addend = 0; + goto dodyn; + case R_PPC64_TPREL64: addend -= htab->tls_sec->vma + TP_OFFSET; goto dodyn; @@ -7808,7 +7817,6 @@ ppc64_elf_relocate_section (output_bfd, info, input_bfd, input_section, /* Relocations that may need to be propagated if this is a dynamic object. */ - case R_PPC64_DTPMOD64: case R_PPC64_REL30: case R_PPC64_REL32: case R_PPC64_REL64: @@ -8028,8 +8036,9 @@ ppc64_elf_relocate_section (output_bfd, info, input_bfd, input_section, 'sec' would be NULL, and we should leave the symbol alone (it will be set to zero elsewhere in the link). */ if (sec != NULL) - /* Add 0x10000 if sign bit in 0:15 is set. */ - addend += ((relocation + addend) & 0x8000) << 1; + /* Add 0x10000 if sign bit in 0:15 is set. + Bits 0:15 are not used. */ + addend += 0x8000; break; case R_PPC64_ADDR16_DS: diff --git a/ld/testsuite/ChangeLog b/ld/testsuite/ChangeLog index af7a1e6..048d36e 100644 --- a/ld/testsuite/ChangeLog +++ b/ld/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2003-03-11 Alan Modra <amodra@bigpond.net.au> + + * ld-powerpc/tlsso.r: Adjust for corrected zero symbol index relocs. + * ld-powerpc/tlsso32.r: Likewise. + 2003-02-18 Alan Modra <amodra@bigpond.net.au> * ld-powerpc/tlsexe.d: Update for changed handling of invalid LD diff --git a/ld/testsuite/ld-powerpc/tlsso.r b/ld/testsuite/ld-powerpc/tlsso.r index 2d89e0b..7b36dea 100644 --- a/ld/testsuite/ld-powerpc/tlsso.r +++ b/ld/testsuite/ld-powerpc/tlsso.r @@ -59,8 +59,8 @@ Relocation section '\.rela\.dyn' at offset .* contains 16 entries: 0+7ca +0+900000046 R_PPC64_TPREL16_LO +0+107f8 \.tdata \+ 30 0+10988 +0+44 R_PPC64_DTPMOD64 +0+ 0+10998 +0+44 R_PPC64_DTPMOD64 +0+ -0+109a0 +0+4e R_PPC64_DTPREL64 +0+107f8 -0+109a8 +0+4e R_PPC64_DTPREL64 +0+10810 +0+109a0 +0+4e R_PPC64_DTPREL64 +0+ +0+109a8 +0+4e R_PPC64_DTPREL64 +0+18 0+109b0 +0+1300000044 R_PPC64_DTPMOD64 +0+ gd \+ 0 0+109b8 +0+130000004e R_PPC64_DTPREL64 +0+ gd \+ 0 0+109c0 +0+1b0000004e R_PPC64_DTPREL64 +0+50 ld2 \+ 0 diff --git a/ld/testsuite/ld-powerpc/tlsso32.r b/ld/testsuite/ld-powerpc/tlsso32.r index 7125875..6009467 100644 --- a/ld/testsuite/ld-powerpc/tlsso32.r +++ b/ld/testsuite/ld-powerpc/tlsso32.r @@ -62,7 +62,7 @@ Relocation section '\.rela\.dyn' at offset 0x454 contains 18 entries: 0+5a6 +0+846 R_PPC_TPREL16_LO +0+105a8 +\.tdata \+ 105c0 0+10674 +0+44 R_PPC_DTPMOD32 +0+ 0+1067c +0+44 R_PPC_DTPMOD32 +0+ -0+10680 +0+4e R_PPC_DTPREL32 +0+105a8 +0+10680 +0+4e R_PPC_DTPREL32 +0+ 0+10684 +0+1244 R_PPC_DTPMOD32 +0+ +gd \+ 0 0+10688 +0+124e R_PPC_DTPREL32 +0+ +gd \+ 0 0+1068c +0+2144 R_PPC_DTPMOD32 +0+1c +gd0 \+ 0 |