On Thu Sep 1 17:48:34 2022 +0000, Kevin Puetz wrote:
Ok, figured out a few more things. The problem seems to be that libwinecrt0.a was compiled with `-fno-PIC`, and then gets linked into .so files that are being linked with `-fPIC`. The use of `-fno-PIC` for winecrt0 seems very much intentional per 8f732c66ab37b54c30d63c74f7822ba1d4f04996 (and indeed only for i386). https://bugs.winehq.org/show_bug.cgi?id=37540#c19 mentions a "suppress read only relocs workaround", but I'm not sure what it was, unless it's a reference to using `-read_only_relocs suppress`. But probably not, since that seems to have been for darwin-powerpc, and this change was only for x86. In any case, wine itself is being consistent, and linking with `-fno-PIC`: https://gitlab.winehq.org/wine/wine/-/blob/master/configure.ac#L813-814. I see the warning, when wine did not, because my CMake toolchain for winegcc is adding -fPIC to its rules for SHARED and MODULE (.dll.so) files. So that seems to be on me. And apparently I only see the warning in ubuntu, and not wind river, because it's a relatively new warning added in binutils 2.35: https://github.com/bminor/binutils-gdb/commit/a6dbf402de65fe66f4ec99b56527df... So I think this patch is probably fine, and the fix is that I should have updated my CMake toolchain to know that wine >= 4.8 doesn't want builtin dll.so/.exe.so files to use `-fPIC` anymore for x86.
Digging still deeper, winecrt0.a is actually a mixture of `-fPIC` and `-fno-PIC` code:
The PE build (using i686-w64-mingw32-gcc) does not specify either way. If I peek with `objdump -r /usr/local/lib/wine/i386-windows/libwinecrt0.a | sed '/RELOCATION RECORDS FOR [.debug/,/^$/d'`, it and seems to get dir32 (== R_DIR32, Direct 32-bit reference to the symbol's virtual address)and DISP32 (== R_PCRLONG, 32-bit longword PC relative relocation) relocs, so not entirely PIC. Which agrees with https://bugs.winehq.org/show_bug.cgi?id=37540 that default windows/PE practice is no-PIC.
Looking at my build log, crt_fltused.c, crt_dllmain.c, debug.c, dll_main.c, delay_load.c, exception.c, dll_canunload.c, exe16_entry.c, unix_lib.c, setjmp.c, stub.c, dll_register.c, register are all built with `gcc -fno-PIC`. exe_entry.c, exe_main.c, exe_wentry.c, exe_wmain.c are compiled with `gcc -fPIC`, and indeed contain R_386_PLT32 and R_386_GOT32X relocations. Presumably this is a consequence of `#pragma makedep unix`, via [`AC_SUBST(UNIXDLLFLAGS,"-fPIC") `](https://gitlab.winehq.org/wine/wine/-/blob/master/configure.ac#L644).
But a lot of the files built with -fno-PIC just incidentally happen to be PIC-compliant, in that they happen to come out with only R_386_PC32. Before the usage of __dso_handle and __cxa_finalize added by this MR, the only ones that were already non-PIC in a meaningful way were:
``` delay_load.o: file format elf32-i386
RELOCATION RECORDS FOR [.text]: OFFSET TYPE VALUE 00000023 R_386_32 __wine_spec_delay_imports
exception.o: file format elf32-i386
RELOCATION RECORDS FOR [.text]: OFFSET TYPE VALUE 0000002c R_386_32 .text
register.o: file format elf32-i386
RELOCATION RECORDS FOR [.text]: OFFSET TYPE VALUE 00000011 R_386_32 .bss 00000053 R_386_32 .rodata 00000062 R_386_32 .rodata 00000071 R_386_32 .rodata 00000084 R_386_32 .rodata 00000098 R_386_32 .rodata.str1.1 000000a5 R_386_32 .bss 0000023d R_386_32 __wine_spec_nt_header 00000242 R_386_32 .text 0000024c R_386_32 .rodata 000002ad R_386_32 __wine_spec_nt_header 000002b2 R_386_32 .text 000002bc R_386_32 .rodata ```
You wouldn't end up referencing exception.o without using the `_TRY` SEH macros (or having widl code do so), and __wine_register_resources you'd pretty much have to call on purpose. Same for using delayload. So *most* things were still OK (in practice) to be -fPIC.
Seems like I should probably move this into its own atexit.c, marked with `#pragma makedep unix`, and then call that from the 3 entry points that need to (which just happen to be R_386_PC32. That restores the status quo vs `-fPIC`, eliminates having 3 duplicates of it in exe_main/exe_main/crt_dllmain, and eliminate the need to mess with `__attribute__((sysv_abi)` to compenate`-mabi=ms` on amd64. win/win/win.