2007-11-13 Nathan Sidwell bfd/ * elf32-ppc.c (ppc_elf_relocate_section): Resolve relocations that occur in vxworks .tls_vars sections statically. Emit NONE dynamic relocation. * elfxx-sparc.c (_bfd_sparc_elf_relocate_section): Likewise. * elf32-sh.c (sh_elf_relocate_section): Likewise. * elf32-arm.c (elf32_arm_final_link_relocate): Likewise. * elf32-i386.c (elf_i386_relocate_section): Likewise. * elfxx-mips.c (mips_elf_create_dynamic_relocation): Nullify relocation in vxworks .tls_vars section. ld/testsuite/ * ld-vxworks/tls-3.d: New. * ld-vxworks/tls-3.s: New. Index: bfd/elf32-arm.c =================================================================== RCS file: /cvs/src/src/bfd/elf32-arm.c,v retrieving revision 1.130 diff -c -3 -p -r1.130 elf32-arm.c *** bfd/elf32-arm.c 8 Nov 2007 13:51:06 -0000 1.130 --- bfd/elf32-arm.c 12 Nov 2007 18:26:08 -0000 *************** elf32_arm_final_link_relocate (reloc_how *** 4668,4673 **** --- 4668,4683 ---- if (skip) memset (&outrel, 0, sizeof outrel); + else if (info->shared && elf32_arm_hash_table (info)->vxworks_p + && !strcmp (input_section->output_section->name, + ".tls_vars")) + { + /* We have to handle relocations in vxworks .tls_vars + sections specially, because the dynamic loader is + 'weird'. */ + outrel.r_info = ELF32_R_INFO (0, R_ARM_NONE); + relocate = TRUE; + } else if (h != NULL && h->dynindx != -1 && (!info->shared Index: bfd/elf32-i386.c =================================================================== RCS file: /cvs/src/src/bfd/elf32-i386.c,v retrieving revision 1.183 diff -c -3 -p -r1.183 elf32-i386.c *** bfd/elf32-i386.c 8 Nov 2007 13:51:06 -0000 1.183 --- bfd/elf32-i386.c 12 Nov 2007 18:26:11 -0000 *************** elf_i386_relocate_section (bfd *output_b *** 2498,2503 **** --- 2498,2504 ---- bfd_vma *local_tlsdesc_gotents; Elf_Internal_Rela *rel; Elf_Internal_Rela *relend; + bfd_boolean is_vxworks_tls; htab = elf_i386_hash_table (info); symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr; *************** elf_i386_relocate_section (bfd *output_b *** 2505,2510 **** --- 2506,2517 ---- local_got_offsets = elf_local_got_offsets (input_bfd); local_tlsdesc_gotents = elf_i386_local_tlsdesc_gotent (input_bfd); + /* We have to handle relocations in vxworks .tls_vars sections + specially, because the dynamic loader is 'weird'. */ + is_vxworks_tls = (htab->is_vxworks && info->shared + && !strcmp (input_section->output_section->name, + ".tls_vars")); + rel = relocs; relend = relocs + input_section->reloc_count; for (; rel < relend; rel++) *************** elf_i386_relocate_section (bfd *output_b *** 2847,2852 **** --- 2854,2865 ---- if (skip) memset (&outrel, 0, sizeof outrel); + else if (is_vxworks_tls) + { + /* Relocation is done magically by the loader. */ + relocate = TRUE; + outrel.r_info = ELF32_R_INFO (0, R_386_NONE); + } else if (h != NULL && h->dynindx != -1 && (r_type == R_386_PC32 Index: bfd/elf32-ppc.c =================================================================== RCS file: /cvs/src/src/bfd/elf32-ppc.c,v retrieving revision 1.224 diff -c -3 -p -r1.224 elf32-ppc.c *** bfd/elf32-ppc.c 8 Nov 2007 13:51:06 -0000 1.224 --- bfd/elf32-ppc.c 12 Nov 2007 18:26:16 -0000 *************** ppc_elf_relocate_section (bfd *output_bf *** 5758,5763 **** --- 5758,5764 ---- bfd_vma *local_got_offsets; bfd_boolean ret = TRUE; bfd_vma d_offset = (bfd_big_endian (output_bfd) ? 2 : 0); + bfd_boolean is_vxworks_tls; #ifdef DEBUG _bfd_error_handler ("ppc_elf_relocate_section called for %B section %A, " *************** ppc_elf_relocate_section (bfd *output_bf *** 5777,5782 **** --- 5778,5790 ---- local_got_offsets = elf_local_got_offsets (input_bfd); symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr; sym_hashes = elf_sym_hashes (input_bfd); + + /* We have to handle relocations in vxworks .tls_vars sections + specially, because the dynamic loader is 'weird'. */ + is_vxworks_tls = (htab->is_vxworks && info->shared + && !strcmp (input_section->output_section->name, + ".tls_vars")); + rel = relocs; relend = relocs + input_section->reloc_count; for (; rel < relend; rel++) *************** ppc_elf_relocate_section (bfd *output_bf *** 6474,6479 **** --- 6482,6493 ---- if (skip) memset (&outrel, 0, sizeof outrel); + else if (is_vxworks_tls) + { + outrel.r_info = ELF32_R_INFO (0, R_PPC_NONE); + outrel.r_addend = relocation; + skip = 1; + } else if (!SYMBOL_REFERENCES_LOCAL (info, h)) { unresolved_reloc = FALSE; *************** ppc_elf_relocate_section (bfd *output_bf *** 6541,6547 **** { relocation = howto->pc_relative ? outrel.r_offset : 0; addend = 0; - break; } } break; --- 6555,6560 ---- Index: bfd/elf32-sh.c =================================================================== RCS file: /cvs/src/src/bfd/elf32-sh.c,v retrieving revision 1.154 diff -c -3 -p -r1.154 elf32-sh.c *** bfd/elf32-sh.c 8 Nov 2007 13:51:06 -0000 1.154 --- bfd/elf32-sh.c 12 Nov 2007 18:26:20 -0000 *************** sh_elf_relocate_section (bfd *output_bfd *** 3167,3172 **** --- 3167,3173 ---- asection *splt; asection *sreloc; asection *srelgot; + bfd_boolean is_vxworks_tls; htab = sh_elf_hash_table (info); symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr; *************** sh_elf_relocate_section (bfd *output_bfd *** 3180,3185 **** --- 3181,3192 ---- sreloc = NULL; srelgot = NULL; + /* We have to handle relocations in vxworks .tls_vars sections + specially, because the dynamic loader is 'weird'. */ + is_vxworks_tls = (htab->vxworks_p && info->shared + && !strcmp (input_section->output_section->name, + ".tls_vars")); + rel = relocs; relend = relocs + input_section->reloc_count; for (; rel < relend; rel++) *************** sh_elf_relocate_section (bfd *output_bfd *** 3631,3636 **** --- 3638,3649 ---- if (skip) memset (&outrel, 0, sizeof outrel); + else if (is_vxworks_tls) + { + outrel.r_info = ELF32_R_INFO (0, R_SH_NONE); + outrel.r_addend = relocation; + relocate = TRUE; + } else if (r_type == R_SH_REL32) { BFD_ASSERT (h != NULL && h->dynindx != -1); Index: bfd/elfxx-mips.c =================================================================== RCS file: /cvs/src/src/bfd/elfxx-mips.c,v retrieving revision 1.219 diff -c -3 -p -r1.219 elfxx-mips.c *** bfd/elfxx-mips.c 8 Nov 2007 13:51:06 -0000 1.219 --- bfd/elfxx-mips.c 12 Nov 2007 18:26:30 -0000 *************** mips_elf_create_dynamic_relocation (bfd *** 4871,4878 **** *addendp += symbol; if (htab->is_vxworks) ! /* VxWorks uses non-relative relocations for this. */ ! outrel[0].r_info = ELF32_R_INFO (indx, R_MIPS_32); else /* The relocation is always an REL32 relocation because we don't know where the shared library will wind up at load-time. */ --- 4871,4892 ---- *addendp += symbol; if (htab->is_vxworks) ! { ! if (info->shared ! && !strcmp (input_section->output_section->name, ".tls_vars")) ! { ! /* We have to handle relocations in vxworks .tls_vars sections ! specially, because the dynamic loader is 'weird'. */ ! outrel[0].r_info = ELF32_R_INFO (0, R_MIPS_NONE); ! outrel[0].r_addend = 0; ! } ! else ! { ! /* VxWorks uses non-relative relocations for this. */ ! outrel[0].r_info = ELF32_R_INFO (indx, R_MIPS_32); ! outrel[0].r_addend = *addendp; ! } ! } else /* The relocation is always an REL32 relocation because we don't know where the shared library will wind up at load-time. */ *************** mips_elf_create_dynamic_relocation (bfd *** 4919,4925 **** else if (htab->is_vxworks) { /* VxWorks uses RELA rather than REL dynamic relocations. */ - outrel[0].r_addend = *addendp; bfd_elf32_swap_reloca_out (output_bfd, &outrel[0], (sreloc->contents --- 4933,4938 ---- *************** _bfd_mips_elf_relocate_section (bfd *out *** 7740,7745 **** --- 7753,7759 ---- const struct elf_backend_data *bed; bed = get_elf_backend_data (output_bfd); + relend = relocs + input_section->reloc_count * bed->s->int_rels_per_ext_rel; for (rel = relocs; rel < relend; ++rel) { *************** _bfd_mips_elf_relocate_section (bfd *out *** 8145,8151 **** contents, require_jalx)) return FALSE; } - return TRUE; } --- 8159,8164 ---- Index: bfd/elfxx-sparc.c =================================================================== RCS file: /cvs/src/src/bfd/elfxx-sparc.c,v retrieving revision 1.36 diff -c -3 -p -r1.36 elfxx-sparc.c *** bfd/elfxx-sparc.c 8 Nov 2007 13:51:06 -0000 1.36 --- bfd/elfxx-sparc.c 12 Nov 2007 18:26:35 -0000 *************** _bfd_sparc_elf_relocate_section (bfd *ou *** 2481,2486 **** --- 2481,2487 ---- Elf_Internal_Rela *rel; Elf_Internal_Rela *relend; int num_relocs; + bfd_boolean is_vxworks_tls; htab = _bfd_sparc_elf_hash_table (info); symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr; *************** _bfd_sparc_elf_relocate_section (bfd *ou *** 2494,2499 **** --- 2495,2506 ---- sreloc = elf_section_data (input_section)->sreloc; + /* We have to handle relocations in vxworks .tls_vars sections + specially, because the dynamic loader is 'weird'. */ + is_vxworks_tls = (htab->is_vxworks && info->shared + && !strcmp (input_section->output_section->name, + ".tls_vars")); + rel = relocs; if (ABI_64_P (output_bfd)) num_relocs = NUM_SHDR_ENTRIES (& elf_section_data (input_section)->rel_hdr); *************** _bfd_sparc_elf_relocate_section (bfd *ou *** 2845,2850 **** --- 2852,2863 ---- if (skip) memset (&outrel, 0, sizeof outrel); + else if (is_vxworks_tls) + { + outrel.r_info = ELF32_R_INFO (0, R_SPARC_NONE); + outrel.r_addend = relocation; + relocate = TRUE; + } /* h->dynindx may be -1 if the symbol was marked to become local. */ else if (h != NULL && ! is_plt Index: ld/testsuite/ld-vxworks/tls-3.d =================================================================== RCS file: ld/testsuite/ld-vxworks/tls-3.d diff -N ld/testsuite/ld-vxworks/tls-3.d *** /dev/null 1 Jan 1970 00:00:00 -0000 --- ld/testsuite/ld-vxworks/tls-3.d 12 Nov 2007 18:26:42 -0000 *************** *** 0 **** --- 1,9 ---- + # source: tls-3.s + # ld: -shared -z now + # objdump: -R + + #... + DYNAMIC RELOCATION RECORDS + OFFSET.* + [0-9a-f]+ R_[A-Z0-9]+_NONE *\*ABS\*(\+0x[0-9a-f]+)? + Index: ld/testsuite/ld-vxworks/tls-3.s =================================================================== RCS file: ld/testsuite/ld-vxworks/tls-3.s diff -N ld/testsuite/ld-vxworks/tls-3.s *** /dev/null 1 Jan 1970 00:00:00 -0000 --- ld/testsuite/ld-vxworks/tls-3.s 12 Nov 2007 18:26:42 -0000 *************** *** 0 **** --- 1,19 ---- + .globl foo + foo: + + .section .tls_data,"a" + .p2align 2 + .type i,%object + .size i,4 + i: + .space 4 + .globl __tls__i + .section .tls_vars,"a" + .p2align 2 + .type __tls__i,%object + .size __tls__i,12 + __tls__i: + .4byte i + .4byte 0 + .4byte 4 +