casaroli commented on code in PR #20723: URL: https://github.com/apache/nuttx/pull/20723#discussion_r4329267228
########## libs/libc/libc.h: ########## @@ -332,12 +332,15 @@ ssize_t lib_parse_hostfile(FAR FILE *stream, FAR struct hostent *host, int lib_restoredir(void); #endif -/* Defined in tls/tls_emutls.c. exit() and pthread_exit() call - * tls_emutls_destruct() through g_tls_emutls_destruct (tls/tls_getinfo.c). +/* Defined in tls/tls_emutls.c. exit(), pthread_exit() and the loader call + * them through these pointers (tls/tls_getinfo.c). */ extern CODE void (*g_tls_emutls_destruct)(void); +extern CODE void (*g_tls_emutls_release)(FAR const void *start, Review Comment: I tried it on `qemu-armv8a:knsh`, with `void tls_emutls_destruct(void) weak_function;` and `if (tls_emutls_destruct != NULL) tls_emutls_destruct();` (the same for `lib_emutls_release()`). The null check does not change the call: gcc still calls the function directly and only adds a load of its address. gcc 14 for aarch64 (`-O2` and `-Os`) makes `adrp`/`ldr` with `R_AARCH64_ADR_GOT_PAGE`/`R_AARCH64_LD64_GOT_LO12_NC`, `cbz`, then `bl` with `R_AARCH64_CALL26`. arm-none-eabi 13 and 15 make `bl` with `R_ARM_THM_CALL` or `R_ARM_CALL`, and riscv gcc 14 makes `R_RISCV_CALL_PLT`. Only with `-mlong-calls` does the call go through a register. In a final link (flat and protected images, and kernel programs linked as executables, such as `rv-virt:knsh`) ld changes the `bl` to an undefined weak function into a `nop`, so there it works. But a program of `qemu-armv8a:knsh` is a relocatable object (`ld -r`) and keeps these relocations: `/system/bin/init` has 3 `R_AARCH64_CALL26` and 6 GOT relocations against `tls_emutls_destruct` (from `exit()`, `quick_exit()` and `pthread_exit()`). The loader on master does not know the GOT relocations. With #20789 it does, but the `bl` to address 0 is out of range: `up_relocateadd: ERROR: overflow in relocation type 283 val 0`, `exec_internal: ERROR: Failed to load program '/system/bin/init': -8`. So this needs a loader change in each arch that loads relocatable programs (a branch to an undefined weak symbol becomes a `nop`, as ld does), and #20789 on arm64. With the pointer, the call goes through a register and the loader needs nothing, so I prefer to keep the pointers. -- This is an automated message from the Apache Git Service. To respond to the message, please log on to GitHub and use the URL above to go to the specific comment. To unsubscribe, e-mail: [email protected] For queries about this service, please contact Infrastructure at: [email protected]
