aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--bfd/ChangeLog29
-rw-r--r--bfd/elfxx-mips.c95
-rw-r--r--ld/testsuite/ChangeLog16
-rw-r--r--ld/testsuite/ld-mips-elf/got-dump-1.d4
-rw-r--r--ld/testsuite/ld-mips-elf/got-dump-2.d4
-rw-r--r--ld/testsuite/ld-mips-elf/mips16-pic-2.dd4
-rw-r--r--ld/testsuite/ld-mips-elf/mips16-pic-2.gd8
-rw-r--r--ld/testsuite/ld-mips-elf/mips16-pic-2.nd4
-rw-r--r--ld/testsuite/ld-mips-elf/mips16-pic-2.rd2
-rw-r--r--ld/testsuite/ld-mips-elf/tls-hidden4.got7
-rw-r--r--ld/testsuite/ld-mips-elf/tls-hidden4.r4
11 files changed, 98 insertions, 79 deletions
diff --git a/bfd/ChangeLog b/bfd/ChangeLog
index 8dee0b4..581e89b 100644
--- a/bfd/ChangeLog
+++ b/bfd/ChangeLog
@@ -1,5 +1,34 @@
2008-08-07 Richard Sandiford <rdsandiford@googlemail.com>
+ * elfxx-mips.c (mips_got_info): Add a "reloc_only_gotno" field.
+ (mips_elf_got_section): Delete.
+ (mips_elf_sort_hash_table): Use g->reloc_only_gotno to decide
+ how many reloc-only entries there are.
+ (mips_elf_count_got_symbols): Adjust g->reloc_only_gotno as
+ well as g->global_gotno.
+ (mips_elf_make_got_per_bfd): Initialize reloc_only_gotno.
+ (mips_elf_multi_got): Likewise. Use gg->reloc_only_gotno
+ rather than gg->assigned_gotno to store the number of
+ reloc-only GOT entries.
+ (mips_elf_create_got_section): Remove the MAYBE_EXCLUDE parameter.
+ Initialize reloc_only_gotno.
+ (mips_elf_calculate_relocation): Check htab->got_info instead of
+ dynobj when deciding whether to call mips_elf_adjust_gp,
+ (_bfd_mips_elf_create_dynamic_sections): Adjust the call
+ to mips_elf_create_got_section.
+ (mips_elf_record_relocs): Likewise. Remove redundant
+ "dynobj == NULL" code. Do not use mips_elf_create_got_section
+ or mips_elf_record_global_got_symbol for R_MIPS_32, R_MIPS_REL32
+ and R_MIPS_64; limit global_got_area to GGA_RELOC_ONLY instead.
+ (_bfd_mips_elf_finish_dynamic_symbol): Use htab->sgot instead
+ of mips_elf_got_section.
+ (_bfd_mips_vxworks_finish_dynamic_symbol): Likewise.
+ (_bfd_mips_elf_finish_dynamic_sections): Likewise.
+ Move the initial assignment of G to the block that uses it;
+ it is used for an unrelated purpose later.
+
+2008-08-07 Richard Sandiford <rdsandiford@googlemail.com>
+
* elfxx-mips.c (count_section_dynsyms): Move before the new first use.
(mips_elf_sort_hash_table): Take the output bfd as a parameter.
Remove the MAX_LOCAL parameter. Exit early if there are no
diff --git a/bfd/elfxx-mips.c b/bfd/elfxx-mips.c
index 297c361..36c94d5 100644
--- a/bfd/elfxx-mips.c
+++ b/bfd/elfxx-mips.c
@@ -145,6 +145,8 @@ struct mips_got_info
struct elf_link_hash_entry *global_gotsym;
/* The number of global .got entries. */
unsigned int global_gotno;
+ /* The number of global .got entries that are in the GGA_RELOC_ONLY area. */
+ unsigned int reloc_only_gotno;
/* The number of .got slots used for TLS. */
unsigned int tls_gotno;
/* The first unused TLS .got entry. Used only during
@@ -2280,19 +2282,6 @@ mips_elf_rel_dyn_section (struct bfd_link_info *info, bfd_boolean create_p)
return sreloc;
}
-/* Returns the GOT section, if it hasn't been excluded. */
-
-static asection *
-mips_elf_got_section (struct bfd_link_info *info)
-{
- struct mips_elf_link_hash_table *htab;
-
- htab = mips_elf_hash_table (info);
- if (htab->sgot == NULL || (htab->sgot->flags & SEC_EXCLUDE) != 0)
- return NULL;
- return htab->sgot;
-}
-
/* Count the number of relocations needed for a TLS GOT entry, with
access types from TLS_TYPE, and symbol H (or a local symbol if H
is NULL). */
@@ -2423,12 +2412,14 @@ mips_elf_initialize_tls_slots (bfd *abfd, bfd_vma got_offset,
struct mips_elf_link_hash_entry *h,
bfd_vma value)
{
+ struct mips_elf_link_hash_table *htab;
int indx;
asection *sreloc, *sgot;
bfd_vma offset, offset2;
bfd_boolean need_relocs = FALSE;
- sgot = mips_elf_got_section (info);
+ htab = mips_elf_hash_table (info);
+ sgot = htab->sgot;
indx = 0;
if (h != NULL)
@@ -2954,16 +2945,9 @@ mips_elf_sort_hash_table (bfd *abfd, struct bfd_link_info *info)
return TRUE;
hsd.low = NULL;
- hsd.max_unref_got_dynindx =
- hsd.min_got_dynindx = elf_hash_table (info)->dynsymcount
- /* In the multi-got case, assigned_gotno of the master got_info
- indicate the number of entries that aren't referenced in the
- primary GOT, but that must have entries because there are
- dynamic relocations that reference it. Since they aren't
- referenced, we move them to the end of the GOT, so that they
- don't prevent other entries that are referenced from getting
- too large offsets. */
- - (g->next ? g->assigned_gotno : 0);
+ hsd.max_unref_got_dynindx
+ = hsd.min_got_dynindx
+ = (elf_hash_table (info)->dynsymcount - g->reloc_only_gotno);
hsd.max_non_got_dynindx = count_section_dynsyms (abfd, info) + 1;
mips_elf_link_hash_traverse (((struct mips_elf_link_hash_table *)
elf_hash_table (info)),
@@ -3413,7 +3397,11 @@ mips_elf_count_got_symbols (struct mips_elf_link_hash_entry *h, void *data)
h->global_got_area = GGA_NONE;
}
else
- g->global_gotno++;
+ {
+ g->global_gotno++;
+ if (h->global_got_area == GGA_RELOC_ONLY)
+ g->reloc_only_gotno++;
+ }
}
return 1;
}
@@ -3492,6 +3480,7 @@ mips_elf_get_got_for_bfd (struct htab *bfd2got, bfd *output_bfd,
g->global_gotsym = NULL;
g->global_gotno = 0;
+ g->reloc_only_gotno = 0;
g->local_gotno = 0;
g->page_gotno = 0;
g->assigned_gotno = -1;
@@ -3912,6 +3901,7 @@ mips_elf_multi_got (bfd *abfd, struct bfd_link_info *info,
g->next->global_gotsym = NULL;
g->next->global_gotno = 0;
+ g->next->reloc_only_gotno = 0;
g->next->local_gotno = 0;
g->next->page_gotno = 0;
g->next->tls_gotno = 0;
@@ -3964,7 +3954,7 @@ mips_elf_multi_got (bfd *abfd, struct bfd_link_info *info,
/* Every symbol that is referenced in a dynamic relocation must be
present in the primary GOT, so arrange for them to appear after
those that are actually referenced. */
- gg->assigned_gotno = gg->global_gotno - g->global_gotno;
+ gg->reloc_only_gotno = gg->global_gotno - g->global_gotno;
g->global_gotno = gg->global_gotno;
set_got_offset_arg.g = NULL;
@@ -4224,8 +4214,7 @@ mips_elf_create_compact_rel_section
/* Create the .got section to hold the global offset table. */
static bfd_boolean
-mips_elf_create_got_section (bfd *abfd, struct bfd_link_info *info,
- bfd_boolean maybe_exclude)
+mips_elf_create_got_section (bfd *abfd, struct bfd_link_info *info)
{
flagword flags;
register asection *s;
@@ -4238,20 +4227,12 @@ mips_elf_create_got_section (bfd *abfd, struct bfd_link_info *info,
htab = mips_elf_hash_table (info);
/* This function may be called more than once. */
- s = htab->sgot;
- if (s)
- {
- if (! maybe_exclude)
- s->flags &= ~SEC_EXCLUDE;
- return TRUE;
- }
+ if (htab->sgot)
+ return TRUE;
flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
| SEC_LINKER_CREATED);
- if (maybe_exclude)
- flags |= SEC_EXCLUDE;
-
/* We have to use an alignment of 2**4 here because this is hardcoded
in the function stub generation and in the linker script. */
s = bfd_make_section_with_flags (abfd, ".got", flags);
@@ -4285,6 +4266,7 @@ mips_elf_create_got_section (bfd *abfd, struct bfd_link_info *info,
return FALSE;
g->global_gotsym = NULL;
g->global_gotno = 0;
+ g->reloc_only_gotno = 0;
g->tls_gotno = 0;
g->local_gotno = MIPS_RESERVED_GOTNO (info);
g->page_gotno = 0;
@@ -4642,7 +4624,7 @@ mips_elf_calculate_relocation (bfd *abfd, bfd *input_bfd,
gp0 = _bfd_get_gp_value (input_bfd);
gp = _bfd_get_gp_value (abfd);
- if (dynobj)
+ if (htab->got_info)
gp += mips_elf_adjust_gp (abfd, htab->got_info, input_bfd);
if (gnu_local_gp_p)
@@ -6417,7 +6399,7 @@ _bfd_mips_elf_create_dynamic_sections (bfd *abfd, struct bfd_link_info *info)
}
/* We need to create .got section. */
- if (! mips_elf_create_got_section (abfd, info, FALSE))
+ if (!mips_elf_create_got_section (abfd, info))
return FALSE;
if (! mips_elf_rel_dyn_section (info, TRUE))
@@ -7039,7 +7021,7 @@ _bfd_mips_elf_check_relocs (bfd *abfd, struct bfd_link_info *info,
case R_MIPS_TLS_LDM:
if (dynobj == NULL)
elf_hash_table (info)->dynobj = dynobj = abfd;
- if (! mips_elf_create_got_section (dynobj, info, FALSE))
+ if (!mips_elf_create_got_section (dynobj, info))
return FALSE;
if (htab->is_vxworks && !info->shared)
{
@@ -7301,12 +7283,11 @@ _bfd_mips_elf_check_relocs (bfd *abfd, struct bfd_link_info *info,
between global GOT entries and .dynsym entries. */
if (h != NULL && !htab->is_vxworks)
{
- if (dynobj == NULL)
- elf_hash_table (info)->dynobj = dynobj = abfd;
- if (! mips_elf_create_got_section (dynobj, info, TRUE))
- return FALSE;
- if (!mips_elf_record_global_got_symbol (h, abfd, info, 0))
- return FALSE;
+ struct mips_elf_link_hash_entry *hmips;
+
+ hmips = (struct mips_elf_link_hash_entry *) h;
+ if (hmips->global_got_area > GGA_RELOC_ONLY)
+ hmips->global_got_area = GGA_RELOC_ONLY;
}
}
@@ -8818,8 +8799,7 @@ _bfd_mips_elf_finish_dynamic_symbol (bfd *output_bfd,
BFD_ASSERT (h->dynindx != -1
|| h->forced_local);
- sgot = mips_elf_got_section (info);
- BFD_ASSERT (sgot != NULL);
+ sgot = htab->sgot;
g = htab->got_info;
BFD_ASSERT (g != NULL);
@@ -9089,8 +9069,7 @@ _bfd_mips_vxworks_finish_dynamic_symbol (bfd *output_bfd,
BFD_ASSERT (h->dynindx != -1 || h->forced_local);
- sgot = mips_elf_got_section (info);
- BFD_ASSERT (sgot != NULL);
+ sgot = htab->sgot;
g = htab->got_info;
BFD_ASSERT (g != NULL);
@@ -9252,15 +9231,8 @@ _bfd_mips_elf_finish_dynamic_sections (bfd *output_bfd,
sdyn = bfd_get_section_by_name (dynobj, ".dynamic");
- sgot = mips_elf_got_section (info);
- if (sgot == NULL)
- gg = g = NULL;
- else
- {
- gg = htab->got_info;
- g = mips_elf_got_for_ibfd (gg, output_bfd);
- BFD_ASSERT (g != NULL);
- }
+ sgot = htab->sgot;
+ gg = htab->got_info;
if (elf_hash_table (info)->dynamic_sections_created)
{
@@ -9268,6 +9240,9 @@ _bfd_mips_elf_finish_dynamic_sections (bfd *output_bfd,
int dyn_to_skip = 0, dyn_skipped = 0;
BFD_ASSERT (sdyn != NULL);
+ BFD_ASSERT (gg != NULL);
+
+ g = mips_elf_got_for_ibfd (gg, output_bfd);
BFD_ASSERT (g != NULL);
for (b = sdyn->contents;
diff --git a/ld/testsuite/ChangeLog b/ld/testsuite/ChangeLog
index d40ec92..9294772 100644
--- a/ld/testsuite/ChangeLog
+++ b/ld/testsuite/ChangeLog
@@ -1,5 +1,21 @@
2008-08-07 Richard Sandiford <rdsandiford@googlemail.com>
+ * ld-mips-elf/tls-hidden4.got, ld-mips-elf/tls-hidden4.r: We have
+ removed an unused GOT entry that was allocated for the R_MIPS_32
+ relocation against "undef", so adjust addresses down by 4 bytes.
+ * ld-mips-elf/got-dump-1.d, ld-mips-elf/got-dump-2.d: We have
+ changed the order of the GOT entries so that reloc-only ones
+ come last. "undef" is only referred to by dynamic relocations,
+ so it now comes after "glob".
+ * ld-mips-elf/mips16-pic-2.dd, ld-mips-elf/mips16-pic-2.gd,
+ ld-mips-elf/mips16-pic-2.nd, ld-mips-elf/mips16-pic-2.rd: We have
+ removed two unused local GOT entries that were originally created
+ as global entries for the hidden symbols "used2" and "used3".
+ "used4" and "used5" are only referred to by relocations, so they
+ now come after "used6" and "used7".
+
+2008-08-07 Richard Sandiford <rdsandiford@googlemail.com>
+
* ld-mips-elf/got-vers-1a.s, ld-mips-elf/got-vers-1b.s,
ld-mips-elf/got-vers-1.ver, ld-mips-elf/got-vers-1.dd,
ld-mips-elf/got-vers-1.sd, ld-mips-elf/got-vers-1.rd: New tests.
diff --git a/ld/testsuite/ld-mips-elf/got-dump-1.d b/ld/testsuite/ld-mips-elf/got-dump-1.d
index eaf9c6b..b14adff 100644
--- a/ld/testsuite/ld-mips-elf/got-dump-1.d
+++ b/ld/testsuite/ld-mips-elf/got-dump-1.d
@@ -20,6 +20,6 @@ Primary GOT:
Global entries:
Address Access Initial Sym.Val. Type Ndx Name
00060020 -32736\(gp\) 00050020 00050020 FUNC UND extern
- 00060024 -32732\(gp\) 00000000 00000000 NOTYPE UND undef
- 00060028 -32728\(gp\) 00050000 00050000 FUNC 7 glob
+ 00060024 -32732\(gp\) 00050000 00050000 FUNC 7 glob
+ 00060028 -32728\(gp\) 00000000 00000000 NOTYPE UND undef
diff --git a/ld/testsuite/ld-mips-elf/got-dump-2.d b/ld/testsuite/ld-mips-elf/got-dump-2.d
index 1e656f0..56cc0b3 100644
--- a/ld/testsuite/ld-mips-elf/got-dump-2.d
+++ b/ld/testsuite/ld-mips-elf/got-dump-2.d
@@ -20,6 +20,6 @@ Primary GOT:
Global entries:
Address Access Initial Sym.Val. Type Ndx Name
0001236000000030 -32720\(gp\) 0001235000000020 0001235000000020 FUNC UND extern
- 0001236000000038 -32712\(gp\) 0000000000000000 0000000000000000 NOTYPE UND undef
- 0001236000000040 -32704\(gp\) 0001235000000000 0001235000000000 FUNC 7 glob
+ 0001236000000038 -32712\(gp\) 0001235000000000 0001235000000000 FUNC 7 glob
+ 0001236000000040 -32704\(gp\) 0000000000000000 0000000000000000 NOTYPE UND undef
diff --git a/ld/testsuite/ld-mips-elf/mips16-pic-2.dd b/ld/testsuite/ld-mips-elf/mips16-pic-2.dd
index 75ea6dc..7052057 100644
--- a/ld/testsuite/ld-mips-elf/mips16-pic-2.dd
+++ b/ld/testsuite/ld-mips-elf/mips16-pic-2.dd
@@ -77,7 +77,7 @@ Disassembly of section \.text:
.*: [^\t]* move t9,v0
.*: [^\t]* lw v0,16\(sp\)
.*: [^\t]* move gp,v0
-.*: [^\t]* lw v0,-32708\(v0\)
+.*: [^\t]* lw v0,-32716\(v0\)
.*: [^\t]* jalr v0
.*: [^\t]* move t9,v0
.*: [^\t]* lw v0,16\(sp\)
@@ -101,7 +101,7 @@ Disassembly of section \.text:
.*: [^\t]* move t9,v0
.*: [^\t]* lw v0,16\(sp\)
.*: [^\t]* move gp,v0
-.*: [^\t]* lw v0,-32696\(v0\)
+.*: [^\t]* lw v0,-32712\(v0\)
.*: [^\t]* jalr v0
.*: [^\t]* move t9,v0
.*: [^\t]* lw v0,16\(sp\)
diff --git a/ld/testsuite/ld-mips-elf/mips16-pic-2.gd b/ld/testsuite/ld-mips-elf/mips16-pic-2.gd
index ebc341e..d8d1451 100644
--- a/ld/testsuite/ld-mips-elf/mips16-pic-2.gd
+++ b/ld/testsuite/ld-mips-elf/mips16-pic-2.gd
@@ -16,13 +16,11 @@ Primary GOT:
00050018 -32728\(gp\) 00000000
0005001c -32724\(gp\) 00000000
00050020 -32720\(gp\) 00000000
- 00050024 -32716\(gp\) 00000000
- 00050028 -32712\(gp\) 00000000
Global entries:
Address Access Initial Sym\.Val\. Type Ndx Name
- 0005002c -32708\(gp\) 00040574 00040574 FUNC 6 used6
+ 00050024 -32716\(gp\) 00040574 00040574 FUNC 6 used6
+ 00050028 -32712\(gp\) 00040598 00040598 FUNC 6 used7
+ 0005002c -32708\(gp\) 00040550 00040550 FUNC 6 used5
00050030 -32704\(gp\) 0004052c 0004052c FUNC 6 used4
- 00050034 -32700\(gp\) 00040550 00040550 FUNC 6 used5
- 00050038 -32696\(gp\) 00040598 00040598 FUNC 6 used7
diff --git a/ld/testsuite/ld-mips-elf/mips16-pic-2.nd b/ld/testsuite/ld-mips-elf/mips16-pic-2.nd
index c4ad9fd..a2b67b6 100644
--- a/ld/testsuite/ld-mips-elf/mips16-pic-2.nd
+++ b/ld/testsuite/ld-mips-elf/mips16-pic-2.nd
@@ -3,8 +3,8 @@
4: 000405bc 36 FUNC GLOBAL DEFAULT .* used8
5: .* _GLOBAL_OFFSET_TABLE_
6: 00040574 36 FUNC GLOBAL DEFAULT .* used6
- 7: 0004052c 36 FUNC GLOBAL DEFAULT .* used4
+ 7: 00040598 36 FUNC GLOBAL DEFAULT .* used7
8: 00040550 36 FUNC GLOBAL DEFAULT .* used5
- 9: 00040598 36 FUNC GLOBAL DEFAULT .* used7
+ 9: 0004052c 36 FUNC GLOBAL DEFAULT .* used4
#pass
diff --git a/ld/testsuite/ld-mips-elf/mips16-pic-2.rd b/ld/testsuite/ld-mips-elf/mips16-pic-2.rd
index 8411dbe..09a97b7 100644
--- a/ld/testsuite/ld-mips-elf/mips16-pic-2.rd
+++ b/ld/testsuite/ld-mips-elf/mips16-pic-2.rd
@@ -5,5 +5,5 @@ Relocation section '\.rel\.dyn' .*:
0+50400 * [0-9]+ * R_MIPS_REL32 *
0+50404 * [0-9]+ * R_MIPS_REL32 *
0+50410 * [0-9]+ * R_MIPS_REL32 *
-0+50408 * [0-9]+ * R_MIPS_REL32 * 0004052c * used4
0+50414 * [0-9]+ * R_MIPS_REL32 * 00040550 * used5
+0+50408 * [0-9]+ * R_MIPS_REL32 * 0004052c * used4
diff --git a/ld/testsuite/ld-mips-elf/tls-hidden4.got b/ld/testsuite/ld-mips-elf/tls-hidden4.got
index 0c90da2..e6b2115 100644
--- a/ld/testsuite/ld-mips-elf/tls-hidden4.got
+++ b/ld/testsuite/ld-mips-elf/tls-hidden4.got
@@ -15,8 +15,8 @@ Contents of section \.got:
# entry for each symbol.
#
#...
- 1c4010 00000000 00000000 0000abc8 0000abcc .*
- 1c4020 0000abc0 0000abc4 00000000 80000000 .*
+ 1c4010 00000000 0000abc8 0000abcc 0000abc0 .*
+ 1c4020 0000abc4 00000000 80000000 00000000 .*
#
# Likewise, but the order of the entries in this GOT is:
#
@@ -25,4 +25,5 @@ Contents of section \.got:
# foo0
# foo1
#...
- 1d0030 0000abcc 0000abc8 0000abc0 0000abc4 .*
+ 1d0020 00000000 00000000 00000000 0000abcc .*
+ 1d0030 0000abc8 0000abc0 0000abc4 .*
diff --git a/ld/testsuite/ld-mips-elf/tls-hidden4.r b/ld/testsuite/ld-mips-elf/tls-hidden4.r
index 7a9353d..ccf2e80 100644
--- a/ld/testsuite/ld-mips-elf/tls-hidden4.r
+++ b/ld/testsuite/ld-mips-elf/tls-hidden4.r
@@ -7,13 +7,13 @@ Relocation section '\.rel\.dyn' at offset .* contains .* entries:
# important thing is that there is exactly one entry per GOT TLS slot
# and that the addresses match those in the .got dump.
#
+001c4014 0000002f R_MIPS_TLS_TPREL3
001c4018 0000002f R_MIPS_TLS_TPREL3
001c401c 0000002f R_MIPS_TLS_TPREL3
001c4020 0000002f R_MIPS_TLS_TPREL3
-001c4024 0000002f R_MIPS_TLS_TPREL3
+001d002c 0000002f R_MIPS_TLS_TPREL3
001d0030 0000002f R_MIPS_TLS_TPREL3
001d0034 0000002f R_MIPS_TLS_TPREL3
001d0038 0000002f R_MIPS_TLS_TPREL3
-001d003c 0000002f R_MIPS_TLS_TPREL3
.* R_MIPS_REL32 .*
#pass