riscvarchive/riscv-newlib

Build failure with riscv32-elf gcc 7.0.1

afaerber opened this issue · 9 comments

When building the latest riscv-newlib-2.4.0 branch against an upstream gcc configured as riscv32-elf, it will fail to build, complaining about some lp64 subdir trying to use elf64-littleriscv:

https://build.opensuse.org/package/live_build_log/home:a_faerber:riscv/cross-riscv32-newlib-devel/openSUSE_Leap_42.2/x86_64

If using a riscv64-elf gcc, it will succeed to build:

https://build.opensuse.org/package/live_build_log/home:a_faerber:riscv/cross-riscv64-newlib-devel/openSUSE_Leap_42.2/x86_64

I would expect newlib to simply not enter 64-bit directories with a 32-bit only toolchain.

Note that upstream binutils 2.28 does not support a generic riscv-elf target, so it would seem weird to force everyone into using riscv64-elf for 32-bit development.

When I build riscv-gnu-toolchain with

../configure --prefix=$RISCV --disable-linux --enable-multilib --with-arch=rv32imafd

I get a problem similar to this one. I think this might actually be a binutils bug: we have eelf64lriscv in ALL_64_EMULATION_SOURCES, which means that a 32-bit LD can't target 64-bit binaries. I think there's two possible fixes:

  • Add elf64-littleriscv support to the 32-bit LD. This would have the advantage of making the 32-bit and 64-bit toolchains exactly the same (like we've been telling people they are), but wouldn't fix binutils-2.28 and would be the only target with this behavior.

  • Add a second GCC multilib target that only builds 32-bit libraries, and use that in 32-bit land.

Thanks for finding the bug!

Thanks for looking into this so quickly.

Note that the documentation is a little inconsistent, talking of riscv-gcc in section Installation (Newlib) and of a directory riscv-elf on the generic tools page in section Testing Your Toolchain.

It appears the target triplet you're currently using is riscv64-unknown-elf, which should be identical to my shortened riscv64-elf. The announcement cited "GNU conventions" for riscv64-unknown-elf, but I assume that refers to the added -elf part? Was riscv-unknown-elf not an option? Why would you want to have two toolchains that are "exactly the same"? Just to allow different ISA defaults? In that case your binutils suggestion seems sound, and if you declare it a bug fix maybe they're even willing to backport it to the 2.28 stable branch.

When thinking of native RISC-V Linux systems though, allowing to build 32-bit code on a 64-bit host certainly makes sense as that might be executed locally and avoids requiring a separate cross-compiler, but on a 32-bit system having all the elf64 and rv64 stuff in native binutils+gcc might cause some bloat. I think ppc does all in one powerpc target, whereas aarch64 is separate from arm, so both models seem permissible.

Confirming that both riscv32-elf and riscv64-elf newlib 2.5 builds succeed now, applying the patch onto our GCC 7.1.1 package.

We actually have a patch upstream in binutils that enables 64-bit BFDs on the 32-bit toolchain. I think it'd be better if you used that if possible, as that's the cleaner fix.

Also, FYI: there's a patches@groups.riscv.org mailing list that you should probably subscribe to if you're planning on distributing RISC-V toolchain software, all the core patches are being CC'd onto there.

@palmer-dabbelt Can you point me to the upstream binutils commit(s) for backporting please?

I submitted a patch set to the 2.28 maintainer for approval earlier today https://sourceware.org/ml/binutils/2017-05/msg00041.html . In general I backport every RISC-V patch to 2.28, as that's what we're releasing in riscv-gnu-toolchain.

The specific patch you're looking for is https://sourceware.org/ml/binutils/2017-05/msg00044.html which is also on our 2.28 branch riscvarchive/riscv-binutils-gdb@a4e99bc .

Was fixed with a binutils patch about 8 months ago.