From 69e6fe89fa9baafeca3e3515bb50897cd8ee7c35 Mon Sep 17 00:00:00 2001 From: Kacper Date: Mon, 15 Dec 2025 18:24:54 +0100 Subject: Add getauxval and cleanup libc startup --- lib/libc/arch/x86_64/Kbuild | 4 +-- lib/libc/arch/x86_64/_start.c | 8 +++++ lib/libc/arch/x86_64/clock_gettime.c | 15 --------- lib/libc/arch/x86_64/crt0.c | 63 ----------------------------------- lib/libc/arch/x86_64/vdso_setup.c | 64 ------------------------------------ 5 files changed, 9 insertions(+), 145 deletions(-) create mode 100644 lib/libc/arch/x86_64/_start.c delete mode 100644 lib/libc/arch/x86_64/clock_gettime.c delete mode 100644 lib/libc/arch/x86_64/crt0.c delete mode 100644 lib/libc/arch/x86_64/vdso_setup.c (limited to 'lib/libc/arch') diff --git a/lib/libc/arch/x86_64/Kbuild b/lib/libc/arch/x86_64/Kbuild index fc8a2d3f..830a1c5b 100644 --- a/lib/libc/arch/x86_64/Kbuild +++ b/lib/libc/arch/x86_64/Kbuild @@ -1,7 +1,5 @@ -obj-y += clock_gettime.o -obj-y += crt0.o +obj-y += _start.o obj-y += fenv.o obj-y += longjmp.o obj-y += setjmp.o obj-y += sigsetjmp.o -obj-y += vdso_setup.o diff --git a/lib/libc/arch/x86_64/_start.c b/lib/libc/arch/x86_64/_start.c new file mode 100644 index 00000000..52b5c774 --- /dev/null +++ b/lib/libc/arch/x86_64/_start.c @@ -0,0 +1,8 @@ +#include +#include + +__dead __naked void _start(void) +{ + __asm__ __volatile__("mov %rsp, %rdi\n" + "call __libc_main\n"); +} diff --git a/lib/libc/arch/x86_64/clock_gettime.c b/lib/libc/arch/x86_64/clock_gettime.c deleted file mode 100644 index c05926fa..00000000 --- a/lib/libc/arch/x86_64/clock_gettime.c +++ /dev/null @@ -1,15 +0,0 @@ -#include "asm/unistd_64.h" // for __NR_clock_gettime - -#include // for __vdso_clock_gettime -#include // for __syscall_2, syscall -#include // for clock_gettime, clockid_t - -int clock_gettime(clockid_t clock_id, struct timespec *tp) -{ -#if defined(__x86_64__) - if (__vdso_clock_gettime) - return __vdso_clock_gettime(clock_id, tp); -#endif - - return syscall(clock_gettime, clock_id, tp); -} diff --git a/lib/libc/arch/x86_64/crt0.c b/lib/libc/arch/x86_64/crt0.c deleted file mode 100644 index c60239d3..00000000 --- a/lib/libc/arch/x86_64/crt0.c +++ /dev/null @@ -1,63 +0,0 @@ -#include "asm/auxvec.h" // for AT_SYSINFO_EHDR -#include -#include // for AT_NULL -#include // for Elf64_Ehdr -#include // for uintptr_t -#include // for exit - -#define weak_reference(old, new) \ - extern __typeof(old) new __attribute__((__weak__, __alias__(#old))) - -extern int main(int, char *[]); -char **environ; -char *__progname; - -struct __attribute__((packed)) auxv_t { - uintptr_t a_type; - uintptr_t a_val; -} *__auxv; - -static void __vdso_setup(Elf64_Ehdr *vdso_addr __attribute__((unused))) -{ -} - -weak_reference(__vdso_setup, vdso_setup); - -static void __io_uring_setup_(void) -{ -} -weak_reference(__io_uring_setup_, __io_uring_setup); - -__attribute__((used)) void __libc_start(uintptr_t *sp) -{ - char **argv; - int argc; - - argc = (int)(*sp); - argv = (char **)(++sp); - __progname = argv[0]; - sp += argc; - environ = (char **)(++sp); - - while (*sp) - sp++; - - __auxv = (struct auxv_t *)(++sp); - while (__auxv->a_type != AT_NULL) { - if (__auxv->a_type == AT_SYSINFO_EHDR) { - vdso_setup((Elf64_Ehdr *)__auxv->a_val); - } - - __auxv++; - } - - __io_uring_setup_(); - - exit(main(argc, argv)); -} - -__attribute__((noreturn, naked)) void _start(void) -{ - __asm__ __volatile__("mov %rsp, %rdi\n" - "call __libc_start\n"); -} diff --git a/lib/libc/arch/x86_64/vdso_setup.c b/lib/libc/arch/x86_64/vdso_setup.c deleted file mode 100644 index 059aa44a..00000000 --- a/lib/libc/arch/x86_64/vdso_setup.c +++ /dev/null @@ -1,64 +0,0 @@ -#include // for Elf64_Sym, (anonymous struct)::(anonymous) -#include "stddef.h" // for NULL - -#include // for strcmp - -struct timespec; - -int (*__vdso_clock_gettime)(int, struct timespec *) = NULL; -int (*__vdso_getcpu)(unsigned *, unsigned *, void *) = NULL; -int (*__vdso_time)(long *) = NULL; - -static __inline __attribute__((used)) void vdso_setup(Elf64_Ehdr *vdso_addr) -{ - Elf64_Phdr *phdr = - (Elf64_Phdr *)((char *)vdso_addr + vdso_addr->e_phoff); - - for (int i = 0; i < vdso_addr->e_phnum; i++) { - if (phdr[i].p_type == PT_DYNAMIC) { - Elf64_Dyn *dyn = (Elf64_Dyn *)((char *)vdso_addr + - phdr[i].p_offset); - const char *strtab = NULL; - Elf64_Sym *symtab = NULL; - for (; dyn->d_tag != DT_NULL; dyn++) { - if (dyn->d_tag == DT_STRTAB) { - strtab = (const char *)vdso_addr + - dyn->d_un.d_ptr; - } else if (dyn->d_tag == DT_SYMTAB) { - symtab = - (Elf64_Sym *)((char *)vdso_addr + - dyn->d_un.d_ptr); - } - } - - if (strtab == NULL || symtab == NULL) { - return; - } - - Elf64_Sym *sym = symtab; - while ((char *)sym < (char *)strtab) { - if (sym->st_name != 0 && sym->st_value != 0) { - const char *name = - strtab + sym->st_name; - if (strcmp(name, - "__vdso_clock_gettime") == 0) - __vdso_clock_gettime = - (void *)(vdso_addr + - sym->st_value); - else if (strcmp(name, - "__vdso_getcpu") == 0) - __vdso_getcpu = - (void *)(vdso_addr + - sym->st_value); - else if (strcmp(name, "__vdso_time") == - 0) - __vdso_time = - (void *)(vdso_addr + - sym->st_value); - } - sym = (Elf64_Sym *)((char *)sym + - sizeof(Elf64_Sym)); - } - } - } -} -- cgit v1.2.3