ld/
authorAlan Modra <amodra@gmail.com>
Wed, 16 Aug 2006 08:31:45 +0000 (08:31 +0000)
committerAlan Modra <amodra@gmail.com>
Wed, 16 Aug 2006 08:31:45 +0000 (08:31 +0000)
PR 3052
* ldlang.h (lang_output_section_statement_type): Replace
"processed" field with "processed_vma" and "processed_lma".
* ldlang.c (lang_do_assignments_1): Move lma setting code..
(lang_size_sections_1): ..to here.
(lang_reset_memory_regions): Adjust for
lang_output_section_statement_type change.
* ldexp.c (fold_name): Likewise.

And this is something I forgot the check in from the previous patch.
ld/testsuite/
* ld-scripts/overlay-size-map.d: Adjust.

ld/ChangeLog
ld/ldexp.c
ld/ldlang.c
ld/ldlang.h
ld/testsuite/ChangeLog
ld/testsuite/ld-scripts/overlay-size-map.d

index d74b0a85446402d47207a30aa480430124bff0b7..206faf009b8139b055ae30ad0601fd138e8eed46 100644 (file)
@@ -1,3 +1,14 @@
+2006-08-16  Alan Modra  <amodra@bigpond.net.au>
+
+       PR 3052
+       * ldlang.h (lang_output_section_statement_type): Replace
+       "processed" field with "processed_vma" and "processed_lma".
+       * ldlang.c (lang_do_assignments_1): Move lma setting code..
+       (lang_size_sections_1): ..to here.
+       (lang_reset_memory_regions): Adjust for
+       lang_output_section_statement_type change.
+       * ldexp.c (fold_name): Likewise.
+
 2006-08-08  Peter S. Mazinger  <ps.m@gmx.net>
 
        * emulparams/armelf.sh (MAXPAGESIZE): Changed to
index 71f4c8e31547a4fb951acc3ac4cbe06fdc042dd8..22937a27209b95412bf9854208c9539dadd61c88 100644 (file)
@@ -563,7 +563,7 @@ fold_name (etree_type *tree)
          lang_output_section_statement_type *os;
 
          os = lang_output_section_find (tree->name.name);
-         if (os != NULL && os->processed)
+         if (os != NULL && os->processed_vma)
            new_rel (0, NULL, os->bfd_section);
        }
       break;
@@ -574,7 +574,7 @@ fold_name (etree_type *tree)
          lang_output_section_statement_type *os;
 
          os = lang_output_section_find (tree->name.name);
-         if (os != NULL && os->processed)
+         if (os != NULL && os->processed_lma)
            {
              if (os->load_base == NULL)
                new_rel (os->bfd_section->lma - os->bfd_section->vma,
@@ -594,7 +594,7 @@ fold_name (etree_type *tree)
          os = lang_output_section_find (tree->name.name);
          if (os == NULL)
            new_abs (0);
-         else if (os->processed)
+         else if (os->processed_vma)
            new_abs (os->bfd_section->size / opb);
        }
       break;
index 0ee11569700f03d613934d566796343f0004b28e..e478bd8ba26785f85dd130453ed84abefe67420d 100644 (file)
@@ -4228,11 +4228,12 @@ lang_size_sections_1
          {
            bfd_vma newdot, after;
            lang_output_section_statement_type *os;
+           lang_memory_region_type *r;
 
            os = &s->output_section_statement;
            if (os->addr_tree != NULL)
              {
-               os->processed = FALSE;
+               os->processed_vma = FALSE;
                exp_fold_tree (os->addr_tree, bfd_abs_section_ptr, &dot);
 
                if (!expld.result.valid_p
@@ -4361,24 +4362,90 @@ lang_size_sections_1
            lang_size_sections_1 (os->children.head, os, &os->children.head,
                                  os->fill, newdot, relax, check_regions);
 
-           os->processed = TRUE;
+           os->processed_vma = TRUE;
 
            if (bfd_is_abs_section (os->bfd_section) || os->ignored)
+             ASSERT (os->bfd_section->size == 0);
+           else
              {
-               ASSERT (os->bfd_section->size == 0);
-               break;
+               dot = os->bfd_section->vma;
+
+               /* Put the section within the requested block size, or
+                  align at the block boundary.  */
+               after = ((dot
+                         + TO_ADDR (os->bfd_section->size)
+                         + os->block_value - 1)
+                        & - (bfd_vma) os->block_value);
+
+               os->bfd_section->size = TO_SIZE (after - os->bfd_section->vma);
+             }
+
+           /* Set section lma.  */
+           r = os->region;
+           if (r == NULL)
+             r = lang_memory_region_lookup (DEFAULT_MEMORY_REGION, FALSE);
+
+           if (os->load_base)
+             {
+               bfd_vma lma = exp_get_abs_int (os->load_base, 0, "load base");
+               os->bfd_section->lma = lma;
              }
+           else if (os->region != NULL
+                    && os->lma_region != NULL
+                    && os->lma_region != os->region)
+             {
+               bfd_vma lma = os->lma_region->current;
 
-           dot = os->bfd_section->vma;
+               if (os->section_alignment != -1)
+                 lma = align_power (lma, os->section_alignment);
+               os->bfd_section->lma = lma;
+             }
+           else if (r->last_os != NULL)
+             {
+               bfd_vma lma;
+               asection *last;
+
+               last = r->last_os->output_section_statement.bfd_section;
+               /* If dot moved backwards (which is invalid according
+                  to ld docs) then leave lma equal to vma.  This
+                  keeps users of buggy ld scripts happy.  */
+               if (dot >= last->vma)
+                 {
+                   /* If the current vma overlaps the previous section,
+                      then set the current lma to that at the end of
+                      the previous section.  The previous section was
+                      probably an overlay.  */
+                   if ((dot >= last->vma
+                        && dot < last->vma + last->size)
+                       || (last->vma >= dot
+                           && last->vma < dot + os->bfd_section->size))
+                     lma = last->lma + last->size;
+
+                   /* Otherwise, keep the same lma to vma relationship
+                      as the previous section.  */
+                   else
+                     lma = dot + last->lma - last->vma;
+
+                   if (os->section_alignment != -1)
+                     lma = align_power (lma, os->section_alignment);
+                   os->bfd_section->lma = lma;
+                 }
+             }
+           os->processed_lma = TRUE;
 
-           /* Put the section within the requested block size, or
-              align at the block boundary.  */
-           after = ((dot
-                     + TO_ADDR (os->bfd_section->size)
-                     + os->block_value - 1)
-                    & - (bfd_vma) os->block_value);
+           if (bfd_is_abs_section (os->bfd_section) || os->ignored)
+             break;
 
-           os->bfd_section->size = TO_SIZE (after - os->bfd_section->vma);
+           /* Keep track of normal sections using the default
+              lma region.  We use this to set the lma for
+              following sections.  Overlays or other linker
+              script assignment to lma might mean that the
+              default lma == vma is incorrect.  */
+           if (((os->bfd_section->flags & SEC_HAS_CONTENTS) != 0
+                || (os->bfd_section->flags & SEC_THREAD_LOCAL) == 0)
+               && os->lma_region == NULL
+               && !link_info.relocatable)
+             r->last_os = s;
 
            /* .tbss sections effectively have zero size.  */
            if ((os->bfd_section->flags & SEC_HAS_CONTENTS) != 0
@@ -4410,14 +4477,12 @@ lang_size_sections_1
 
                if (os->lma_region != NULL && os->lma_region != os->region)
                  {
-                   /* Set load_base, which will be handled later.  */
-                   os->load_base = exp_intop (os->lma_region->current);
-                   os->lma_region->current +=
-                     TO_ADDR (os->bfd_section->size);
+                   os->lma_region->current
+                     = os->bfd_section->lma + TO_ADDR (os->bfd_section->size);
 
                    if (check_regions)
                      os_region_check (os, os->lma_region, NULL,
-                                      os->lma_region->current);
+                                      os->bfd_section->lma);
                  }
              }
          }
@@ -4717,62 +4782,15 @@ lang_do_assignments_1 (lang_statement_union_type *s,
            os = &(s->output_section_statement);
            if (os->bfd_section != NULL && !os->ignored)
              {
-               lang_memory_region_type *r;
-
                dot = os->bfd_section->vma;
-               r = os->region;
-               if (r == NULL)
-                 r = lang_memory_region_lookup (DEFAULT_MEMORY_REGION, FALSE);
-
-               if (os->load_base)
-                 os->bfd_section->lma
-                   = exp_get_abs_int (os->load_base, 0, "load base");
-               else if (r->last_os != NULL)
-                 {
-                   asection *last;
-                   bfd_vma lma;
 
-                   last = r->last_os->output_section_statement.bfd_section;
-
-                   /* If the current vma overlaps the previous section,
-                      then set the current lma to that at the end of
-                      the previous section.  The previous section was
-                      probably an overlay.  */
-                   if ((dot >= last->vma
-                        && dot < last->vma + last->size)
-                       || (last->vma >= dot
-                           && last->vma < dot + os->bfd_section->size))
-                     lma = last->lma + last->size;
-
-                   /* Otherwise, keep the same lma to vma relationship
-                      as the previous section.  */
-                   else
-                     lma = dot + last->lma - last->vma;
-
-                   if (os->section_alignment != -1)
-                     lma = align_power (lma, os->section_alignment);
-                   os->bfd_section->lma = lma;
-                 }
-
-               lang_do_assignments_1 (os->children.head,
-                                      os, os->fill, dot);
+               lang_do_assignments_1 (os->children.head, os, os->fill, dot);
 
                /* .tbss sections effectively have zero size.  */
                if ((os->bfd_section->flags & SEC_HAS_CONTENTS) != 0
                    || (os->bfd_section->flags & SEC_THREAD_LOCAL) == 0
                    || link_info.relocatable)
-                 {
-                   dot += TO_ADDR (os->bfd_section->size);
-
-                   /* Keep track of normal sections using the default
-                      lma region.  We use this to set the lma for
-                      following sections.  Overlays or other linker
-                      script assignment to lma might mean that the
-                      default lma == vma is incorrect.  */
-                   if (!link_info.relocatable
-                       && os->lma_region == NULL)
-                     r->last_os = s;
-                 }
+                 dot += TO_ADDR (os->bfd_section->size);
              }
          }
          break;
@@ -5451,7 +5469,10 @@ lang_reset_memory_regions (void)
   for (os = &lang_output_section_statement.head->output_section_statement;
        os != NULL;
        os = os->next)
-    os->processed = FALSE;
+    {
+      os->processed_vma = FALSE;
+      os->processed_lma = FALSE;
+    }
 
   for (o = output_bfd->sections; o != NULL; o = o->next)
     {
index c23c3e5ed5d861153989123323494cfcba5bcc00..1c135b6b24708648599b982c98e1400f4f4e9e52 100644 (file)
@@ -150,7 +150,8 @@ typedef struct lang_output_section_statement_struct
   int constraint;
   flagword flags;
   enum section_type sectype;
-  unsigned int processed : 1;
+  unsigned int processed_vma : 1;
+  unsigned int processed_lma : 1;
   unsigned int all_input_readonly : 1;
   unsigned int ignored : 1; 
 } lang_output_section_statement_type;
index 4fc6599c83f2e3d527cbc016befd08afa18ab1fc..f07e2ca4aad16cafadc5dd773d5bfb6c483bfee1 100644 (file)
@@ -1,3 +1,7 @@
+2006-08-16  Alan Modra  <amodra@bigpond.net.au>
+
+       * ld-scripts/overlay-size-map.d: Update.
+
 2006-08-11  Thiemo Seufer  <ths@mips.com>
 
        * ld-elfcomm/elfcomm.exp (dump_common1): Extend regexp to match also
        * ld-mips-elf/hash1b.d, ld-mips-elf/hash1c.d: New tests.
        * ld-mips-elf/mips-elf.exp: Run them.
 
-2006-07-26  Alan Modra  <amodra@bigpond.net.au>
-
-       * ld-scripts/overlay-size-map.d: Update.
-
 2006-07-25  Thiemo Seufer  <ths@mips.com>
 
        * ld-mips-elf/mips16-call-global-2.s,
index 852ed81b4b34cb5ad46c43a9743d8c7f65df35bc..cd35db04fc4d72cca6a8810a779cd16cd1f83696 100644 (file)
@@ -5,19 +5,19 @@
 #...
 \.bss3 *0x0*20000 *0x20
 #...
-\.mtext *0x0*10000 *0x20 load address 0x0*30000
+\.mtext *0x0*10000 *0x20
 #...
 \.mbss *0x0*20030 *0x230 load address 0x0*20060
 #...
-\.text1 *0x0*10020 *0x80 load address 0x0*30020
+\.text1 *0x0*10020 *0x80
 #...
-\.text2 *0x0*10020 *0x40 load address 0x0*300a0
+\.text2 *0x0*10020 *0x40
 #...
-\.text3 *0x0*10020 *0x20 load address 0x0*300e0
+\.text3 *0x0*10020 *0x20
 #...
-\.data1 *0x0*20260 *0x30 load address 0x0*30100
+\.data1 *0x0*20260 *0x30
 #...
-\.data2 *0x0*20260 *0x40 load address 0x0*30130
+\.data2 *0x0*20260 *0x40
 #...
-\.data3 *0x0*20260 *0x50 load address 0x0*30170
+\.data3 *0x0*20260 *0x50
 #pass