diff options
author | Iain Sandoe <iain@codesourcery.com> | 2012-02-10 11:24:44 +0000 |
---|---|---|
committer | Iain Sandoe <iain@codesourcery.com> | 2012-02-10 11:24:44 +0000 |
commit | 09903f4b533109ab6d161a6c9b513b6f85aa8028 (patch) | |
tree | e5fb52868e076b65e31c06812c68b383d330ea84 /bfd/mach-o.c | |
parent | 632039e0a80cb94726526c8bfac3bf0d2c863dbc (diff) | |
download | binutils-09903f4b533109ab6d161a6c9b513b6f85aa8028.zip binutils-09903f4b533109ab6d161a6c9b513b6f85aa8028.tar.gz binutils-09903f4b533109ab6d161a6c9b513b6f85aa8028.tar.bz2 |
bfd:
* mach-o.c (bfd_mach_o_build_seg_command): Count zerofill section
vma additions in their logical, rather than physical order.
Diffstat (limited to 'bfd/mach-o.c')
-rw-r--r-- | bfd/mach-o.c | 63 |
1 files changed, 52 insertions, 11 deletions
diff --git a/bfd/mach-o.c b/bfd/mach-o.c index 73d4594..a7b9f80 100644 --- a/bfd/mach-o.c +++ b/bfd/mach-o.c @@ -2026,7 +2026,12 @@ bfd_mach_o_build_seg_command (const char *segment, seg->sect_head = NULL; seg->sect_tail = NULL; - /* Append sections to the segment. */ + /* Append sections to the segment. + + This is a little tedious, we have to honor the need to account zerofill + sections after all the rest. This forces us to do the calculation of + total vmsize in three passes so that any alignment increments are + properly accounted. */ for (i = 0; i < mdata->nsects; ++i) { @@ -2039,14 +2044,10 @@ bfd_mach_o_build_seg_command (const char *segment, && strncmp (segment, s->segname, BFD_MACH_O_SEGNAME_SIZE) != 0) continue; + /* Although we account for zerofill section sizes in vm order, they are + placed in the file in source sequence. */ bfd_mach_o_append_section_to_segment (seg, sec); - s->offset = 0; - if (s->size > 0) - { - seg->vmsize = FILE_ALIGN (seg->vmsize, s->align); - seg->vmsize += s->size; - } /* Zerofill sections have zero file size & offset, and are not written. */ @@ -2057,19 +2058,59 @@ bfd_mach_o_build_seg_command (const char *segment, if (s->size > 0) { + seg->vmsize = FILE_ALIGN (seg->vmsize, s->align); + seg->vmsize += s->size; + + seg->filesize = FILE_ALIGN (seg->filesize, s->align); + seg->filesize += s->size; + mdata->filelen = FILE_ALIGN (mdata->filelen, s->align); s->offset = mdata->filelen; } sec->filepos = s->offset; - mdata->filelen += s->size; } - seg->filesize = mdata->filelen - seg->fileoff; - seg->filesize = FILE_ALIGN(seg->filesize, 2); + /* Now pass through again, for zerofill, only now we just update the vmsize. */ + for (i = 0; i < mdata->nsects; ++i) + { + bfd_mach_o_section *s = mdata->sections[i]; + + if ((s->flags & BFD_MACH_O_SECTION_TYPE_MASK) != BFD_MACH_O_S_ZEROFILL) + continue; + + if (! is_mho + && strncmp (segment, s->segname, BFD_MACH_O_SEGNAME_SIZE) != 0) + continue; + + if (s->size > 0) + { + seg->vmsize = FILE_ALIGN (seg->vmsize, s->align); + seg->vmsize += s->size; + } + } + + /* Now pass through again, for zerofill_GB. */ + for (i = 0; i < mdata->nsects; ++i) + { + bfd_mach_o_section *s = mdata->sections[i]; + + if ((s->flags & BFD_MACH_O_SECTION_TYPE_MASK) != BFD_MACH_O_S_GB_ZEROFILL) + continue; + + if (! is_mho + && strncmp (segment, s->segname, BFD_MACH_O_SEGNAME_SIZE) != 0) + continue; + + if (s->size > 0) + { + seg->vmsize = FILE_ALIGN (seg->vmsize, s->align); + seg->vmsize += s->size; + } + } - /* Allocate relocation room. */ + /* Allocate space for the relocations. */ mdata->filelen = FILE_ALIGN(mdata->filelen, 2); for (i = 0; i < mdata->nsects; ++i) |