aboutsummaryrefslogtreecommitdiff
path: root/bfd/elf.c
diff options
context:
space:
mode:
authorH.J. Lu <hjl.tools@gmail.com>2006-11-25 00:38:14 +0000
committerH.J. Lu <hjl.tools@gmail.com>2006-11-25 00:38:14 +0000
commit9f17e2a6cded940f18630a4f6612f47e7e2f9c03 (patch)
treec83397837349e56175e534815631343424422402 /bfd/elf.c
parentb30697a1361b90003b9aaf2d7f81030934c969a1 (diff)
downloadgdb-9f17e2a6cded940f18630a4f6612f47e7e2f9c03.zip
gdb-9f17e2a6cded940f18630a4f6612f47e7e2f9c03.tar.gz
gdb-9f17e2a6cded940f18630a4f6612f47e7e2f9c03.tar.bz2
2006-11-24 H.J. Lu <hongjiu.lu@intel.com>
* elf.c (IS_SECTION_IN_INPUT_SEGMENT): New. (INCLUDE_SECTION_IN_SEGMENT): Use IS_SECTION_IN_INPUT_SEGMENT. (rewrite_elf_program_header): Don't preserve segment physical address in the output segment if the first section in the corresponding input segment is removed.
Diffstat (limited to 'bfd/elf.c')
-rw-r--r--bfd/elf.c35
1 files changed, 29 insertions, 6 deletions
diff --git a/bfd/elf.c b/bfd/elf.c
index 9550ab1..e4f4a95 100644
--- a/bfd/elf.c
+++ b/bfd/elf.c
@@ -5257,13 +5257,12 @@ rewrite_elf_program_header (bfd *ibfd, bfd *obfd)
7. SHF_TLS sections are only in PT_TLS or PT_LOAD segments.
8. PT_DYNAMIC should not contain empty sections at the beginning
(with the possible exception of .dynamic). */
-#define INCLUDE_SECTION_IN_SEGMENT(section, segment, bed) \
+#define IS_SECTION_IN_INPUT_SEGMENT(section, segment, bed) \
((((segment->p_paddr \
? IS_CONTAINED_BY_LMA (section, segment, segment->p_paddr) \
: IS_CONTAINED_BY_VMA (section, segment)) \
&& (section->flags & SEC_ALLOC) != 0) \
|| IS_COREFILE_NOTE (segment, section)) \
- && section->output_section != NULL \
&& segment->p_type != PT_GNU_STACK \
&& (segment->p_type != PT_TLS \
|| (section->flags & SEC_THREAD_LOCAL)) \
@@ -5279,6 +5278,12 @@ rewrite_elf_program_header (bfd *ibfd, bfd *obfd)
== 0)) \
&& ! section->segment_mark)
+/* If the output section of a section in the input segment is NULL,
+ it is removed from the corresponding output segment. */
+#define INCLUDE_SECTION_IN_SEGMENT(section, segment, bed) \
+ (IS_SECTION_IN_INPUT_SEGMENT (section, segment, bed) \
+ && section->output_section != NULL)
+
/* Returns TRUE iff seg1 starts after the end of seg2. */
#define SEGMENT_AFTER_SEGMENT(seg1, seg2, field) \
(seg1->field >= SEGMENT_END (seg2, seg2->field))
@@ -5386,16 +5391,27 @@ rewrite_elf_program_header (bfd *ibfd, bfd *obfd)
bfd_vma suggested_lma;
unsigned int j;
bfd_size_type amt;
+ asection * first_section;
if (segment->p_type == PT_NULL)
continue;
+ first_section = NULL;
/* Compute how many sections might be placed into this segment. */
for (section = ibfd->sections, section_count = 0;
section != NULL;
section = section->next)
- if (INCLUDE_SECTION_IN_SEGMENT (section, segment, bed))
- ++section_count;
+ {
+ /* Find the first section in the input segment, which may be
+ removed from the corresponding output segment. */
+ if (IS_SECTION_IN_INPUT_SEGMENT (section, segment, bed))
+ {
+ if (first_section == NULL)
+ first_section = section;
+ if (section->output_section != NULL)
+ ++section_count;
+ }
+ }
/* Allocate a segment map big enough to contain
all of the sections we have selected. */
@@ -5411,8 +5427,14 @@ rewrite_elf_program_header (bfd *ibfd, bfd *obfd)
map->p_type = segment->p_type;
map->p_flags = segment->p_flags;
map->p_flags_valid = 1;
- map->p_paddr = segment->p_paddr;
- map->p_paddr_valid = 1;
+ /* If the first section in the input segment is removed, there is
+ no need to preserve segment physical address in the corresponding
+ output segment. */
+ if (first_section->output_section != NULL)
+ {
+ map->p_paddr = segment->p_paddr;
+ map->p_paddr_valid = 1;
+ }
/* Determine if this segment contains the ELF file header
and if it contains the program headers themselves. */
@@ -5742,6 +5764,7 @@ rewrite_elf_program_header (bfd *ibfd, bfd *obfd)
#undef IS_CONTAINED_BY_LMA
#undef IS_COREFILE_NOTE
#undef IS_SOLARIS_PT_INTERP
+#undef IS_SECTION_IN_INPUT_SEGMENT
#undef INCLUDE_SECTION_IN_SEGMENT
#undef SEGMENT_AFTER_SEGMENT
#undef SEGMENT_OVERLAPS