TransWikia.com

cross-compiling for 32-bit architecture on 64-bit (FreeBSD)

Unix & Linux Asked by sephiroth on November 30, 2020

I’m having problems cross-compiling a library for 32bit FreeBSD architecture on a 64bit FreeBSD-system. I’m happy about any hint/advice. Compiling for same architecture (64bit) works fine.

I built ports lang/gcc9 & lang/gcc9-devel. In the configuration of the port, I enabled “multilib”, which should build for 32 and 64 bit. If I search for available libstdc on the system, I find the following:

[root@build /usr/local/share/ohNet-build4FreeBSD/ohNet-ohNet_1.17.2776]# find / -iname "*libstdc*"
/usr/local/share/gcc-9.2.0/python/libstdcxx
/usr/local/lib32/gcc9/libstdc++.so.6.0.27
/usr/local/lib32/gcc9/libstdc++.so
/usr/local/lib32/gcc9/libstdc++.so.6
/usr/local/lib32/gcc9/libstdc++.so.6.0.27-gdb.py
/usr/local/lib32/gcc9/libstdc++.a
/usr/local/lib32/gcc9/libstdc++fs.a
/usr/local/lib/gcc9/libstdc++.so.6.0.27
/usr/local/lib/gcc9/libstdc++fs.a
/usr/local/lib/gcc9/libstdc++.so.6
/usr/local/lib/gcc9/libstdc++.so
/usr/local/lib/gcc9/libstdc++.a
/usr/local/lib/gcc9/libstdc++.so.6.0.27-gdb.py
/usr/ports/lang/libstdc++_stldoc_4.2.2

When compiling for 64bit, my project builds fine.
When compiling for 32bit, I set the following env-variables:

export CROSS_COMPILE_CFLAGS=-m32
export CROSS_COMPILE_LINKFLAGS=-m32

and the build fails with

/usr/local/bin/ld: skipping incompatible /usr/local/lib/gcc9/gcc/x86_64-portbld-freebsd11.2/9.2.1/../../../libstdc++.a when searching for -lstdc++
/usr/local/bin/ld: cannot find -lstdc++

If I understand correctly, the compiler fails to find the compatible 32-bit libraries, although they are there (see above). Please advise for the correct way to fix this.

One Answer

I know it's very late, but I ran into this issue as well and had trouble finding a good solution to this. It looks like GCC is unable to find its own library path when using -m32. The main issue is that FreeBSD switched to libc++ back on FreeBSD 11, and stdc++ was not provided anymore.

The only way I got it to work was:

  1. compile with -B/usr/lib32 -B/usr/local/lib32/gcc9/. That honestly looks like a bug in GCC, because running g++ main.cpp -v will show that GCC tries to call LD with the wrong lib path. These two flags fix it; the first one is only necessary for GCC 7 and below (GCC 8 and above will look in /usr/lib32). The next one is necessary for all versions of G++; replace gcc9 with whatever GCC actually ships with.
  2. The program will compile but fail to find libstdc++.so.6 at runtime. Either use -static-libstdc++ (not a very good option for my program which is plugin based; all 30 DLLs just grew by a megabyte) or install compat9x-amd64 which, despite its name, will add a version of libstdc++.so.6 for x86 as well as amd64. You need to reboot or rerun ldconfig for the path to become visible. That also looks like a bug in GCC, as GCC adds a config file in ldconfig for AMD64 libraries, but does not have this config file for lib32 (although there is a dedicated system for ldconfig32). The compat9x package provides a libstdc++ and will also add a config file for ldconfig.

With this setup, I managed to build my program, although I still think that FreeBSD has really poor support for multilib (many Linux distros have better multilib support where you can install both 32 and 64 bit libraries in parallel, and Debian-based and some other distros even have multiarch support where you can also add cross-compilation for foreign architectures in parallel with the main architecture, like arm and powerpc on AMD64)

Answered by Nicolas Mercier on November 30, 2020

Add your own answers!

Ask a Question

Get help from others!

© 2024 TransWikia.com. All rights reserved. Sites we Love: PCI Database, UKBizDB, Menu Kuliner, Sharing RPP