4

我目前正在我的 Ubuntu 机器上为 Raspberry Pi 执行一些交叉编译测试。我目前的理解是 Raspberry Pi 支持硬件浮点,并且默认的 Raspbian OS 映像是使用硬件浮点 (armhf) 构建的。正确的?

如果我使用“arm-linux-gnueabi”工具链(不指定任何 ARM 标志)构建我的应用程序,那么我的应用程序将使用软浮点 ABI。正确的?

在这种情况下,我的所有依赖项也必须使用相同的 ABI 才能正确链接。正确的?

如果我的应用程序使用软浮点 ABI,那么我的应用程序肯定链接到软浮点 ABI 共享标准库。当我在 Raspberry Pi 上运行我的应用程序时,一切都按预期工作。如果 Raspbian 使用硬浮点 ABI(我猜共享标准库也可以),这怎么可能?

仅供参考:我的默认 arm-linux-gnueabi 配置为:

--with-float=soft
--with-arch=armv5

我正在像这样编译我的应用程序:

arm-linux-gnueabi-g++ test.cpp -o test

我的程序确实包括浮点计算:

double test = (123.456 + 789.123) * 1.23;
printf("%f\n", test); // prints: 1122.472170
printf("%f\n", std::floor(test)); // prints: 1122.000000
4

1 回答 1

7

您的所有确认都是正确的,我只想对 Raspbian 的armhf.

Debian 的armhf( arm-linux-gnueabihf) 以ARMv7t硬浮点为目标。由于 Raspbian 是基于 Debian 的,你会期望相同,但是 Raspbian 的armhf目标是ARMv6硬浮点(这首先是 Raspbian 存在的原因:在 Debian 的armel-- ARMv4t 软浮点之间找到一个中间地带 --以及armhf正确利用 Raspberry CPU 的架构)。

所以说 Raspbian 有点危险armhf,特别是因为很多人会使用 Debian(或 Ubuntu 等衍生产品)作为主机系统,因此很可能会混淆两者。如果你问我,Raspbian 的人在保持相同的架构名称时犯了一个错误,它确实应该是arm6hf.

当我在 Raspberry Pi 上运行我的应用程序时,一切都按预期工作。如果 Raspbian 使用硬浮点 ABI(我猜共享标准库也可以),这怎么可能?

arm-linux-gnueabi据我所知,和之间的唯一区别arm-linux-gnueabihf是涉及浮点的调用约定(前者使用整数寄存器传递它们,后者使用浮点寄存器传递)。

如果您从未在测试程序中使用浮点 ABI(我的意思是您不通过 CPU/FPU 寄存器将浮点数传递给外部库 - 但是您可以在内部完美地进行浮点计算 - 使用软-float - 例如,将结果转换为int在第三方库中实际“使用”它之前),那么您永远不会遇到 ABI 差异并且一切正常。

关于您给出的使用浮点数的示例,我相信它们属于我刚才描述的类别:您从不使用硬浮点 ABI。

  • 很可能std::floor是内联的(确保这一点的最佳方法是查看您的程序集转储)。
  • printf使用可变参数,因此您实际上使用的是传统的 C 调用约定,即。参数在堆栈上传递,而不是通过 CPU/FPU 寄存器。

无论如何,您应该远离当前的arm-linux-gnueabi工具链,并使用专为 Raspbian 设计的工具链。只需在网上搜索“ Raspberry Pi cross-compiler ”即可。这样你就不会被打扰了。

于 2013-10-04T12:23:19.180 回答