ARM 编译错误,VFP 寄存器使用的是可执行文件,而不是目标文件

过去几天我一直有这个问题,我不能理解这里到底发生了什么,或者问题是什么。

我有一个这些旗子的 makefile:

CC = arm-linux-gnueabihf-gcc-4.6
FLAGS = -O3 -march=armv7-a -mtune=cortex-a9 -mfpu=neon -ftree-vectorize -mfloat-abi=softfp -std=gnu99

我有一个图书馆。一个文件,其中有一些目标文件,所有我需要做的是链接到我的可执行文件。我知道原型机什么的,唯一不满的是:

/usr/bin/ld: error: *EXECUTABLE* uses VFP register arguments, *OBJECTFILE* does not
/usr/bin/ld: failed to merge target specific data of file *OBJECTFILE*

当我不使用-mfloat-abi = softfp 时,会得到另一个与浮点寄存器相关的错误。

有人知道是什么导致了这个问题吗? 我能做些什么来解决这个问题,比如让我的可执行文件不使用虚拟浮点寄存器参数?

x@x:~/Desktop/perf_test$ make
arm-linux-gnueabihf-gcc-4.6 -c -O3 -march=armv7-a -mtune=cortex-a9 -mfpu=neon -ftree-vectorize -std=gnu99 -mfloat-abi=softfp  perf_test.c ../baseline/util.c
arm-linux-gnueabihf-gcc-4.6 -o perf_test perf_test.o util.o  ../baseline/lib.a
/usr/bin/ld: error: perf_test uses VFP register arguments, perf_test.o does not
/usr/bin/ld: failed to merge target specific data of file perf_test.o
/usr/bin/ld: error: perf_test uses VFP register arguments, util.o does not
/usr/bin/ld: failed to merge target specific data of file util.o
/usr/bin/ld: error: perf_test uses VFP register arguments, ../baseline/lib.a(a.o) does not
/usr/bin/ld: failed to merge target specific data of file ../baseline/lib.a(a.o)
/usr/bin/ld: error: perf_test uses VFP register arguments, ../baseline/lib.a(b.o) does not
/usr/bin/ld: failed to merge target specific data of file ../baseline/lib.a(b.o)
/usr/bin/ld: error: perf_test uses VFP register arguments, ../baseline/lib.a(c.o) does not
/usr/bin/ld: failed to merge target specific data of file ../baseline/lib.a(c.o)
/usr/bin/ld: error: perf_test uses VFP register arguments, ../baseline/lib.a(d.o) does not
/usr/bin/ld: failed to merge target specific data of file ../baseline/lib.a(d.o)
/usr/bin/ld: error: perf_test uses VFP register arguments, ../baseline/lib.a(e.o) does not
/usr/bin/ld: failed to merge target specific data of file ../baseline/lib.a(e.o)
/usr/bin/ld: error: perf_test uses VFP register arguments, ../baseline/lib.a(f.o) does not
/usr/bin/ld: failed to merge target specific data of file ../baseline/lib.a(f.o)
collect2: ld returned 1 exit status
make: *** [perf_test] Error 1
123330 次浏览

这只是猜测,但是您可能还需要为链接阶段提供部分或全部与浮点相关的交换机。

您的目标三元组表明您的编译器配置为 硬漂浮 ABI。这意味着 libgcc 库也将是 hardfp。错误消息表明至少部分系统正在使用 软浮球ABI。

如果编译器启用了 multilib (你可以从 -print-multi-lib中看出来) ,那么你可以使用 -mfloat-abi=softfp,但是如果没有,那么这个选项对你没有多大帮助: gcc 将很高兴地生成 softfp 代码,但是那样就没有兼容的 libgcc 来链接了。

基本上,硬 fp 和软 fp 就是不兼容。您需要以某种方式配置整个系统。

编辑: 一些发行版已经或将要成为“ multiarch”。如果您有其中之一,那么可以立即安装 都有 ABI,但是这是通过将所有内容加倍来完成的——兼容性问题仍然存在。

也可以通过添加几个标志(如 -marm -mthumb-interwork)来解决这个错误。这对我避免同样的错误很有帮助。

我发现在 arm hardfloat 系统中,glibc binutils 和 gcc 被交叉编译,使用 gcc 会出现同样的错误。

它是通过将 -mfloat-abi=hard导出到标志来解决的,然后 gcc 编译时没有错误。

也使用相同的编译器选项进行链接。

例如:

gcc  -mfloat-abi=hard fpu=neon -c -o test.cpp test.o
gcc  -mfloat-abi=hard fpu=neon -c test1.cpp test1.o
gcc test.o test1.o mfloat-abi=hard fpu=neon HardTest

在我的案例中,CFLAGS = -O0 -g -Wall -I. -mcpu=cortex-m4 -mthumb -mfpu=fpv4-sp-d16 -mfloat-abi=soft起到了一定的作用。正如你所看到的,我将它用于我的 stm32f407。

在我的特殊情况下 -g -march=armv7-a -mfloat-abi=hard -mfpu=neon -marm -mthumb-interwork工作。

我在 STM32F4上使用 Atollic for ARM 遇到了这个问题(我猜它适用于所有带 FPU 的 STM32)。

使用 SW 浮点数对我来说不太好(因此编译是正确的)。

当 STM32cubeMX 为 TrueStudio (Atollic)生成代码时,它不会在 C/C + + 构建设置中设置 FPU 单元(不确定是否为其他 IDE 生成代码)。

“目标”中为(在项目属性构建设置下)设置 FPU:

  • 汇编器
  • C 编译器
  • C 林克

然后您可以选择混合 HW/SW fp 或使用 HW。

为预期目标添加生成的命令行:

-mfloat-abi=hard -mfpu=fpv4-sp-d16

< a href = “/questions/tags/atollic”class = “ post-tag”title = “ show questions tag & # 39; atollic & # 39;”rel = “ tag”> atollic

这个答案在表面上看起来可能是不相关的,但是这个错误消息有一个间接的原因。

首先,“使用 VFP 寄存器...”错误消息是在构建中混合使用 mfloat-abi = soft 和 mfloat-abi = hard 选项直接导致的。对于要链接的所有对象,此设置必须一致。对这个问题的其他回答很好地涵盖了这个事实。

这个错误的间接原因可能是 Eclipse 编辑器被项目中自己造成的错误弄糊涂了”。Cproject 」档案。Eclipse 编辑器经常重新调整文件链接,有时当您更改目录结构或文件位置时,它会自行中断。这也会影响到 gcc 编译器的路径设置——并且只对项目文件的子集有影响。虽然我还不确定到底是什么导致了这个失败,但是。带备份的 cproject 文件为我纠正了这个问题。我注意到了。在添加了一个包含目录路径并开始接收“ VFP 寄存器错误”消息之后,java.null.point 出现错误。在构建日志中,我注意到一个不同的 gcc 编译器路径被用于我的一些源代码,这些源代码是工作区的本地源代码,但不是所有源代码! ?两个 gcc 编译器由于未知的原因使用不同的 float 设置-因此出现了 VFP 寄存器错误。

我比较了。Cproject 设置,并观察到引起麻烦的源的条目的差异-即使项目设置的重写被禁用。通过替换。C 项目文件的旧版本的问题消失了,我留下这个答案作为发生了什么事情的提醒。

我也面临着同样的问题。我正在尝试构建用于 CyclonV FPGA-SoC 的 Linux 应用程序。我面对的问题如下:

Error: <application_name> uses VFP register arguments, main.o does not

我使用的工具链 arm-linux-gnueabihf-g++提供的嵌入式软件设计工具的改变。

这个问题可以通过出口来解决: mfloat-abi=hard到标志,然后 arm-linux-gnueabihf-g++编译没有错误。也包括在 CCLD的标志。

请注意,硬浮点和软浮点 ABI 不具有链接兼容性; 您必须使用相同的 ABI 编译整个程序,并使用一组兼容的库进行链接 Https://gcc.gnu.org/onlinedocs/gcc/arm-options.html Arm-none-eabi-gcc. exe

Silicon Labs“ kjostera”“ Employee”对 EFR32 Flex Gecko (交叉参考 Cortex-M4F)的回应: “所以用 softfp ABI 编译的代码与用 hardfp ABI 编译的代码在链接时间上是不兼容的。因此,由于我们目前只支持使用 softfp ABI 编译的 RAIL 库,这意味着您还必须使用 softfp ABI 构建应用程序。” ”注意,使用 softfp ABI 并不意味着您的代码不能使用 FPU 指令。当编译器认为浮点运算有意义时,任何做浮点运算的代码都会使用 FPU。” 然后,“ kjostera”继续演示 GCC 7为 -mfloat-abi=softfp-mfloat-abi=hard生成 Assembly,调用 vmul.f32指令,softfp的指令计数为10,hard的指令计数为9。 Https://www.silabs.com/community/mcu/32-bit/forum.topic.html/enable_fpu_in_rail-p-seyr https://www.silabs.com/documents/public/reference-manuals/efr32xg14-rm.pdf

这个问题的另一个原因是您忽略了最终二进制目标的 CPU 体系结构规范。

例如,即使您的 -mfloat-abi-mfpu交换机在所有模块和最终的二进制文件之间达成一致,您仍然可能在 -mcpu上出错。

在我的例子中,为最终的二进制文件省略 -mcpu=cortex-m4导致链接器默认为某些其他 CPU 架构。这也产生了关于 VFP 寄存器的相同消息。

我有类似的问题,通过静态链接我的项目与一些外部库覆盆子。任何提到的编译器选项都可能有帮助。通过比较我所链接的静态库的目标文件和我所链接的静态库的目标文件的自述输出,我使用了另一种交叉编译器。使用与前面相同的编译器选项,就不会再出现这个问题了。所以,也许您只需要使用正确的交叉编译器,支持正确的 ABI 版本。

作为提示,ABI 版本在主机上的编译器名称中进行编码。