2006-04-06  H.J. Lu  <hongjiu.lu@intel.com>

	* elfxx-ia64.c (elfNN_ia64_relax_section): Skip unneeded passes
	with the skip_relax_pass_0 and skip_relax_pass_1 bits in the
	section structure.

include/

2006-04-06  H.J. Lu  <hongjiu.lu@intel.com>

	* bfdlink.h (bfd_link_info): Replace need_relax_finalize with
	relax_pass.

ld/

2006-04-06  H.J. Lu  <hongjiu.lu@intel.com>

	* emultempl/ia64elf.em: Set link_info.relax_pass to 2. Remove
	link_info.need_relax_finalize.

	* ldlang.c (relax_sections): New.
	(lang_process): Use. Call relax_sections link_info.relax_pass
	times.

	* ldmain.c (main): Set link_info.relax_pass to 1. Remove
	link_info.need_relax_finalize.
This commit is contained in:
H.J. Lu 2006-04-06 18:52:46 +00:00
parent 7f198e01c2
commit fbbc375958
8 changed files with 100 additions and 52 deletions

View File

@ -1,3 +1,9 @@
2006-04-06 H.J. Lu <hongjiu.lu@intel.com>
* elfxx-ia64.c (elfNN_ia64_relax_section): Skip unneeded passes
with the skip_relax_pass_0 and skip_relax_pass_1 bits in the
section structure.
2006-04-05 Bernd Schmidt <bernd.schmidt@analog.com> 2006-04-05 Bernd Schmidt <bernd.schmidt@analog.com>
* elf32-bfin.c (bfinfdpic_relocs_info_hash): Sprinkle casts to * elf32-bfin.c (bfinfdpic_relocs_info_hash): Sprinkle casts to

View File

@ -863,6 +863,12 @@ elfNN_ia64_relax_brl (bfd_byte *contents, bfd_vma off)
bfd_putl64 (t0, hit_addr); bfd_putl64 (t0, hit_addr);
bfd_putl64 (t1, hit_addr + 8); bfd_putl64 (t1, hit_addr + 8);
} }
/* Rename some of the generic section flags to better document how they
are used here. */
#define skip_relax_pass_0 need_finalize_relax
#define skip_relax_pass_1 has_gp_reloc
/* These functions do relaxation for IA-64 ELF. */ /* These functions do relaxation for IA-64 ELF. */
@ -891,6 +897,8 @@ elfNN_ia64_relax_section (abfd, sec, link_info, again)
bfd_boolean changed_contents = FALSE; bfd_boolean changed_contents = FALSE;
bfd_boolean changed_relocs = FALSE; bfd_boolean changed_relocs = FALSE;
bfd_boolean changed_got = FALSE; bfd_boolean changed_got = FALSE;
bfd_boolean skip_relax_pass_0 = TRUE;
bfd_boolean skip_relax_pass_1 = TRUE;
bfd_vma gp = 0; bfd_vma gp = 0;
/* Assume we're not going to change any sizes, and we'll only need /* Assume we're not going to change any sizes, and we'll only need
@ -902,11 +910,11 @@ elfNN_ia64_relax_section (abfd, sec, link_info, again)
return FALSE; return FALSE;
/* Nothing to do if there are no relocations or there is no need for /* Nothing to do if there are no relocations or there is no need for
the relax finalize pass. */ the current pass. */
if ((sec->flags & SEC_RELOC) == 0 if ((sec->flags & SEC_RELOC) == 0
|| sec->reloc_count == 0 || sec->reloc_count == 0
|| (!link_info->need_relax_finalize || (link_info->relax_pass == 0 && sec->skip_relax_pass_0)
&& sec->need_finalize_relax == 0)) || (link_info->relax_pass == 1 && sec->skip_relax_pass_1))
return TRUE; return TRUE;
symtab_hdr = &elf_tdata (abfd)->symtab_hdr; symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
@ -947,20 +955,19 @@ elfNN_ia64_relax_section (abfd, sec, link_info, again)
case R_IA64_PCREL21BI: case R_IA64_PCREL21BI:
case R_IA64_PCREL21M: case R_IA64_PCREL21M:
case R_IA64_PCREL21F: case R_IA64_PCREL21F:
/* In the finalize pass, all br relaxations are done. We can /* In pass 1, all br relaxations are done. We can skip it. */
skip it. */ if (link_info->relax_pass == 1)
if (!link_info->need_relax_finalize)
continue; continue;
skip_relax_pass_0 = FALSE;
is_branch = TRUE; is_branch = TRUE;
break; break;
case R_IA64_PCREL60B: case R_IA64_PCREL60B:
/* We can't optimize brl to br before the finalize pass since /* We can't optimize brl to br in pass 0 since br relaxations
br relaxations will increase the code size. Defer it to will increase the code size. Defer it to pass 1. */
the finalize pass. */ if (link_info->relax_pass == 0)
if (link_info->need_relax_finalize)
{ {
sec->need_finalize_relax = 1; skip_relax_pass_1 = FALSE;
continue; continue;
} }
is_branch = TRUE; is_branch = TRUE;
@ -968,12 +975,11 @@ elfNN_ia64_relax_section (abfd, sec, link_info, again)
case R_IA64_LTOFF22X: case R_IA64_LTOFF22X:
case R_IA64_LDXMOV: case R_IA64_LDXMOV:
/* We can't relax ldx/mov before the finalize pass since /* We can't relax ldx/mov in pass 0 since br relaxations will
br relaxations will increase the code size. Defer it to increase the code size. Defer it to pass 1. */
the finalize pass. */ if (link_info->relax_pass == 0)
if (link_info->need_relax_finalize)
{ {
sec->need_finalize_relax = 1; skip_relax_pass_1 = FALSE;
continue; continue;
} }
is_branch = FALSE; is_branch = FALSE;
@ -1363,8 +1369,12 @@ elfNN_ia64_relax_section (abfd, sec, link_info, again)
} }
} }
if (!link_info->need_relax_finalize) if (link_info->relax_pass == 0)
sec->need_finalize_relax = 0; {
/* Pass 0 is only needed to relax br. */
sec->skip_relax_pass_0 = skip_relax_pass_0;
sec->skip_relax_pass_1 = skip_relax_pass_1;
}
*again = changed_contents || changed_relocs; *again = changed_contents || changed_relocs;
return TRUE; return TRUE;
@ -1380,6 +1390,8 @@ elfNN_ia64_relax_section (abfd, sec, link_info, again)
free (internal_relocs); free (internal_relocs);
return FALSE; return FALSE;
} }
#undef skip_relax_pass_0
#undef skip_relax_pass_1
static void static void
elfNN_ia64_relax_ldxmov (contents, off) elfNN_ia64_relax_ldxmov (contents, off)

View File

@ -1,3 +1,8 @@
2006-04-06 H.J. Lu <hongjiu.lu@intel.com>
* bfdlink.h (bfd_link_info): Replace need_relax_finalize with
relax_pass.
2006-03-25 Bernd Schmidt <bernd.schmidt@analog.com> 2006-03-25 Bernd Schmidt <bernd.schmidt@analog.com>
* elf/bfin.h (R_BFIN_GOT17M4, R_BFIN_GOTHI, R_BFIN_GOTLO, * elf/bfin.h (R_BFIN_GOT17M4, R_BFIN_GOTHI, R_BFIN_GOTLO,

View File

@ -301,9 +301,6 @@ struct bfd_link_info
/* TRUE if global symbols in discarded sections should be stripped. */ /* TRUE if global symbols in discarded sections should be stripped. */
unsigned int strip_discarded: 1; unsigned int strip_discarded: 1;
/* TRUE if the final relax pass is needed. */
unsigned int need_relax_finalize: 1;
/* TRUE if generating a position independent executable. */ /* TRUE if generating a position independent executable. */
unsigned int pie: 1; unsigned int pie: 1;
@ -398,6 +395,12 @@ struct bfd_link_info
unloaded. */ unloaded. */
const char *fini_function; const char *fini_function;
/* Number of relaxation passes. Usually only one relaxation pass
is needed. But a backend can have as many relaxation passes as
necessary. During bfd_relax_section call, it is set to the
current pass, starting from 0. */
int relax_pass;
/* Non-zero if auto-import thunks for DATA items in pei386 DLLs /* Non-zero if auto-import thunks for DATA items in pei386 DLLs
should be generated/linked against. Set to 1 if this feature should be generated/linked against. Set to 1 if this feature
is explicitly requested by the user, -1 if enabled by default. */ is explicitly requested by the user, -1 if enabled by default. */

View File

@ -1,3 +1,15 @@
2006-04-06 H.J. Lu <hongjiu.lu@intel.com>
* emultempl/ia64elf.em: Set link_info.relax_pass to 2. Remove
link_info.need_relax_finalize.
* ldlang.c (relax_sections): New.
(lang_process): Use. Call relax_sections link_info.relax_pass
times.
* ldmain.c (main): Set link_info.relax_pass to 1. Remove
link_info.need_relax_finalize.
2006-04-05 Alan Modra <amodra@bigpond.net.au> 2006-04-05 Alan Modra <amodra@bigpond.net.au>
* Makefile.am (GENSCRIPTS): Pass prefix. * Makefile.am (GENSCRIPTS): Pass prefix.

View File

@ -32,7 +32,7 @@ static int itanium = 0;
static void static void
gld${EMULATION_NAME}_after_parse (void) gld${EMULATION_NAME}_after_parse (void)
{ {
link_info.need_relax_finalize = TRUE; link_info.relax_pass = 2;
bfd_elf${ELFSIZE}_ia64_after_parse (itanium); bfd_elf${ELFSIZE}_ia64_after_parse (itanium);
} }

View File

@ -5411,6 +5411,37 @@ lang_gc_sections (void)
bfd_gc_sections (output_bfd, &link_info); bfd_gc_sections (output_bfd, &link_info);
} }
/* Relax all sections until bfd_relax_section gives up. */
static void
relax_sections (void)
{
/* Keep relaxing until bfd_relax_section gives up. */
bfd_boolean relax_again;
do
{
relax_again = FALSE;
/* Note: pe-dll.c does something like this also. If you find
you need to change this code, you probably need to change
pe-dll.c also. DJ */
/* Do all the assignments with our current guesses as to
section sizes. */
lang_do_assignments ();
/* We must do this after lang_do_assignments, because it uses
size. */
lang_reset_memory_regions ();
/* Perform another relax pass - this time we know where the
globals are, so can make a better guess. */
lang_size_sections (&relax_again, FALSE);
}
while (relax_again);
}
void void
lang_process (void) lang_process (void)
{ {
@ -5507,38 +5538,17 @@ lang_process (void)
/* Now run around and relax if we can. */ /* Now run around and relax if we can. */
if (command_line.relax) if (command_line.relax)
{ {
/* Keep relaxing until bfd_relax_section gives up. */ /* We may need more than one relaxation pass. */
bfd_boolean relax_again; int i = link_info.relax_pass;
do /* The backend can use it to determine the current pass. */
link_info.relax_pass = 0;
while (i--)
{ {
relax_again = FALSE; relax_sections ();
link_info.relax_pass++;
/* Note: pe-dll.c does something like this also. If you find
you need to change this code, you probably need to change
pe-dll.c also. DJ */
/* Do all the assignments with our current guesses as to
section sizes. */
lang_do_assignments ();
/* We must do this after lang_do_assignments, because it uses
size. */
lang_reset_memory_regions ();
/* Perform another relax pass - this time we know where the
globals are, so can make a better guess. */
lang_size_sections (&relax_again, FALSE);
/* If the normal relax is done and the relax finalize pass
is not performed yet, we perform another relax pass. */
if (!relax_again && link_info.need_relax_finalize)
{
link_info.need_relax_finalize = FALSE;
relax_again = TRUE;
}
} }
while (relax_again);
/* Final extra sizing to report errors. */ /* Final extra sizing to report errors. */
lang_do_assignments (); lang_do_assignments ();

View File

@ -313,7 +313,7 @@ main (int argc, char **argv)
link_info.spare_dynamic_tags = 5; link_info.spare_dynamic_tags = 5;
link_info.flags = 0; link_info.flags = 0;
link_info.flags_1 = 0; link_info.flags_1 = 0;
link_info.need_relax_finalize = FALSE; link_info.relax_pass = 1;
link_info.warn_shared_textrel = FALSE; link_info.warn_shared_textrel = FALSE;
link_info.gc_sections = FALSE; link_info.gc_sections = FALSE;