bfd/
* elf.c (assign_file_positions_for_load_sections): Retrieve maxpagesize from m->p_align if it is valid. Set p_vaddr, p_paddr and p_align earlier. Revert 2006-05-19 change to p_align. (copy_elf_program_header): Copy p_align. Set p_align_valid. include/elf/ * internal.h (elf_segment_map): Add p_align and p_align_valid.
This commit is contained in:
parent
6a8d9e540a
commit
3f570048d7
4 changed files with 64 additions and 28 deletions
|
@ -1,3 +1,11 @@
|
|||
2006-05-27 Alan Modra <amodra@bigpond.net.au>
|
||||
H.J. Lu <hongjiu.lu@intel.com>
|
||||
|
||||
* elf.c (assign_file_positions_for_load_sections): Retrieve
|
||||
maxpagesize from m->p_align if it is valid. Set p_vaddr,
|
||||
p_paddr and p_align earlier. Revert 2006-05-19 change to p_align.
|
||||
(copy_elf_program_header): Copy p_align. Set p_align_valid.
|
||||
|
||||
2006-05-26 H.J. Lu <hongjiu.lu@intel.com>
|
||||
|
||||
* elf64-x86-64.c (ELF_MINPAGESIZE): Changed to 0x1000.
|
||||
|
|
73
bfd/elf.c
73
bfd/elf.c
|
@ -4111,6 +4111,7 @@ assign_file_positions_for_load_sections (bfd *abfd,
|
|||
Elf_Internal_Phdr *phdrs;
|
||||
Elf_Internal_Phdr *p;
|
||||
file_ptr off, voff;
|
||||
bfd_size_type maxpagesize;
|
||||
unsigned int count;
|
||||
unsigned int alloc;
|
||||
unsigned int i;
|
||||
|
@ -4196,6 +4197,10 @@ assign_file_positions_for_load_sections (bfd *abfd,
|
|||
if (phdrs == NULL)
|
||||
return FALSE;
|
||||
|
||||
maxpagesize = 1;
|
||||
if ((abfd->flags & D_PAGED) != 0)
|
||||
maxpagesize = bed->maxpagesize;
|
||||
|
||||
off = bed->s->sizeof_ehdr;
|
||||
off += alloc * bed->s->sizeof_phdr;
|
||||
|
||||
|
@ -4227,6 +4232,39 @@ assign_file_positions_for_load_sections (bfd *abfd,
|
|||
p->p_type = m->p_type;
|
||||
p->p_flags = m->p_flags;
|
||||
|
||||
if (m->count == 0)
|
||||
p->p_vaddr = 0;
|
||||
else
|
||||
p->p_vaddr = m->sections[0]->vma;
|
||||
|
||||
if (m->p_paddr_valid)
|
||||
p->p_paddr = m->p_paddr;
|
||||
else if (m->count == 0)
|
||||
p->p_paddr = 0;
|
||||
else
|
||||
p->p_paddr = m->sections[0]->lma;
|
||||
|
||||
if (p->p_type == PT_LOAD
|
||||
&& (abfd->flags & D_PAGED) != 0)
|
||||
{
|
||||
/* p_align in demand paged PT_LOAD segments effectively stores
|
||||
the maximum page size. When copying an executable with
|
||||
objcopy, we set m->p_align from the input file. Use this
|
||||
value for maxpagesize rather than bed->maxpagesize, which
|
||||
may be different. Note that we use maxpagesize for PT_TLS
|
||||
segment alignment later in this function, so we are relying
|
||||
on at least one PT_LOAD segment appearing before a PT_TLS
|
||||
segment. */
|
||||
if (m->p_align_valid)
|
||||
maxpagesize = m->p_align;
|
||||
|
||||
p->p_align = maxpagesize;
|
||||
}
|
||||
else if (m->count == 0)
|
||||
p->p_align = 1 << bed->s->log_file_align;
|
||||
else
|
||||
p->p_align = 0;
|
||||
|
||||
if (p->p_type == PT_LOAD
|
||||
&& m->count > 0)
|
||||
{
|
||||
|
@ -4244,8 +4282,8 @@ assign_file_positions_for_load_sections (bfd *abfd,
|
|||
}
|
||||
align = (bfd_size_type) 1 << align_power;
|
||||
|
||||
if ((abfd->flags & D_PAGED) != 0 && bed->maxpagesize > align)
|
||||
align = bed->maxpagesize;
|
||||
if (align < maxpagesize)
|
||||
align = maxpagesize;
|
||||
|
||||
adjust = vma_page_aligned_bias (m->sections[0]->vma, off, align);
|
||||
off += adjust;
|
||||
|
@ -4286,26 +4324,6 @@ assign_file_positions_for_load_sections (bfd *abfd,
|
|||
return FALSE;
|
||||
}
|
||||
|
||||
if (m->count == 0)
|
||||
p->p_vaddr = 0;
|
||||
else
|
||||
p->p_vaddr = m->sections[0]->vma;
|
||||
|
||||
if (m->p_paddr_valid)
|
||||
p->p_paddr = m->p_paddr;
|
||||
else if (m->count == 0)
|
||||
p->p_paddr = 0;
|
||||
else
|
||||
p->p_paddr = m->sections[0]->lma;
|
||||
|
||||
if (p->p_type == PT_LOAD
|
||||
&& (abfd->flags & D_PAGED) != 0)
|
||||
p->p_align = bed->maxpagesize;
|
||||
else if (m->count == 0)
|
||||
p->p_align = 1 << bed->s->log_file_align;
|
||||
else
|
||||
p->p_align = 0;
|
||||
|
||||
p->p_offset = 0;
|
||||
p->p_filesz = 0;
|
||||
p->p_memsz = 0;
|
||||
|
@ -4386,7 +4404,7 @@ assign_file_positions_for_load_sections (bfd *abfd,
|
|||
|
||||
sec = *secpp;
|
||||
flags = sec->flags;
|
||||
align = 1 << bfd_get_section_alignment (abfd, sec);
|
||||
align = (bfd_size_type) 1 << bfd_get_section_alignment (abfd, sec);
|
||||
|
||||
if (p->p_type == PT_LOAD
|
||||
|| p->p_type == PT_TLS)
|
||||
|
@ -4416,8 +4434,8 @@ assign_file_positions_for_load_sections (bfd *abfd,
|
|||
/* The section VMA must equal the file position
|
||||
modulo the page size. */
|
||||
bfd_size_type page = align;
|
||||
if ((abfd->flags & D_PAGED) != 0 && bed->maxpagesize > page)
|
||||
page = bed->maxpagesize;
|
||||
if (page < maxpagesize)
|
||||
page = maxpagesize;
|
||||
adjust = vma_page_aligned_bias (sec->vma,
|
||||
p->p_vaddr + p->p_memsz,
|
||||
page);
|
||||
|
@ -4494,8 +4512,7 @@ assign_file_positions_for_load_sections (bfd *abfd,
|
|||
|
||||
if (align > p->p_align
|
||||
&& (p->p_type != PT_LOAD
|
||||
|| (abfd->flags & D_PAGED) == 0
|
||||
|| ((p->p_vaddr - p->p_offset) & (align - 1)) == 0))
|
||||
|| (abfd->flags & D_PAGED) == 0))
|
||||
p->p_align = align;
|
||||
}
|
||||
|
||||
|
@ -5800,6 +5817,8 @@ copy_elf_program_header (bfd *ibfd, bfd *obfd)
|
|||
map->p_flags_valid = 1;
|
||||
map->p_paddr = segment->p_paddr;
|
||||
map->p_paddr_valid = 1;
|
||||
map->p_align = segment->p_align;
|
||||
map->p_align_valid = 1;
|
||||
|
||||
/* Determine if this segment contains the ELF file header
|
||||
and if it contains the program headers themselves. */
|
||||
|
|
|
@ -1,3 +1,7 @@
|
|||
2006-05-27 H.J. Lu <hongjiu.lu@intel.com>
|
||||
|
||||
* internal.h (struct elf_segment_map): Add p_align and p_align_valid.
|
||||
|
||||
2006-05-24 Carlos O'Donell <carlos@systemhalted.org>
|
||||
Randolph Chung <randolph@tausq.org>
|
||||
* hppa.h (R_PARISC_TLS_GD21L, R_PARISC_TLS_GD14R, R_PARISC_TLS_GDCALL,
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/* ELF support for BFD.
|
||||
Copyright 1991, 1992, 1993, 1994, 1995, 1997, 1998, 2000, 2001, 2002,
|
||||
2003 Free Software Foundation, Inc.
|
||||
2003, 2006 Free Software Foundation, Inc.
|
||||
|
||||
Written by Fred Fish @ Cygnus Support, from information published
|
||||
in "UNIX System V Release 4, Programmers Guide: ANSI C and
|
||||
|
@ -235,12 +235,17 @@ struct elf_segment_map
|
|||
unsigned long p_flags;
|
||||
/* Program segment physical address. */
|
||||
bfd_vma p_paddr;
|
||||
/* Program segment alignment. */
|
||||
bfd_vma p_align;
|
||||
/* Whether the p_flags field is valid; if not, the flags are based
|
||||
on the section flags. */
|
||||
unsigned int p_flags_valid : 1;
|
||||
/* Whether the p_paddr field is valid; if not, the physical address
|
||||
is based on the section lma values. */
|
||||
unsigned int p_paddr_valid : 1;
|
||||
/* Whether the p_align field is valid; if not, PT_LOAD segment
|
||||
alignment is based on the default maximum page size. */
|
||||
unsigned int p_align_valid : 1;
|
||||
/* Whether this segment includes the file header. */
|
||||
unsigned int includes_filehdr : 1;
|
||||
/* Whether this segment includes the program headers. */
|
||||
|
|
Loading…
Reference in a new issue