public inbox for binutils@sourceware.org
 help / color / mirror / Atom feed
From: "H. J. Lu" <hjl@lucon.org>
To: Richard Henderson <rth@redhat.com>, gcc@gcc.gnu.org
Cc: binutils@sources.redhat.com, amodra@bigpond.net.au, jakub@redhat.com
Subject: PATCH: Fix the relax finalize pass
Date: Wed, 14 May 2003 22:53:00 -0000	[thread overview]
Message-ID: <20030514155346.A9453@lucon.org> (raw)
In-Reply-To: <20030514075330.GC16863@redhat.com>; from rth@redhat.com on Wed, May 14, 2003 at 12:53:30AM -0700

[-- Attachment #1: Type: text/plain, Size: 453 bytes --]

On Wed, May 14, 2003 at 12:53:30AM -0700, Richard Henderson wrote:
> On Tue, May 13, 2003 at 04:36:47PM -0700, H. J. Lu wrote:
> > I am not sure if it is the right usage of LTOFF22X
> 
> It is.  You're allowed to use it with any operand whatsoever.
> 
> 

The problem is linker keeps changing data segment address after the
relax finalize pass starts. It makes the GP calculation in the relax
finalize pass invalid. This patch tries to avoid it.


H.J.

[-- Attachment #2: ld-final.patch --]
[-- Type: text/plain, Size: 11106 bytes --]

2003-05-14  H.J. Lu <hongjiu.lu@intel.com>

	* ldlang.c (lang_size_sections_1): Take one more argument to
	indicate if the relax finalize pass is needed.
	(lang_size_sections): Updated.
	(lang_process): Likewise.
	* ldlang.h (lang_size_sections_1): Likewise.
	* pe-dll.c (pe_dll_fill_sections): Likewise.
	(pe_exe_fill_sections): Likewise.
	* emultempl/elf32.em (gld${EMULATION_NAME}_finish): Likewise.
	* emultempl/hppaelf.em (hppaelf_layout_sections_again): Likewise.
	* emultempl/ppc64elf.em (ppc_before_allocation): Likewise.
	(ppc_layout_sections_again): Likewise.

	* ldlang.c (lang_size_sections): Don't adjust data segment
	address after the relax finalize pass starts.
	(lang_process): Perform the relax finalize pass only when
	needed. Finalize addresses before the relax finalize pass.

--- ld/emultempl/elf32.em.final	2003-05-09 08:13:31.000000000 -0700
+++ ld/emultempl/elf32.em	2003-05-14 15:21:48.000000000 -0700
@@ -1430,7 +1430,8 @@ gld${EMULATION_NAME}_finish ()
 
       /* Resize the sections.  */
       lang_size_sections (stat_ptr->head, abs_output_section,
-			  &stat_ptr->head, 0, (bfd_vma) 0, NULL, TRUE);
+			  &stat_ptr->head, 0, (bfd_vma) 0, NULL,
+			  NULL, TRUE);
 
       /* Redo special stuff.  */
       ldemul_after_allocation ();
--- ld/emultempl/hppaelf.em.final	2003-02-28 12:53:34.000000000 -0800
+++ ld/emultempl/hppaelf.em	2003-05-14 15:21:57.000000000 -0700
@@ -231,7 +231,8 @@ hppaelf_layout_sections_again ()
 
   /* Resize the sections.  */
   lang_size_sections (stat_ptr->head, abs_output_section,
-		      &stat_ptr->head, 0, (bfd_vma) 0, NULL, TRUE);
+		      &stat_ptr->head, 0, (bfd_vma) 0, NULL, NULL,
+		      TRUE);
 
   /* Redo special stuff.  */
   ldemul_after_allocation ();
--- ld/emultempl/ppc64elf.em.final	2003-02-28 12:53:38.000000000 -0800
+++ ld/emultempl/ppc64elf.em	2003-05-14 15:22:16.000000000 -0700
@@ -118,7 +118,8 @@ ppc_before_allocation ()
 	  /* Size the sections.  This is premature, but we want to know the
 	     TLS segment layout so that certain optimizations can be done.  */
 	  lang_size_sections (stat_ptr->head, abs_output_section,
-			      &stat_ptr->head, 0, (bfd_vma) 0, NULL, TRUE);
+			      &stat_ptr->head, 0, (bfd_vma) 0,
+			      NULL, NULL, TRUE);
 
 	  if (!ppc64_elf_tls_optimize (output_bfd, &link_info))
 	    {
@@ -273,7 +274,8 @@ ppc_layout_sections_again ()
 
   /* Resize the sections.  */
   lang_size_sections (stat_ptr->head, abs_output_section,
-		      &stat_ptr->head, 0, (bfd_vma) 0, NULL, TRUE);
+		      &stat_ptr->head, 0, (bfd_vma) 0,
+		      NULL, NULL, TRUE);
 
   /* Recalculate TOC base.  */
   ldemul_after_allocation ();
--- ld/ldlang.c.final	2003-05-13 08:45:34.000000000 -0700
+++ ld/ldlang.c	2003-05-14 15:36:47.000000000 -0700
@@ -199,9 +199,10 @@ static void os_region_check
   PARAMS ((lang_output_section_statement_type *,
 	   struct memory_region_struct *, etree_type *, bfd_vma));
 static bfd_vma lang_size_sections_1
-  PARAMS ((lang_statement_union_type *, lang_output_section_statement_type *,
-	   lang_statement_union_type **, fill_type *, bfd_vma, bfd_boolean *,
-	   bfd_boolean));
+  PARAMS ((lang_statement_union_type *,
+	   lang_output_section_statement_type *,
+	   lang_statement_union_type **, fill_type *, bfd_vma,
+	   bfd_boolean *, bfd_boolean *, bfd_boolean));
 typedef void (*callback_t)
   PARAMS ((lang_wild_statement_type *, struct wildcard_list *, asection *,
 	   lang_input_statement_type *, PTR));
@@ -2978,14 +2979,15 @@ os_region_check (os, region, tree, base)
 /* Set the sizes for all the output sections.  */
 
 static bfd_vma
-lang_size_sections_1 (s, output_section_statement, prev, fill, dot, relax,
-		      check_regions)
+lang_size_sections_1 (s, output_section_statement, prev, fill, dot,
+		      relax, need_finalize_relax, check_regions)
      lang_statement_union_type *s;
      lang_output_section_statement_type *output_section_statement;
      lang_statement_union_type **prev;
      fill_type *fill;
      bfd_vma dot;
      bfd_boolean *relax;
+     bfd_boolean *need_finalize_relax;
      bfd_boolean check_regions;
 {
   unsigned opb = bfd_arch_mach_octets_per_byte (ldfile_output_architecture,
@@ -3123,8 +3125,10 @@ lang_size_sections_1 (s, output_section_
 		os->bfd_section->output_offset = 0;
 	      }
 
-	    lang_size_sections_1 (os->children.head, os, &os->children.head,
-				  os->fill, dot, relax, check_regions);
+	    lang_size_sections_1 (os->children.head, os,
+				  &os->children.head, os->fill, dot,
+				  relax, need_finalize_relax,
+				  check_regions);
 
 	    /* Put the section within the requested block size, or
 	       align at the block boundary.  */
@@ -3193,7 +3197,9 @@ lang_size_sections_1 (s, output_section_
 	  dot = lang_size_sections_1 (constructor_list.head,
 				      output_section_statement,
 				      &s->wild_statement.children.head,
-				      fill, dot, relax, check_regions);
+				      fill, dot, relax,
+				      need_finalize_relax,
+				      check_regions);
 	  break;
 
 	case lang_data_statement_enum:
@@ -3257,7 +3263,9 @@ lang_size_sections_1 (s, output_section_
 	  dot = lang_size_sections_1 (s->wild_statement.children.head,
 				      output_section_statement,
 				      &s->wild_statement.children.head,
-				      fill, dot, relax, check_regions);
+				      fill, dot, relax,
+				      need_finalize_relax,
+				      check_regions);
 
 	  break;
 
@@ -3286,6 +3294,7 @@ lang_size_sections_1 (s, output_section_
 		  einfo (_("%P%F: can't relax section: %E\n"));
 		if (again)
 		  *relax = TRUE;
+		*need_finalize_relax |= i->need_finalize_relax;
 	      }
 	    dot = size_input_section (prev, output_section_statement,
 				      output_section_statement->fill, dot);
@@ -3355,7 +3364,9 @@ lang_size_sections_1 (s, output_section_
 	  dot = lang_size_sections_1 (s->group_statement.children.head,
 				      output_section_statement,
 				      &s->group_statement.children.head,
-				      fill, dot, relax, check_regions);
+				      fill, dot, relax,
+				      need_finalize_relax,
+				      check_regions);
 	  break;
 
 	default:
@@ -3372,22 +3383,28 @@ lang_size_sections_1 (s, output_section_
 }
 
 bfd_vma
-lang_size_sections (s, output_section_statement, prev, fill, dot, relax,
-		    check_regions)
+lang_size_sections (s, output_section_statement, prev, fill, dot,
+		    relax, need_finalize_relax, check_regions)
      lang_statement_union_type *s;
      lang_output_section_statement_type *output_section_statement;
      lang_statement_union_type **prev;
      fill_type *fill;
      bfd_vma dot;
      bfd_boolean *relax;
+     bfd_boolean *need_finalize_relax;
      bfd_boolean check_regions;
 {
   bfd_vma result;
 
   exp_data_seg.phase = exp_dataseg_none;
-  result = lang_size_sections_1 (s, output_section_statement, prev, fill,
-				 dot, relax, check_regions);
-  if (exp_data_seg.phase == exp_dataseg_end_seen)
+  result = lang_size_sections_1 (s, output_section_statement, prev,
+				 fill, dot, relax, need_finalize_relax,
+				 check_regions);
+
+  /* We can't change addresses after the relax finalize pass starts
+     since the relaxation may assume addresses won't be changes.  */
+  if (!link_info.relax_finalizing
+      && exp_data_seg.phase == exp_dataseg_end_seen)
     {
       /* If DATA_SEGMENT_ALIGN DATA_SEGMENT_END pair was seen, check whether
 	 a page could be saved in the data segment.  */
@@ -3401,8 +3418,10 @@ lang_size_sections (s, output_section_st
 	  && first + last <= exp_data_seg.pagesize)
 	{
 	  exp_data_seg.phase = exp_dataseg_adjust;
-	  result = lang_size_sections_1 (s, output_section_statement, prev,
-					 fill, dot, relax, check_regions);
+	  result = lang_size_sections_1 (s, output_section_statement,
+					 prev, fill, dot, relax,
+					 need_finalize_relax,
+					 check_regions);
 	}
     }
 
@@ -4378,7 +4397,7 @@ lang_process ()
   /* Size up the sections.  */
   lang_size_sections (statement_list.head,
 		      abs_output_section,
-		      &statement_list.head, 0, (bfd_vma) 0, NULL,
+		      &statement_list.head, 0, (bfd_vma) 0, NULL, NULL,
 		      command_line.relax ? FALSE : TRUE);
 
   /* Now run around and relax if we can.  */
@@ -4386,6 +4405,7 @@ lang_process ()
     {
       /* Keep relaxing until bfd_relax_section gives up.  */
       bfd_boolean relax_again;
+      bfd_boolean need_finalize_relax;
 
       do
 	{
@@ -4408,14 +4428,29 @@ lang_process ()
 	  lang_size_sections (statement_list.head,
 			      abs_output_section,
 			      &statement_list.head, 0, (bfd_vma) 0,
-			      &relax_again, FALSE);
+			      &relax_again, &need_finalize_relax,
+			      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.relax_finalizing)
+	  if (!relax_again
+	      && need_finalize_relax
+	      && !link_info.relax_finalizing)
 	    {
 	      link_info.relax_finalizing = TRUE;
 	      relax_again = TRUE;
+	      if (exp_data_seg.phase == exp_dataseg_adjust)
+		{
+		  /* Make sure addresses are finalized.  */
+		  lang_reset_memory_regions ();
+		  lang_do_assignments (statement_list.head,
+				       abs_output_section,
+				       (fill_type *) 0, (bfd_vma) 0);
+		  lang_size_sections (statement_list.head,
+				      abs_output_section,
+				      &statement_list.head, 0,
+				      (bfd_vma) 0, NULL, NULL, TRUE);
+		}
 	    }
 	}
       while (relax_again);
@@ -4428,7 +4463,7 @@ lang_process ()
       lang_size_sections (statement_list.head,
 			  abs_output_section,
 			  & statement_list.head, 0, (bfd_vma) 0, 
-			  NULL, TRUE);
+			  NULL, NULL, TRUE);
     }
 
   /* See if anything special should be done now we know how big
--- ld/ldlang.h.final	2003-03-04 11:11:00.000000000 -0800
+++ ld/ldlang.h	2003-05-14 15:09:58.000000000 -0700
@@ -482,7 +482,9 @@ extern bfd_vma lang_size_sections
   PARAMS ((lang_statement_union_type *s,
 	   lang_output_section_statement_type *output_section_statement,
 	   lang_statement_union_type **prev, fill_type *fill,
-	   bfd_vma dot, bfd_boolean *relax, bfd_boolean check_regions));
+	   bfd_vma dot, bfd_boolean *relax,
+	   bfd_boolean *need_finalize_relax,
+	   bfd_boolean check_regions));
 extern void lang_enter_group
   PARAMS ((void));
 extern void lang_leave_group
--- ld/pe-dll.c.final	2003-04-02 13:42:02.000000000 -0800
+++ ld/pe-dll.c	2003-05-14 15:10:50.000000000 -0700
@@ -2703,7 +2703,8 @@ pe_dll_fill_sections (abfd, info)
 
       /* Resize the sections.  */
       lang_size_sections (stat_ptr->head, abs_output_section,
-			  &stat_ptr->head, 0, (bfd_vma) 0, NULL, TRUE);
+			  &stat_ptr->head, 0, (bfd_vma) 0,
+			  NULL, NULL, TRUE);
 
       /* Redo special stuff.  */
       ldemul_after_allocation ();
@@ -2738,7 +2739,8 @@ pe_exe_fill_sections (abfd, info)
 
       /* Resize the sections.  */
       lang_size_sections (stat_ptr->head, abs_output_section,
-			  &stat_ptr->head, 0, (bfd_vma) 0, NULL, TRUE);
+			  &stat_ptr->head, 0, (bfd_vma) 0,
+			  NULL, NULL, TRUE);
 
       /* Redo special stuff.  */
       ldemul_after_allocation ();

       reply	other threads:[~2003-05-14 22:53 UTC|newest]

Thread overview: 19+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
     [not found] <20030513163647.B21871@lucon.org>
     [not found] ` <20030514075330.GC16863@redhat.com>
2003-05-14 22:53   ` H. J. Lu [this message]
2003-05-14 23:22     ` Alan Modra
2003-05-14 23:28       ` H. J. Lu
2003-05-14 23:53         ` Alan Modra
2003-05-15  0:06           ` H. J. Lu
2003-05-15  0:32             ` Alan Modra
2003-05-15  1:04     ` Richard Henderson
2003-05-15  2:19       ` H. J. Lu
2003-05-15  5:34         ` Richard Henderson
2003-05-15  5:41           ` H. J. Lu
2003-05-15  6:13             ` Alan Modra
2003-05-15 14:53               ` H. J. Lu
2003-05-15 15:36                 ` Daniel Jacobowitz
2003-05-27 14:31                   ` Daniel Jacobowitz
2003-05-27 14:59                     ` H. J. Lu
2003-05-27 15:03                       ` Daniel Jacobowitz
2003-05-15  5:24       ` H. J. Lu
2003-05-15  5:40         ` Richard Henderson
2003-05-15  5:42           ` H. J. Lu

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20030514155346.A9453@lucon.org \
    --to=hjl@lucon.org \
    --cc=amodra@bigpond.net.au \
    --cc=binutils@sources.redhat.com \
    --cc=gcc@gcc.gnu.org \
    --cc=jakub@redhat.com \
    --cc=rth@redhat.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).