如何为 Android NDK 更新 GNU 链接器?
How do you update the GNU linker for an Android NDK?
我正在使用 NDK r12b 开发原生 Android 项目。这个 NDK(从那以后它看起来像所有其他的一样)附带了一个预构建的 GNU 链接器版本 2.25。我们最近试图提取我们项目的许多子模块,这些子模块引入了一个看起来是由 this bug in ld.
引起的构建错误
构建错误输出:
/opt/android-ndk-r12b/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin/../lib/gcc/arm-linux-androideabi/4.9.x/../../../../arm-linux-androideabi/bin/ld: internal error in do_relocate_sections, at /usr/local/google/buildbot/src/android/gcc/toolchain/build/../binutils/binutils-2.25/gold/reloc.cc:953
collect2: error: ld returned 1 exit status
我想我会尝试更新链接器,但没有找到预构建的二进制文件。所以我陷入了试图自己编译 ld/binutils 的困境。要么我的 Google 技能让我失望,要么执行此操作的文档真的很少见,要么假定用户有很多我没有的介绍性知识。
当使用 target=arm-linux 构建 binutils 2.29.1 时,我的应用程序构建错误,结果如下:
/opt/android-ndk-r12b/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin/../lib/gcc/arm-linux-androideabi/4.9.x/../../../../arm-linux-androideabi/bin/ld: unrecognised emulation mode: armelf_linux_eabi
Supported emulations: armelf_linux armelf armelfb armelfb_linux
collect2: error: ld returned 1 exit status
作为参考,我们当前版本的 ld 的 -V 输出是:
me@linux-vm:/opt/android-ndk-r12b/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/arm-linux-androideabi/bin$ ./ld-2.25 -V
GNU gold (binutils-2.25-0666073 2.25.51.20141117) 1.11
Supported targets:
elf64-littleaarch64
elf64-bigaarch64
elf32-littleaarch64
elf32-bigaarch64
elf64-tradlittlemips
elf32-tradlittlemips-nacl
elf64-tradbigmips
elf32-tradlittlemips-nacl
elf32-tradlittlemips
elf32-tradlittlemips-nacl
elf32-tradbigmips
elf32-tradlittlemips-nacl
elf32-tilegx-be
elf64-tilegx-be
elf32-tilegx-le
elf64-tilegx-le
elf32-bigarm
elf32-bigarm-nacl
elf32-littlearm
elf32-littlearm-nacl
elf64-powerpcle
elf64-powerpc
elf32-powerpcle
elf32-powerpc
elf64-sparc
elf32-sparc
elf32-x86-64
elf32-x86-64-freebsd
elf32-x86-64-nacl
elf64-x86-64
elf64-x86-64-freebsd
elf64-x86-64-nacl
elf32-i386
elf32-i386-freebsd
elf32-i386-nacl
Supported emulations:
aarch64_elf64_le_vec
aarch64_elf64_be_vec
aarch64_elf32_le_vec
aarch64_elf32_be_vec
elf64-tradlittlemips
elf32-tradlittlemips-nacl
elf64-tradbigmips
elf32-tradlittlemips-nacl
elf32-tradlittlemips
elf32-tradlittlemips-nacl
elf32-tradbigmips
elf32-tradlittlemips-nacl
elf32tilegx_be
elf64tilegx_be
elf32tilegx
elf64tilegx
armelfb
armelfb_nacl
armelf
armelf_nacl
elf64lppc
elf64ppc
elf32lppc
elf32ppc
elf64_sparc
elf32_sparc
elf32_x86_64
elf32_x86_64_nacl
elf_x86_64
elf_x86_64_nacl
elf_i386
elf_i386_nacl
显然我遗漏了一些重要的配置参数。我还尝试使用较旧的 (r8e) Android NDK 的 build/tools/build-gcc.sh 脚本来构建整个编译器工具链,但使用较新的 binutils 版本。这导致了未知的构建错误:
me@linux-vm:/opt/android-ndk-r8e/build/tools$ ./build-gcc.sh --gmp-version=5.0.5 --mpfr-version=3.1.1 --mpc-version=1.0.1 --binutils-version=2.26
$(pwd)/src $(pwd) arm-linux-androideabi-4.7
To follow build in another terminal, please use: tail -F /tmp/ndk-me/build/toolchain/config.log
Using C compiler: gcc -m32
Using C++ compiler: g++ -m32
Sysroot : Copying: /opt/android-ndk-r8e/platforms/android-9/arch-arm --> /tmp/ndk-me/build/toolchain/prefix/sysroot
Configure: arm-linux-androideabi-4.7 toolchain build
Building : arm-linux-androideabi-4.7 toolchain [this can take a long time].
Error while building toolchain. See /tmp/ndk-me/build/toolchain/config.log
config.log 的最后条目:
ar cru libintl.a bindtextdom.o dcgettext.o dgettext.o gettext.o finddomain.o loadmsgcat.o localealias.o textdomain.o l10nflist.o explodename.o dcigettext.o dcngettext.o dngettext.o ngettext.o plural.o plural-exp.o localcharset.o relocatable.o localename.o log.o osdep.o intl-compat.o
ranlib libintl.a
make[1]: Leaving directory `/tmp/ndk-me/build/toolchain/libbfd-binutils-2.26/intl'
在这一点上,我只是在转动我的轮胎,并试图通过配置参数和源包版本的不同组合来暴力破解成功。它看起来就像为 armelf_linux_eabi 添加仿真支持一样简单,但正如我所说,我没有找到任何说明如何执行此操作的文档或指南。肯定有某个 GNU 向导可以为我指明一条更好的道路吗?感谢您的帮助!
我会先尝试 --enable-targets=all
。这是一个有点大的锤子,但也许它可以帮助您避免弄清楚您需要的确切目标三胞胎(我的猜测是 arm-unknown-linux-eabi
)。
我正在使用 NDK r12b 开发原生 Android 项目。这个 NDK(从那以后它看起来像所有其他的一样)附带了一个预构建的 GNU 链接器版本 2.25。我们最近试图提取我们项目的许多子模块,这些子模块引入了一个看起来是由 this bug in ld.
引起的构建错误构建错误输出:
/opt/android-ndk-r12b/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin/../lib/gcc/arm-linux-androideabi/4.9.x/../../../../arm-linux-androideabi/bin/ld: internal error in do_relocate_sections, at /usr/local/google/buildbot/src/android/gcc/toolchain/build/../binutils/binutils-2.25/gold/reloc.cc:953
collect2: error: ld returned 1 exit status
我想我会尝试更新链接器,但没有找到预构建的二进制文件。所以我陷入了试图自己编译 ld/binutils 的困境。要么我的 Google 技能让我失望,要么执行此操作的文档真的很少见,要么假定用户有很多我没有的介绍性知识。
当使用 target=arm-linux 构建 binutils 2.29.1 时,我的应用程序构建错误,结果如下:
/opt/android-ndk-r12b/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/bin/../lib/gcc/arm-linux-androideabi/4.9.x/../../../../arm-linux-androideabi/bin/ld: unrecognised emulation mode: armelf_linux_eabi
Supported emulations: armelf_linux armelf armelfb armelfb_linux
collect2: error: ld returned 1 exit status
作为参考,我们当前版本的 ld 的 -V 输出是:
me@linux-vm:/opt/android-ndk-r12b/toolchains/arm-linux-androideabi-4.9/prebuilt/linux-x86_64/arm-linux-androideabi/bin$ ./ld-2.25 -V
GNU gold (binutils-2.25-0666073 2.25.51.20141117) 1.11
Supported targets:
elf64-littleaarch64
elf64-bigaarch64
elf32-littleaarch64
elf32-bigaarch64
elf64-tradlittlemips
elf32-tradlittlemips-nacl
elf64-tradbigmips
elf32-tradlittlemips-nacl
elf32-tradlittlemips
elf32-tradlittlemips-nacl
elf32-tradbigmips
elf32-tradlittlemips-nacl
elf32-tilegx-be
elf64-tilegx-be
elf32-tilegx-le
elf64-tilegx-le
elf32-bigarm
elf32-bigarm-nacl
elf32-littlearm
elf32-littlearm-nacl
elf64-powerpcle
elf64-powerpc
elf32-powerpcle
elf32-powerpc
elf64-sparc
elf32-sparc
elf32-x86-64
elf32-x86-64-freebsd
elf32-x86-64-nacl
elf64-x86-64
elf64-x86-64-freebsd
elf64-x86-64-nacl
elf32-i386
elf32-i386-freebsd
elf32-i386-nacl
Supported emulations:
aarch64_elf64_le_vec
aarch64_elf64_be_vec
aarch64_elf32_le_vec
aarch64_elf32_be_vec
elf64-tradlittlemips
elf32-tradlittlemips-nacl
elf64-tradbigmips
elf32-tradlittlemips-nacl
elf32-tradlittlemips
elf32-tradlittlemips-nacl
elf32-tradbigmips
elf32-tradlittlemips-nacl
elf32tilegx_be
elf64tilegx_be
elf32tilegx
elf64tilegx
armelfb
armelfb_nacl
armelf
armelf_nacl
elf64lppc
elf64ppc
elf32lppc
elf32ppc
elf64_sparc
elf32_sparc
elf32_x86_64
elf32_x86_64_nacl
elf_x86_64
elf_x86_64_nacl
elf_i386
elf_i386_nacl
显然我遗漏了一些重要的配置参数。我还尝试使用较旧的 (r8e) Android NDK 的 build/tools/build-gcc.sh 脚本来构建整个编译器工具链,但使用较新的 binutils 版本。这导致了未知的构建错误:
me@linux-vm:/opt/android-ndk-r8e/build/tools$ ./build-gcc.sh --gmp-version=5.0.5 --mpfr-version=3.1.1 --mpc-version=1.0.1 --binutils-version=2.26
$(pwd)/src $(pwd) arm-linux-androideabi-4.7
To follow build in another terminal, please use: tail -F /tmp/ndk-me/build/toolchain/config.log
Using C compiler: gcc -m32
Using C++ compiler: g++ -m32
Sysroot : Copying: /opt/android-ndk-r8e/platforms/android-9/arch-arm --> /tmp/ndk-me/build/toolchain/prefix/sysroot
Configure: arm-linux-androideabi-4.7 toolchain build
Building : arm-linux-androideabi-4.7 toolchain [this can take a long time].
Error while building toolchain. See /tmp/ndk-me/build/toolchain/config.log
config.log 的最后条目:
ar cru libintl.a bindtextdom.o dcgettext.o dgettext.o gettext.o finddomain.o loadmsgcat.o localealias.o textdomain.o l10nflist.o explodename.o dcigettext.o dcngettext.o dngettext.o ngettext.o plural.o plural-exp.o localcharset.o relocatable.o localename.o log.o osdep.o intl-compat.o
ranlib libintl.a
make[1]: Leaving directory `/tmp/ndk-me/build/toolchain/libbfd-binutils-2.26/intl'
在这一点上,我只是在转动我的轮胎,并试图通过配置参数和源包版本的不同组合来暴力破解成功。它看起来就像为 armelf_linux_eabi 添加仿真支持一样简单,但正如我所说,我没有找到任何说明如何执行此操作的文档或指南。肯定有某个 GNU 向导可以为我指明一条更好的道路吗?感谢您的帮助!
我会先尝试 --enable-targets=all
。这是一个有点大的锤子,但也许它可以帮助您避免弄清楚您需要的确切目标三胞胎(我的猜测是 arm-unknown-linux-eabi
)。