From: "H.J. Lu" <hjl.tools@gmail.com>
To: Fangrui Song <maskray@google.com>
Cc: binutils@sourceware.org, mintsuki@protonmail.com,
Fangrui Song <maskray@gcc.gnu.org>
Subject: Re: [PATCH] Don't set ET_EXEC for -pie -Ttext-segment= (PR31795)
Date: Tue, 28 May 2024 05:24:16 -0700 [thread overview]
Message-ID: <CAMe9rOrpuH62ZgGfUFmq+yz=E=Muwg1nQKWgmhTvdx4aHWHehg@mail.gmail.com> (raw)
In-Reply-To: <20240528042803.2007198-1-maskray@google.com>
On Mon, May 27, 2024 at 9:28 PM Fangrui Song <maskray@google.com> wrote:
>
> From: Fangrui Song <maskray@gcc.gnu.org>
>
> Commit 58e7ebacdd97c858834c07c7dce098aeacd500fb added the special case
> that sets ET_EXEC for -pie -Ttext-segment=$non_zero. This was to
> support a way[1] to ensure that the address of the first byte is >=
> -Ttext-segment=.
>
> % cat a.c
> #include <stdio.h>
> int main() { printf("%p\n", main); }
> % gcc -pie a.c -fuse-ld=bfd -Wl,--no-relax,-Ttext-segment=0x600000000000 -o a
> % ./a
> 0x600000001139
> % ./a
> 0x600000001139 # no ASLR
>
> While changing ET_DYN to ET_EXEC fulfills the address requirement, it
> disables ASLR, which may be undesired. (While Linux kernel/glibc do not
> provide the address>=p_vaddr guarantee, this is technically feasible to
> support.)
>
> Since commit e8f6c2a5bab10b039a12b69a30a8248c91161e11, --no-pie has been
> available and we can do the following to use crtbeginS.o and ET_EXEC.
> (Using crtbegin.o could lead to R_X86_64_32/R_X86_64_32S relocation
> issues with a high address.)
>
> % gcc -pie -Wl,-no-pie a.c -fuse-ld=bfd -Wl,--no-relax,-Ttext-segment=0x600000000000 -o a
> % ./a
> 0x600000001139
> % ./a
> 0x600000001139 # no ASLR
>
> [1]: https://sourceware.org/pipermail/binutils/2013-December/083381.html
> ---
> bfd/elf.c | 26 +++-----------------------
> ld/testsuite/ld-pie/vaddr-1.d | 2 +-
> 2 files changed, 4 insertions(+), 24 deletions(-)
>
> diff --git a/bfd/elf.c b/bfd/elf.c
> index 74236a658fd..a8a9be53c17 100644
> --- a/bfd/elf.c
> +++ b/bfd/elf.c
> @@ -7150,35 +7150,15 @@ _bfd_elf_init_file_header (bfd *abfd,
> return true;
> }
>
> -/* Set e_type in ELF header to ET_EXEC for -pie -Ttext-segment=.
> -
> - FIXME: We used to have code here to sort the PT_LOAD segments into
> +/* FIXME: We used to have code here to sort the PT_LOAD segments into
> ascending order, as per the ELF spec. But this breaks some programs,
> including the Linux kernel. But really either the spec should be
> changed or the programs updated. */
>
> bool
> -_bfd_elf_modify_headers (bfd *obfd, struct bfd_link_info *link_info)
> +_bfd_elf_modify_headers (bfd *obfd ATTRIBUTE_UNUSED,
> + struct bfd_link_info *link_info ATTRIBUTE_UNUSED)
> {
> - if (link_info != NULL && bfd_link_pie (link_info))
> - {
> - Elf_Internal_Ehdr *i_ehdrp = elf_elfheader (obfd);
> - unsigned int num_segments = i_ehdrp->e_phnum;
> - struct elf_obj_tdata *tdata = elf_tdata (obfd);
> - Elf_Internal_Phdr *segment = tdata->phdr;
> - Elf_Internal_Phdr *end_segment = &segment[num_segments];
> -
> - /* Find the lowest p_vaddr in PT_LOAD segments. */
> - bfd_vma p_vaddr = (bfd_vma) -1;
> - for (; segment < end_segment; segment++)
> - if (segment->p_type == PT_LOAD && p_vaddr > segment->p_vaddr)
> - p_vaddr = segment->p_vaddr;
> -
> - /* Set e_type to ET_EXEC if the lowest p_vaddr in PT_LOAD
> - segments is non-zero. */
> - if (p_vaddr)
> - i_ehdrp->e_type = ET_EXEC;
This is required to create a small model executable guaranteed to be
loaded at an address specified with -Wl,-Ttext-segment=0x100000000
on x86-64. This change will break such programs.
> - }
> return true;
> }
>
> diff --git a/ld/testsuite/ld-pie/vaddr-1.d b/ld/testsuite/ld-pie/vaddr-1.d
> index 7b5f9922718..98eff841193 100644
> --- a/ld/testsuite/ld-pie/vaddr-1.d
> +++ b/ld/testsuite/ld-pie/vaddr-1.d
> @@ -5,5 +5,5 @@
>
> ELF Header:
> #...
> - Type: EXEC \(Executable file\)
> + Type: DYN \(Position-Independent Executable file\)
> #pass
> --
> 2.45.1.288.g0e0cd299f1-goog
>
--
H.J.
prev parent reply other threads:[~2024-05-28 12:24 UTC|newest]
Thread overview: 2+ messages / expand[flat|nested] mbox.gz Atom feed top
2024-05-28 4:28 Fangrui Song
2024-05-28 12:24 ` H.J. Lu [this message]
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to='CAMe9rOrpuH62ZgGfUFmq+yz=E=Muwg1nQKWgmhTvdx4aHWHehg@mail.gmail.com' \
--to=hjl.tools@gmail.com \
--cc=binutils@sourceware.org \
--cc=maskray@gcc.gnu.org \
--cc=maskray@google.com \
--cc=mintsuki@protonmail.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).