I’m trying to compile and link a 300k codebase for RISCV64 using our internal 15.0.7-based toolchain. It almost works, but it fails to link:
Hard-float 'd' ABI can't be used for a target that doesn't support the D instruction set extension (ignoring target-abi)
(... plenty of these ...)
Hard-float 'd' ABI can't be used for a target that doesn't support the D instruction set extension (ignoring target-abi)
ld.lld: error: /home/tamas/work/xx/build/lto_cache/llvmcache-8D3B2369E12D4E19EEDA96FFB8F16EF08BB1D893: cannot link object files with different floating-point ABI
ld.lld: error: /home/tamas/work/xx/build/lto_cache/llvmcache-5B904B7F5E30E1103D236BFB9D9748FC6AF7A62C: cannot link object files with different floating-point ABI
clang-15: error: linker command failed with exit code 1 (use -v to see invocation)
Inspecting these two files, I see
ELF 64-bit LSB relocatable, UCB RISC-V, soft-float ABI, version 1 (SYSV), not stripped
and
ELF 64-bit LSB relocatable, UCB RISC-V, soft-float ABI, version 1 (SYSV), with debug_info, not stripped
I’m using a compiler config file with the following contents:
--sysroot <CFGDIR>/../targets/riscv64-xx-linux-musl
-march=rv64imafdc
-mabi=lp64d
-mfloat-abi=hard
-Wl,--no-dynamic-linker
-Wl,-rpath,<CFGDIR>/../targets/riscv64-xx-linux-musl/lib
-Wl,-rpath,<CFGDIR>/../lib/riscv64-xx-linux-musl
-Qunused-arguments
-pie
-fPIC
-march, -mabi, -mfloat-abi were added later in an effort to fix the issue but did not make a difference (these are the desired values but also what I would expect to be the default without specifying them). The full invocation that I reconstructed from the ninja build looks like this:
#! /bin/bash
/home/tamas/.xx_toolchain/15.0.7+bced4da4f/bin/riscv64-xx-linux-musl-clang \
-Os \
-g \
-DNDEBUG \
-fvisibility=hidden \
-Wall \
-Wsign-compare \
-Wno-reorder-ctor \
-Wno-delete-non-virtual-dtor \
-Wunused-variable \
-Wuninitialized \
-fno-omit-frame-pointer \
-fno-ident \
-g2 \
-glldb \
-gdwarf-aranges \
-ggnu-pubnames \
-fdata-sections \
-ffunction-sections \
-flto=thin \
-Wl,--lto-O2 \
-fwhole-program-vtables \
-Wl,--thinlto-cache-dir=/home/tamas/work/xx/build/lto_cache/ \
-MD -MT test.o -MF test.d -o test.o -c ../test.c
- plus a PCH include which I didn’t bother with.
Inspecting all files in the LTO cache, I see that they are all one of these four:
ELF 64-bit LSB relocatable, UCB RISC-V, double-float ABI, version 1 (GNU/Linux), with debug_info, not stripped
ELF 64-bit LSB relocatable, UCB RISC-V, double-float ABI, version 1 (SYSV), with debug_info, not stripped
ELF 64-bit LSB relocatable, UCB RISC-V, soft-float ABI, version 1 (SYSV), not stripped
ELF 64-bit LSB relocatable, UCB RISC-V, soft-float ABI, version 1 (SYSV), with debug_info, not stripped
Notably, the two ELF files which end up soft-float are containing C source filenames as strings. Attempting to compile them separately with identical flags results in an object file containing IR (as expected). But that’s the output of the compilation, not an artifact that ends up in the LTO cache.
Any idea what I might be doing wrong or how I could troubleshoot this further? Disabling LTO should be a last resort as it would require significant effort to do it in all deps.