+2018-01-11 H.J. Lu <hongjiu.lu@intel.com>
+
+ PR ld/22393
+ * elf.c (_bfd_elf_map_sections_to_segments): When generating
+ separate code and read-only data LOAD segments, create a new
+ LOAD segment if the previous section contains text and the
+ current section doesn't or vice versa. Don't put a writable
+ section in a read-only segment if there is a RELRO segment.
+
2018-01-11 H.J. Lu <hongjiu.lu@intel.com>
PR ld/22649
asection **hdrpp;
bfd_boolean phdr_in_segment = TRUE;
bfd_boolean writable;
+ bfd_boolean executable;
int tls_count = 0;
asection *first_tls = NULL;
asection *first_mbind = NULL;
if (maxpagesize == 0)
maxpagesize = 1;
writable = FALSE;
+ executable = FALSE;
dynsec = bfd_get_section_by_name (abfd, ".dynamic");
if (dynsec != NULL
&& (dynsec->flags & SEC_LOAD) == 0)
file, then there is no other reason for a new segment. */
new_segment = FALSE;
}
+ else if (info != NULL
+ && info->separate_code
+ && executable != ((hdr->flags & SEC_CODE) != 0))
+ {
+ new_segment = TRUE;
+ }
else if (! writable
&& (hdr->flags & SEC_READONLY) == 0
- && (((last_hdr->lma + last_size - 1) & -maxpagesize)
- != (hdr->lma & -maxpagesize)))
+ && ((info != NULL
+ && info->relro_end > info->relro_start)
+ || (((last_hdr->lma + last_size - 1) & -maxpagesize)
+ != (hdr->lma & -maxpagesize))))
{
/* We don't want to put a writable section in a read only
segment, unless they are on the same page in memory
- anyhow. We already know that the last section does not
- bring us past the current section on the page, so the
- only case in which the new section is not on the same
- page as the previous section is when the previous section
- ends precisely on a page boundary. */
+ anyhow and there is no RELRO segment. We already
+ know that the last section does not bring us past the
+ current section on the page, so the only case in which
+ the new section is not on the same page as the previous
+ section is when the previous section ends precisely on
+ a page boundary. */
new_segment = TRUE;
}
else
{
if ((hdr->flags & SEC_READONLY) == 0)
writable = TRUE;
+ if ((hdr->flags & SEC_CODE) != 0)
+ executable = TRUE;
last_hdr = hdr;
/* .tbss sections effectively have zero size. */
if ((hdr->flags & (SEC_THREAD_LOCAL | SEC_LOAD))
else
writable = FALSE;
+ if ((hdr->flags & SEC_CODE) == 0)
+ executable = FALSE;
+ else
+ executable = TRUE;
+
last_hdr = hdr;
/* .tbss sections effectively have zero size. */
if ((hdr->flags & (SEC_THREAD_LOCAL | SEC_LOAD)) != SEC_THREAD_LOCAL)