bfd: RISC-V: relax to gp in more cases.

bfd/ChangeLog:

2017-02-24  Andrew Waterman  <andrew@sifive.com>

	* elfnn-riscv.c (GP_NAME): New macro.
	(riscv_global_pointer_value): Use it.
	(_bfd_riscv_relax_lui): If symbol and global pointer are in same
	output section, consider only that section's alignment.
This commit is contained in:
Andrew Waterman
2017-02-21 21:56:57 -08:00
committed by Palmer Dabbelt
parent 742d14b39b
commit d0f744f970
2 changed files with 22 additions and 1 deletions

View File

@ -1,3 +1,10 @@
2017-02-24 Andrew Waterman <andrew@sifive.com>
* elfnn-riscv.c (GP_NAME): New macro.
(riscv_global_pointer_value): Use it.
(_bfd_riscv_relax_lui): If symbol and global pointer are in same
output section, consider only that section's alignment.
2017-02-23 Maciej W. Rozycki <macro@imgtec.com> 2017-02-23 Maciej W. Rozycki <macro@imgtec.com>
* elfxx-mips.h (_bfd_mips_relax_section): Remove prototype. * elfxx-mips.h (_bfd_mips_relax_section): Remove prototype.

View File

@ -52,6 +52,10 @@
#define ELF_MAXPAGESIZE 0x1000 #define ELF_MAXPAGESIZE 0x1000
#define ELF_COMMONPAGESIZE 0x1000 #define ELF_COMMONPAGESIZE 0x1000
/* The global pointer's symbol name. */
#define GP_NAME "__global_pointer$"
/* The RISC-V linker needs to keep track of the number of relocs that it /* The RISC-V linker needs to keep track of the number of relocs that it
decides to copy as dynamic relocs in check_relocs for each symbol. decides to copy as dynamic relocs in check_relocs for each symbol.
This is so that it can later discard them if they are found to be This is so that it can later discard them if they are found to be
@ -1463,7 +1467,7 @@ riscv_global_pointer_value (struct bfd_link_info *info)
{ {
struct bfd_link_hash_entry *h; struct bfd_link_hash_entry *h;
h = bfd_link_hash_lookup (info->hash, "__global_pointer$", FALSE, FALSE, TRUE); h = bfd_link_hash_lookup (info->hash, GP_NAME, FALSE, FALSE, TRUE);
if (h == NULL || h->type != bfd_link_hash_defined) if (h == NULL || h->type != bfd_link_hash_defined)
return 0; return 0;
@ -2809,6 +2813,16 @@ _bfd_riscv_relax_lui (bfd *abfd,
BFD_ASSERT (rel->r_offset + 4 <= sec->size); BFD_ASSERT (rel->r_offset + 4 <= sec->size);
if (gp)
{
/* If gp and the symbol are in the same output section, then
consider only that section's alignment. */
struct bfd_link_hash_entry *h =
bfd_link_hash_lookup (link_info->hash, GP_NAME, FALSE, FALSE, TRUE);
if (h->u.def.section->output_section == sym_sec->output_section)
max_alignment = (bfd_vma) 1 << sym_sec->output_section->alignment_power;
}
/* Is the reference in range of x0 or gp? /* Is the reference in range of x0 or gp?
Valid gp range conservatively because of alignment issue. */ Valid gp range conservatively because of alignment issue. */
if (VALID_ITYPE_IMM (symval) if (VALID_ITYPE_IMM (symval)