From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 1792) id 055A53858D39; Sun, 30 Apr 2023 23:21:32 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org 055A53858D39 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=sourceware.org; s=default; t=1682896892; bh=1ZOY2WBELhvQ6TIjXcUIjEwuRPPYKfyzPidGApy5eEk=; h=From:To:Subject:Date:From; b=o0+ifeNxhxiiV9BnLtlYLNIstdoW8pxOdUauJMusqLbZk4YC3cJT+UvZZ2mxYq1VY 4oehJ20dnuFXObxfpJonkmiN3Xn23cq3ntsfLgCB1q3O/CD+P+CeIw2e/+nYb8mOmH OgXSPVvvVkVY3Ud32oaTEDvBUCxC+rID118LjbTY= Content-Type: text/plain; charset="us-ascii" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit From: Samuel Thibault To: glibc-cvs@sourceware.org Subject: [glibc] hurd: Make it possible to call memcpy very early X-Act-Checkin: glibc X-Git-Author: Sergey Bugaev X-Git-Refname: refs/heads/master X-Git-Oldrev: e6136c693970bd641cc526cbe204d02c0c3ba0e4 X-Git-Newrev: 2bc516020ff8642d1352e99f0f25fef002457079 Message-Id: <20230430232132.055A53858D39@sourceware.org> Date: Sun, 30 Apr 2023 23:21:32 +0000 (GMT) List-Id: https://sourceware.org/git/gitweb.cgi?p=glibc.git;h=2bc516020ff8642d1352e99f0f25fef002457079 commit 2bc516020ff8642d1352e99f0f25fef002457079 Author: Sergey Bugaev Date: Sat Apr 29 23:18:21 2023 +0300 hurd: Make it possible to call memcpy very early Normally, in static builds, the first code that runs is _start, in e.g. sysdeps/x86_64/start.S, which quickly calls __libc_start_main, passing it the argv etc. Among the first things __libc_start_main does is initializing the tunables (based on env), then CPU features, and then calls _dl_relocate_static_pie (). Specifically, this runs ifunc resolvers to pick, based on the CPU features discovered earlier, the most suitable implementation of "string" functions such as memcpy. Before that point, calling memcpy (or other ifunc-resolved functions) will not work. In the Hurd port, things are more complex. In order to get argv/env for our process, glibc normally needs to do an RPC to the exec server, unless our args/env are already located on the stack (which is what happens to bootstrap processes spawned by GNU Mach). Fetching our argv/env from the exec server has to be done before the call to __libc_start_main, since we need to know what our argv/env are to pass them to __libc_start_main. On the other hand, the implementation of the RPC (and other initial setup needed on the Hurd before __libc_start_main can be run) is not very trivial. In particular, it may (and on x86_64, will) use memcpy. But as described above, calling memcpy before __libc_start_main can not work, since the GOT entry for it is not yet initialized at that point. Work around this by pre-filling the GOT entry with the baseline version of memcpy, __memcpy_sse2_unaligned. This makes it possible for early calls to memcpy to just work. The initial value of the GOT entry is unused on x86_64, and changing it won't interfere with the relocation being performed later: once _dl_relocate_static_pie () is called, the baseline version will get replaced with the most suitable one, and that is what subsequent calls of memcpy are going to call. Checked on x86_64-gnu. Signed-off-by: Sergey Bugaev Message-Id: <20230429201822.2605207-6-bugaevc@gmail.com> Diff: --- sysdeps/mach/hurd/x86_64/static-start.S | 3 +++ 1 file changed, 3 insertions(+) diff --git a/sysdeps/mach/hurd/x86_64/static-start.S b/sysdeps/mach/hurd/x86_64/static-start.S index 982d3d52e4..cc8e2410ea 100644 --- a/sysdeps/mach/hurd/x86_64/static-start.S +++ b/sysdeps/mach/hurd/x86_64/static-start.S @@ -19,6 +19,9 @@ .text .globl _start _start: + + leaq __memcpy_sse2_unaligned(%rip), %rax + movq %rax, memcpy@GOTPCREL(%rip) call _hurd_stack_setup xorq %rdx, %rdx jmp _start1