summaryrefslogtreecommitdiff
path: root/tools/include/nolibc
AgeCommit message (Collapse)AuthorFilesLines
2023-10-12tools/nolibc: add support for constructors and destructorsThomas Weißschuh1-1/+22
With the startup code moved to C, implementing support for constructors and deconstructors is fairly easy to implement. Examples for code size impact: text data bss dec hex filename 21837 104 88 22029 560d nolibc-test.before 22135 120 88 22343 5747 nolibc-test.after 21970 104 88 22162 5692 nolibc-test.after-only-crt.h-changes The sections are defined by [0]. [0] https://refspecs.linuxfoundation.org/elf/gabi4+/ch5.dynamic.html Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Acked-by: Willy Tarreau <w@1wt.eu> Link: https://lore.kernel.org/lkml/20231007-nolibc-constructors-v2-1-ef84693efbc1@weissschuh.net/
2023-10-12tools/nolibc: automatically detect necessity to use pselect6Thomas Weißschuh4-14/+6
We can automatically detect if pselect6 is needed or not from the kernel headers. This removes the need to manually specify it. Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Acked-by: Willy Tarreau <w@1wt.eu> Link: https://lore.kernel.org/r/20230917-nolibc-syscall-nr-v2-4-03863d509b9a@weissschuh.net
2023-10-12tools/nolibc: don't define new syscall numberThomas Weißschuh1-4/+3
All symbols created by nolibc are also visible to user code. Syscall constants are expected to come from the kernel headers and should not be made up by nolibc. Refactor the logic to avoid defining syscall numbers. Also the new code is easier to understand. Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Acked-by: Willy Tarreau <w@1wt.eu> Link: https://lore.kernel.org/r/20230917-nolibc-syscall-nr-v2-3-03863d509b9a@weissschuh.net
2023-10-12tools/nolibc: avoid unused parameter warnings for ENOSYS fallbacksThomas Weißschuh1-17/+27
The ENOSYS fallback code does not use its functions parameters. This can lead to compiler warnings about unused parameters. Explicitly avoid these warnings. Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Acked-by: Willy Tarreau <w@1wt.eu> Link: https://lore.kernel.org/r/20230917-nolibc-syscall-nr-v2-2-03863d509b9a@weissschuh.net
2023-10-12tools/nolibc: string: Remove the `_nolibc_memcpy_up()` functionAmmar Faizi1-13/+7
This function is only called by memcpy(), there is no real reason to have this wrapper. Delete this function and move the code to memcpy() directly. Signed-off-by: Ammar Faizi <ammarfaizi2@gnuweeb.org> Reviewed-by: Alviro Iskandar Setiawan <alviro.iskandar@gnuweeb.org> Signed-off-by: Willy Tarreau <w@1wt.eu> Signed-off-by: Thomas Weißschuh <linux@weissschuh.net>
2023-10-12tools/nolibc: string: Remove the `_nolibc_memcpy_down()` functionAmmar Faizi1-10/+0
This nolibc internal function is not used. Delete it. It was probably supposed to handle memmove(), but today the memmove() has its own implementation. Signed-off-by: Ammar Faizi <ammarfaizi2@gnuweeb.org> Reviewed-by: Alviro Iskandar Setiawan <alviro.iskandar@gnuweeb.org> Signed-off-by: Willy Tarreau <w@1wt.eu> Signed-off-by: Thomas Weißschuh <linux@weissschuh.net>
2023-10-12tools/nolibc: x86-64: Use `rep stosb` for `memset()`Ammar Faizi2-0/+15
Simplify memset() on the x86-64 arch. The x86-64 arch has a 'rep stosb' instruction, which can perform memset() using only a single instruction, given: %al = value (just like the second argument of memset()) %rdi = destination %rcx = length Before this patch: ``` 00000000000010c9 <memset>: 10c9: 48 89 f8 mov %rdi,%rax 10cc: 48 85 d2 test %rdx,%rdx 10cf: 74 0e je 10df <memset+0x16> 10d1: 31 c9 xor %ecx,%ecx 10d3: 40 88 34 08 mov %sil,(%rax,%rcx,1) 10d7: 48 ff c1 inc %rcx 10da: 48 39 ca cmp %rcx,%rdx 10dd: 75 f4 jne 10d3 <memset+0xa> 10df: c3 ret ``` After this patch: ``` 0000000000001511 <memset>: 1511: 96 xchg %eax,%esi 1512: 48 89 d1 mov %rdx,%rcx 1515: 57 push %rdi 1516: f3 aa rep stos %al,%es:(%rdi) 1518: 58 pop %rax 1519: c3 ret ``` v2: - Use pushq %rdi / popq %rax (Alviro). - Use xchg %eax, %esi (Willy). Link: https://lore.kernel.org/lkml/ZO9e6h2jjVIMpBJP@1wt.eu Suggested-by: Alviro Iskandar Setiawan <alviro.iskandar@gnuweeb.org> Suggested-by: Willy Tarreau <w@1wt.eu> Signed-off-by: Ammar Faizi <ammarfaizi2@gnuweeb.org> Reviewed-by: Alviro Iskandar Setiawan <alviro.iskandar@gnuweeb.org> Signed-off-by: Willy Tarreau <w@1wt.eu> Signed-off-by: Thomas Weißschuh <linux@weissschuh.net>
2023-10-12tools/nolibc: x86-64: Use `rep movsb` for `memcpy()` and `memmove()`Ammar Faizi2-0/+33
Simplify memcpy() and memmove() on the x86-64 arch. The x86-64 arch has a 'rep movsb' instruction, which can perform memcpy() using only a single instruction, given: %rdi = destination %rsi = source %rcx = length Additionally, it can also handle the overlapping case by setting DF=1 (backward copy), which can be used as the memmove() implementation. Before this patch: ``` 00000000000010ab <memmove>: 10ab: 48 89 f8 mov %rdi,%rax 10ae: 31 c9 xor %ecx,%ecx 10b0: 48 39 f7 cmp %rsi,%rdi 10b3: 48 83 d1 ff adc $0xffffffffffffffff,%rcx 10b7: 48 85 d2 test %rdx,%rdx 10ba: 74 25 je 10e1 <memmove+0x36> 10bc: 48 83 c9 01 or $0x1,%rcx 10c0: 48 39 f0 cmp %rsi,%rax 10c3: 48 c7 c7 ff ff ff ff mov $0xffffffffffffffff,%rdi 10ca: 48 0f 43 fa cmovae %rdx,%rdi 10ce: 48 01 cf add %rcx,%rdi 10d1: 44 8a 04 3e mov (%rsi,%rdi,1),%r8b 10d5: 44 88 04 38 mov %r8b,(%rax,%rdi,1) 10d9: 48 01 cf add %rcx,%rdi 10dc: 48 ff ca dec %rdx 10df: 75 f0 jne 10d1 <memmove+0x26> 10e1: c3 ret 00000000000010e2 <memcpy>: 10e2: 48 89 f8 mov %rdi,%rax 10e5: 48 85 d2 test %rdx,%rdx 10e8: 74 12 je 10fc <memcpy+0x1a> 10ea: 31 c9 xor %ecx,%ecx 10ec: 40 8a 3c 0e mov (%rsi,%rcx,1),%dil 10f0: 40 88 3c 08 mov %dil,(%rax,%rcx,1) 10f4: 48 ff c1 inc %rcx 10f7: 48 39 ca cmp %rcx,%rdx 10fa: 75 f0 jne 10ec <memcpy+0xa> 10fc: c3 ret ``` After this patch: ``` // memmove is an alias for memcpy 000000000040133b <memcpy>: 40133b: 48 89 d1 mov %rdx,%rcx 40133e: 48 89 f8 mov %rdi,%rax 401341: 48 89 fa mov %rdi,%rdx 401344: 48 29 f2 sub %rsi,%rdx 401347: 48 39 ca cmp %rcx,%rdx 40134a: 72 03 jb 40134f <memcpy+0x14> 40134c: f3 a4 rep movsb %ds:(%rsi),%es:(%rdi) 40134e: c3 ret 40134f: 48 8d 7c 0f ff lea -0x1(%rdi,%rcx,1),%rdi 401354: 48 8d 74 0e ff lea -0x1(%rsi,%rcx,1),%rsi 401359: fd std 40135a: f3 a4 rep movsb %ds:(%rsi),%es:(%rdi) 40135c: fc cld 40135d: c3 ret ``` v3: - Make memmove as an alias for memcpy (Willy). - Make the forward copy the likely case (Alviro). v2: - Fix the broken memmove implementation (David). Link: https://lore.kernel.org/lkml/20230902062237.GA23141@1wt.eu Link: https://lore.kernel.org/lkml/5a821292d96a4dbc84c96ccdc6b5b666@AcuMS.aculab.com Suggested-by: David Laight <David.Laight@aculab.com> Signed-off-by: Ammar Faizi <ammarfaizi2@gnuweeb.org> Signed-off-by: Willy Tarreau <w@1wt.eu> Signed-off-by: Thomas Weißschuh <linux@weissschuh.net>
2023-10-12tools/nolibc: add stdarg.h headerThomas Weißschuh5-5/+21
This allows nolic to work with `-nostdinc` avoiding any reliance on system headers. The implementation has been lifted from musl libc 1.2.4. There is already an implementation of stdarg.h in include/linux/stdarg.h but that is GPL licensed and therefore not suitable for nolibc. The used compiler builtins have been validated to be at least available since GCC 4.1.2 and clang 3.0.0. Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-10-12tools/nolibc: mark start_c as weakThomas Weißschuh1-0/+1
Otherwise the different instances of _start_c from each compilation unit will lead to linker errors: /usr/bin/ld: /tmp/ccSNvRqs.o: in function `_start_c': nolibc-test-foo.c:(.text.nolibc_memset+0x9): multiple definition of `_start_c'; /tmp/ccG25101.o:nolibc-test.c:(.text+0x1ea3): first defined here Fixes: 17336755150b ("tools/nolibc: add new crt.h with _start_c") Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Link: https://lore.kernel.org/lkml/20231012-nolibc-start_c-multiple-v1-1-fbfc73e0283f@weissschuh.net/ Link: https://lore.kernel.org/lkml/20231012-nolibc-linkage-test-v1-1-315e682768b4@weissschuh.net/ Acked-by: Willy Tarreau <w@1wt.eu>
2023-10-12tools/nolibc: i386: Fix a stack misalign bug on _startAmmar Faizi1-1/+3
The ABI mandates that the %esp register must be a multiple of 16 when executing a 'call' instruction. Commit 2ab446336b17 ("tools/nolibc: i386: shrink _start with _start_c") simplified the _start function, but it didn't take care of the %esp alignment, causing SIGSEGV on SSE and AVX programs that use aligned move instruction (e.g., movdqa, movaps, and vmovdqa). The 'and $-16, %esp' aligns the %esp at a multiple of 16. Then 'push %eax' will subtract the %esp by 4; thus, it breaks the 16-byte alignment. Make sure the %esp is correctly aligned after the push by subtracting 12 before the push. Extra: Add 'add $12, %esp' before the 'and $-16, %esp' to avoid over-estimating for particular cases as suggested by Willy. A test program to validate the %esp alignment on _start can be found at: https://lore.kernel.org/lkml/ZOoindMFj1UKqo+s@biznet-home.integral.gnuweeb.org [ Thomas: trim Fixes tag commit id ] Cc: Zhangjin Wu <falcon@tinylab.org> Fixes: 2ab446336b17 ("tools/nolibc: i386: shrink _start with _start_c") Reported-by: Nicholas Rosenberg <inori@vnlx.org> Acked-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Ammar Faizi <ammarfaizi2@gnuweeb.org> Reviewed-by: Alviro Iskandar Setiawan <alviro.iskandar@gnuweeb.org> Signed-off-by: Willy Tarreau <w@1wt.eu> Signed-off-by: Thomas Weißschuh <linux@weissschuh.net>
2023-08-23tools/nolibc: avoid undesired casts in the __sysret() macroWilly Tarreau1-14/+13
Having __sysret() as an inline function has the unfortunate effect of adding casts and large constants comparisons after the syscall returns that significantly inflate some light code that's otherwise syscall- heavy. Even nolibc-test grew by ~1%. Let's switch back to a macro for this, and use it only with signed arguments. Note that it is also possible to design a slightly more complex macro covering unsigned and pointers but we only have 3 such syscalls so it is pointless, and these were just addressed not to use this macro anymore. Now for the argument (the local variable containing the syscall return value), any negative value is an error, that results in -1 being returned and errno to be assigned the opposite value. This may be revisited again in the future if really needed but for now let's get back to something sane. Fixes: 428905da6ec4 ("tools/nolibc: sys.h: add a syscall return helper") Link: https://lore.kernel.org/lkml/20230806095846.GB10627@1wt.eu/ Link: https://lore.kernel.org/lkml/ZNKOJY+g66nkIyvv@1wt.eu/ Cc: Zhangjin Wu <falcon@tinylab.org> Cc: David Laight <David.Laight@ACULAB.COM> Cc: Thomas Weißschuh <thomas@t-8ch.de> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: keep brk(), sbrk(), mmap() away from __sysret()Willy Tarreau1-3/+16
The __sysret() function causes some undesirable casts so we'll revert it. In order to keep it simple it will now only support integer return values like in the past, so we must basically revert the changes that were made to these 3 syscalls which return a pointer so that they simply rely on their own test and the SET_ERRNO() macro. Fixes: 4201cfce15fe ("tools/nolibc: clean up sbrk() routine") Fixes: 924e9539aeaa ("tools/nolibc: clean up mmap() routine") Fixes: d27447bc2e0a ("tools/nolibc: sys.h: apply __sysret() helper") Link: https://lore.kernel.org/lkml/20230806095846.GB10627@1wt.eu/ Link: https://lore.kernel.org/lkml/ZNKOJY+g66nkIyvv@1wt.eu/ Cc: Zhangjin Wu <falcon@tinylab.org> Cc: David Laight <David.Laight@ACULAB.COM> Cc: Thomas Weißschuh <thomas@t-8ch.de> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: silence ppc64 compile warningsZhangjin Wu1-3/+11
Silence the following warnings reported by the new -Wall -Wextra options with pure assembly code. In file included from sysroot/powerpc/include/stdio.h:13, from nolibc-test.c:13: sysroot/powerpc/include/arch.h: In function '_start': sysroot/powerpc/include/arch.h:192:32: warning: unused variable 'r2' [-Wunused-variable] 192 | register volatile long r2 __asm__ ("r2") = (void *)&TOC - (void *)_start; | ^~ sysroot/powerpc/include/arch.h:187:97: warning: optimization may eliminate reads and/or writes to register variables [-Wvolatile-register-var] 187 | void __attribute__((weak, noreturn, optimize("Os", "omit-frame-pointer"))) __no_stack_protector _start(void) | ^~~~~~ Since only elfv2 ABI requires to save the TOC/GOT pointer to r2 register, when using elfv1 ABI, the old C code is simply ignored by the compiler, but the compiler can not ignore the inline assembly code and will introduce build failure or running segfaults. So, let's further only add the new assembly code for elfv2 ABI with the checking of _CALL_ELF == 2. Link: https://refspecs.linuxfoundation.org/ELF/ppc64/PPC-elf64abi.pdf Link: https://www.llvm.org/devmtg/2014-04/PDFs/Talks/Euro-LLVM-2014-Weigand.pdf Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: stackprotector.h: make __stack_chk_init staticZhangjin Wu2-4/+3
This allows to generate smaller text/data/dec size. As the _start_c() function added by crt.h, __stack_chk_init() is called from _start_c() instead of the assembly _start. So, it is able to mark it with static now. Reviewed-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: add support for powerpc64Zhangjin Wu1-0/+16
This follows the 64-bit PowerPC ABI [1], refers to the slides: "A new ABI for little-endian PowerPC64 Design & Implementation" [2] and the musl code in arch/powerpc64/crt_arch.h. First, stdu and clrrdi are used instead of stwu and clrrwi for powerpc64. Second, the stack frame size is increased to 32 bytes for powerpc64, 32 bytes is the minimal stack frame size supported described in [2]. Besides, the TOC pointer (GOT pointer) must be saved to r2. This works on both little endian and big endian 64-bit PowerPC. [1]: https://refspecs.linuxfoundation.org/ELF/ppc64/PPC-elf64abi.pdf [2]: https://www.llvm.org/devmtg/2014-04/PDFs/Talks/Euro-LLVM-2014-Weigand.pdf Reviewed-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: add support for powerpcZhangjin Wu2-0/+199
Both syscall declarations and _start code definition are added for powerpc to nolibc. Like mips, powerpc uses a register (exactly, the summary overflow bit) to record the error occurred, and uses another register to return the value [1]. So, the return value of every syscall declaration must be normalized to match the __sysret() helper, return -value when there is an error, otheriwse, return value directly. Glibc and musl use different methods to check the summary overflow bit, glibc (sysdeps/unix/sysv/linux/powerpc/sysdep.h) saves the cr register to r0 at first, and then check the summary overflow bit in cr0: mfcr r0 r0 & (1 << 28) ? -r3 : r3 --> 10003c14: 7c 00 00 26 mfcr r0 10003c18: 74 09 10 00 andis. r9,r0,4096 10003c1c: 41 82 00 08 beq 0x10003c24 10003c20: 7c 63 00 d0 neg r3,r3 Musl (arch/powerpc/syscall_arch.h) directly checks the summary overflow bit with the 'bns' instruction, it is smaller: /* no summary overflow bit means no error, return value directly */ bns+ 1f /* otherwise, return negated value */ neg r3, r3 1: --> 10000418: 40 a3 00 08 bns 0x10000420 1000041c: 7c 63 00 d0 neg r3,r3 Like musl, Linux (arch/powerpc/include/asm/vdso/gettimeofday.h) uses the same method for do_syscall_2() too. Here applies the second method to get smaller size. [1]: https://man7.org/linux/man-pages/man2/syscall.2.html Reviewed-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: stdint: use __SIZE_TYPE__ for size_tThomas Weißschuh1-1/+1
Otherwise both gcc and clang may generate warnings about type mismatches: sysroot/mips/include/string.h:12:14: warning: mismatch in argument 1 type of built-in function 'malloc'; expected 'unsigned int' [-Wbuiltin-declaration-mismatch] 12 | static void *malloc(size_t len); | ^~~~~~ The compiler provides __SIZE_TYPE__ as the type that corresponds to size_t (typically "long unsigned int" or "unsigned int"). It was verified to be available at least since gcc-3.4 and clang-3.8, so from now on we'll use this definition for size_t. Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Link: https://lore.kernel.org/lkml/20230805161929.GA15284@1wt.eu/ Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: sys: avoid implicit sign castThomas Weißschuh1-1/+1
getauxval() returns an unsigned long but the overall type of the ternary operator needs to be signed. Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: setvbuf: avoid unused parameter warningsThomas Weißschuh1-1/+4
This warning will be enabled later so avoid triggering it. Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: fix return type of getpagesize()Thomas Weißschuh1-2/+2
It's documented as returning int which is also implemented by glibc and musl, so adopt that return type. Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: drop unused variablesThomas Weißschuh1-1/+0
Nobody needs it, get rid of it. Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: add pipe() and pipe2() supportYuan Tan1-0/+24
According to manual page [1], posix spec [2] and source code like arch/mips/kernel/syscall.c, for historic reasons, the sys_pipe() syscall on some architectures has an unusual calling convention. It returns results in two registers which means there is no need for it to do verify the validity of a userspace pointer argument. Historically that used to be expensive in Linux. These days the performance advantage is negligible. Nolibc doesn't support the unusual calling convention above, luckily Linux provides a generic sys_pipe2() with an additional flags argument from 2.6.27. If flags is 0, then pipe2() is the same as pipe(). So here we use sys_pipe2() to implement the pipe(). pipe2() is also provided to allow users to use flags argument on demand. [1]: https://man7.org/linux/man-pages/man2/pipe.2.html [2]: https://pubs.opengroup.org/onlinepubs/9699919799/functions/pipe.html Suggested-by: Zhangjin Wu <falcon@tinylab.org> Link: https://lore.kernel.org/all/20230729100401.GA4577@1wt.eu/ Signed-off-by: Yuan Tan <tanyuan@tinylab.org> Reviewed-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc/stdio: add setvbuf() to set buffering modeRyan Roberts1-0/+24
Add a minimal implementation of setvbuf(), which error checks the mode argument (as required by spec) and returns. Since nolibc never buffers output, nothing needs to be done. The kselftest framework recently added a call to setvbuf(). As a result, any tests that use the kselftest framework and nolibc cause a compiler error due to missing function. This provides an urgent fix for the problem which is preventing arm64 testing on linux-next. Example: clang --target=aarch64-linux-gnu -fintegrated-as -Werror=unknown-warning-option -Werror=ignored-optimization-argument -Werror=option-ignored -Werror=unused-command-line-argument --target=aarch64-linux-gnu -fintegrated-as -fno-asynchronous-unwind-tables -fno-ident -s -Os -nostdlib \ -include ../../../../include/nolibc/nolibc.h -I../..\ -static -ffreestanding -Wall za-fork.c build/kselftest/arm64/fp/za-fork-asm.o -o build/kselftest/arm64/fp/za-fork In file included from <built-in>:1: In file included from ./../../../../include/nolibc/nolibc.h:97: In file included from ./../../../../include/nolibc/arch.h:25: ./../../../../include/nolibc/arch-aarch64.h:178:35: warning: unknown attribute 'optimize' ignored [-Wunknown-attributes] void __attribute__((weak,noreturn,optimize("omit-frame-pointer"))) __no_stack_protector _start(void) ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ In file included from za-fork.c:12: ../../kselftest.h:123:2: error: call to undeclared function 'setvbuf'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration] setvbuf(stdout, NULL, _IOLBF, 0); ^ ../../kselftest.h:123:24: error: use of undeclared identifier '_IOLBF' setvbuf(stdout, NULL, _IOLBF, 0); ^ 1 warning and 2 errors generated. Signed-off-by: Ryan Roberts <ryan.roberts@arm.com> Reported-by: Linux Kernel Functional Testing <lkft@linaro.org> Link: https://lore.kernel.org/linux-kselftest/CA+G9fYus3Z8r2cg3zLv8uH8MRrzLFVWdnor02SNr=rCz+_WGVg@mail.gmail.com/ Reviewed-by: Mark Brown <broonie@kernel.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: s390: shrink _start with _start_cZhangjin Wu1-31/+5
move most of the _start operations to _start_c(), include the stackprotector initialization. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: riscv: shrink _start with _start_cZhangjin Wu1-39/+5
move most of the _start operations to _start_c(), include the stackprotector initialization. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: loongarch: shrink _start with _start_cZhangjin Wu1-40/+4
move most of the _start operations to _start_c(), include the stackprotector initialization. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: mips: shrink _start with _start_cZhangjin Wu1-38/+8
move most of the _start operations to _start_c(), include the stackprotector initialization. Also clean up the instructions in delayed slots. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: x86_64: shrink _start with _start_cZhangjin Wu1-23/+6
move most of the _start operations to _start_c(), include the stackprotector initialization. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: i386: shrink _start with _start_cZhangjin Wu1-27/+7
move most of the _start operations to _start_c(), include the stackprotector initialization. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: aarch64: shrink _start with _start_cZhangjin Wu1-23/+4
move most of the _start operations to _start_c(), include the stackprotector initialization. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: arm: shrink _start with _start_cZhangjin Wu1-39/+5
move most of the _start operations to _start_c(), include the stackprotector initialization. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: crt.h: initialize stack protectorZhangjin Wu1-0/+4
As suggested by Thomas, It is able to move the stackprotector initialization from the assembly _start to the beginning of the new _start_c(). Let's call __stack_chk_init() in _start_c() as a preparation. Suggested-by: Thomas Weißschuh <linux@weissschuh.net> Link: https://lore.kernel.org/lkml/a00284a6-54b1-498c-92aa-44997fa78403@t-8ch.de/ Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: stackprotector.h: add empty __stack_chk_init for ↵Zhangjin Wu1-0/+2
!_NOLIBC_STACKPROTECTOR Let's define an empty __stack_chk_init for the !_NOLIBC_STACKPROTECTOR branch. This allows to remove #ifdef around every call of __stack_chk_init(). Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: add new crt.h with _start_cZhangjin Wu2-0/+58
As the environ and _auxv support added for nolibc, the assembly _start function becomes more and more complex and therefore makes the porting of nolibc to new architectures harder and harder. To simplify portability, this C version of _start_c() is added to do most of the assembly start operations in C, which reduces the complexity a lot and will eventually simplify the porting of nolibc to the new architectures. The new _start_c() only requires a stack pointer argument, it will find argc, argv, envp/environ and _auxv for us, and then call main(), finally, it exit() with main's return status. With this new _start_c(), the future new architectures only require to add very few assembly instructions. As suggested by Thomas, users may use a different signature of main (e.g. void main(void)), a _nolibc_main alias is added for main to silence the warning about potential conflicting types. As suggested by Willy, the code is carefully polished for both smaller size and better readability with local variables and the right types. Suggested-by: Willy Tarreau <w@1wt.eu> Link: https://lore.kernel.org/lkml/20230715095729.GC24086@1wt.eu/ Suggested-by: Thomas Weißschuh <linux@weissschuh.net> Link: https://lore.kernel.org/lkml/90fdd255-32f4-4caf-90ff-06456b53dac3@t-8ch.de/ Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: remove the old sys_stat supportZhangjin Wu9-248/+13
The statx manpage [1] shows that it has been supported from Linux 4.11 and glibc 2.28, the Linux support can be checked for all of the architectures with this command: $ git grep -r statx v4.11 arch/ include/uapi/asm-generic/unistd.h \ | grep -E "aarch64|arm|mips|s390|x86|:include/uapi" Besides riscv and loongarch, all of the nolibc supported architectures have added sys_statx from Linux v4.11. riscv is mainlined to v4.15, loongarch is mainlined to v5.19, both of them use the generic unistd.h, so, they have added sys_statx from their first mainline versions. The current oldest stable branch is v4.14, only reserving sys_statx still preserves compatibility with all of the supported stable branches, So, let's remove the old arch related and dependent sys_stat support completely. This is friendly to the future new architecture porting. [1]: https://man7.org/linux/man-pages/man2/statx.2.html Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: fix up startup failures for -O0 under gcc < 11.1.0Zhangjin Wu8-8/+8
As gcc doc [1] shows: Most optimizations are completely disabled at -O0 or if an -O level is not set on the command line, even if individual optimization flags are specified. Test result [2] shows, gcc>=11.1.0 deviates from the above description, but before gcc 11.1.0, "-O0" still forcely uses frame pointer in the _start function even if the individual optimize("omit-frame-pointer") flag is specified. The frame pointer related operations will change the stack pointer (e.g. In x86_64, an extra "push %rbp" will be inserted at the beginning of _start) and make it differs from the one we expected, as a result, break the whole startup function. To fix up this issue, as suggested by Thomas, the individual "Os" and "omit-frame-pointer" optimize flags are used together on _start function to disable frame pointer completely even if the -O0 is set on the command line. [1]: https://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html [2]: https://lore.kernel.org/lkml/20230714094723.140603-1-falcon@tinylab.org/ Suggested-by: Thomas Weißschuh <linux@weissschuh.net> Link: https://lore.kernel.org/lkml/34b21ba5-7b59-4b3b-9ed6-ef9a3a5e06f7@t-8ch.de/ Fixes: 7f8548589661 ("tools/nolibc: make compiler and assembler agree on the section around _start") Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: arch-*.h: add missing space after ','Zhangjin Wu8-8/+8
Fix up such errors reported by scripts/checkpatch.pl: ERROR: space required after that ',' (ctx:VxV) #148: FILE: tools/include/nolibc/arch-aarch64.h:148: +void __attribute__((weak,noreturn,optimize("omit-frame-pointer"))) __no_stack_protector _start(void) ^ ERROR: space required after that ',' (ctx:VxV) #148: FILE: tools/include/nolibc/arch-aarch64.h:148: +void __attribute__((weak,noreturn,optimize("omit-frame-pointer"))) __no_stack_protector _start(void) ^ Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: completely remove optional environ supportThomas Weißschuh1-10/+2
In commit 52e423f5b93e ("tools/nolibc: export environ as a weak symbol on i386") and friends the asm startup logic was extended to directly populate the "environ" array. This makes it impossible for "environ" to be dropped by the linker. Therefore also drop the other logic to handle non-present "environ". Also add a testcase to validate the initialization of environ. Signed-off-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: add rmdir() supportZhangjin Wu1-0/+22
a reverse operation of mkdir() is meaningful, add rmdir() here. required by nolibc-test to remove /proc while CONFIG_PROC_FS is not enabled. Reviewed-by: Thomas Weißschuh <linux@weissschuh.net> Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: types.h: add RB_ flags for reboot()Zhangjin Wu2-2/+11
Both glibc and musl provide RB_ flags via <sys/reboot.h> for reboot(), they don't need to include <linux/reboot.h>, let nolibc provide RB_ flags too. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: clean up sbrk() routineZhangjin Wu1-5/+4
Fix up the error reported by scripts/checkpatch.pl: ERROR: do not use assignment in if condition #95: FILE: tools/include/nolibc/sys.h:95: + if ((ret = sys_brk(0)) && (sys_brk(ret + inc) == ret + inc)) Apply the new generic __sysret() to merge the SET_ERRNO() and return lines. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: clean up mmap() routineZhangjin Wu2-23/+12
Do several cleanups together: - Since all supported architectures have my_syscall6() now, remove the #ifdef check. - Move the mmap() related macros to tools/include/nolibc/types.h and reuse most of them from <linux/mman.h> - Apply the new generic __sysret() to convert the calling of sys_map() to oneline code Note, since MAP_FAILED is -1 on Linux, so we can use the generic __sysret() which returns -1 upon error and still satisfy user land that checks for MAP_FAILED. Suggested-by: Willy Tarreau <w@1wt.eu> Link: https://lore.kernel.org/lkml/20230702192347.GJ16233@1wt.eu/ Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: __sysret: support syscalls who return a pointerZhangjin Wu1-5/+12
No official reference states the errno range, here aligns with musl and glibc and uses [-MAX_ERRNO, -1] instead of all negative ones. - musl: src/internal/syscall_ret.c - glibc: sysdeps/unix/sysv/linux/sysdep.h The MAX_ERRNO used by musl and glibc is 4095, just like the one nolibc defined in tools/include/nolibc/errno.h. Suggested-by: Willy Tarreau <w@1wt.eu> Link: https://lore.kernel.org/lkml/ZKKdD%2Fp4UkEavru6@1wt.eu/ Suggested-by: David Laight <David.Laight@ACULAB.COM> Link: https://lore.kernel.org/linux-riscv/94dd5170929f454fbc0a10a2eb3b108d@AcuMS.aculab.com/ Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: add missing my_syscall6() for mipsZhangjin Wu2-6/+30
It is able to pass the 6th argument like the 5th argument via the stack for mips, let's add a new my_syscall6() now, see [1] for details: The mips/o32 system call convention passes arguments 5 through 8 on the user stack. Both mmap() and pselect6() require my_syscall6(). [1]: https://man7.org/linux/man-pages/man2/syscall.2.html Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: arch-mips.h: shrink with _NOLIBC_SYSCALL_CLOBBERLISTZhangjin Wu1-12/+10
my_syscall<N> share the same long clobber list, define a macro for them. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: arch-loongarch.h: shrink with _NOLIBC_SYSCALL_CLOBBERLISTZhangjin Wu1-14/+9
my_syscall<N> share the same long clobber list, define a macro for them. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23toolc/nolibc: arch-*.h: clean up whitespaces after __asm__Zhangjin Wu8-54/+54
replace "__asm__ volatile" with "__asm__ volatile" and insert necessary whitespace before "\" to make sure the lines are aligned. $ sed -i -e 's/__asm__ volatile ( /__asm__ volatile ( /g' tools/include/nolibc/*.h Note, arch-s390.h uses post-tab instead of post-whitespaces, must avoid insert whitespace just before the tabs: $ sed -i -e 's/__asm__ volatile (\t/__asm__ volatile (\t/g' tools/include/nolibc/arch-*.h Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-23tools/nolibc: arch-*.h: fix up code indent errorsZhangjin Wu5-39/+39
More than 8 whitespaces of the code indent are replaced with "tab + whitespaces" to fix up such errors reported by scripts/checkpatch.pl: ERROR: code indent should use tabs where possible #64: FILE: tools/include/nolibc/arch-mips.h:64: +^I \$ ERROR: code indent should use tabs where possible #72: FILE: tools/include/nolibc/arch-mips.h:72: +^I "t0", "t1", "t2", "t3", "t4", "t5", "t6", "t7", "t8", "t9" \$ This command is used: $ sed -i -e '/^\t* /{s/ /\t/g}' tools/include/nolibc/arch-*.h Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>
2023-08-06tools/nolibc: unistd.h: reorder the syscall macrosZhangjin Wu1-2/+2
Tune the macros in the using order and align most of them. Signed-off-by: Zhangjin Wu <falcon@tinylab.org> Signed-off-by: Willy Tarreau <w@1wt.eu>