gcc 为什么很少使用-march=native?

vktxenjb  于 2023-03-18  发布在  其他
关注(0)|答案(4)|浏览(191)

大多数C/C++编译器都有一个可传递给编译器的标志-march=native,它告诉编译器针对主机CPU的微体系结构和伊萨扩展调整生成的代码。即使它的名称不同,对于基于LLVM的编译器,通常也有一个等效的选项,如rustcswiftc
根据我自己的经验,这个标志可以为数字密集型代码提供巨大的加速比,而且它 * 听起来 * 似乎不会对您自己的机器编译的代码造成任何损害。也就是说,我不认为我见过任何构建系统或静态编译器默认启用它:

  • 显然,任何需要传递它的命令行编译器可执行文件在默认情况下都不会使用它。
  • 我想不出有哪个IDE默认启用了这一功能。
  • 我想不出我使用过的任何通用构建系统(cmakeautomakecargospm等)在默认情况下启用它,即使是优化的构建也是如此。

我能想到几个原因,但没有一个真正令人满意:

  • -march=native并不适用于将要分发到其他机器上的二进制文件,也就是说,我发现自己在自己的机器上编译源代码的频率要比在其他机器上编译源代码的频率高得多,但这并不能解释它在调试构建中缺乏使用,因为在调试构建中没有分发的意图。
  • 至少在Intel x86 CPU上,我的理解是不经常使用AVX指令可能会降低性能或能效,因为AVX单元在不使用时会断电,需要通电才能使用,而且许多Intel CPU都会降低时钟以运行AVX指令。不过,这只是解释了为什么AVX不会被启用,而不是为什么不针对特定微体系结构对常规指令的处理来调整代码。
  • 由于大多数x86 CPU都使用带有寄存器重命名功能的无序超标量流水线,因此针对特定微架构的调优代码可能并不特别重要。不过,如果它 * 可以 * 有所帮助,为什么不使用它呢?
dy1byipe

dy1byipe1#

保守

如果您仔细查看一下gcc(列表中最老的编译器)的默认值,就会发现它们非常保守:

  • 默认情况下,在x86上,只激活SSE 2;连SSE 4都没有。
  • -Wall-Wextra中的标志集多年未更改;有新的有用警告,它们未添加到-Wall-Wextra

为什么?因为那会弄坏东西!
整个开发链都依赖于这些方便的默认值,任何更改都可能会破坏这些默认值,或者生成无法在目标上运行的二进制文件。
用户越多,威胁就越大,所以gcc的开发人员非常非常保守,避免全球性的破坏,而下一批编译器的开发人员也会步前辈的后尘:这被证明是有效的。

  • 注意:rustc将默认为静态链接,并吹嘘您可以复制二进制文件并将其放在另一台机器上;显然-march=native在这里是一个障碍。*

群众友好

事实上,这并不重要。你自己也意识到了:
根据我自己的经验,这个标志可以为数字密集型代码提供巨大的加速
大多数代码充满了虚拟调用和分支(通常是OO代码),而且根本不是数字密集型的。因此,对于大多数代码,SSE 2通常是足够的。
性能真正重要的几个代码库无论如何都需要投入大量的时间进行性能调优,包括代码和编译器级别的调优。如果向量化很重要,它就不会任由编译器随心所欲地进行:开发人员将使用内置的intrinsic并自己编写矢量化代码,因为这比使用监控工具来确保自动矢量化的发生要便宜。
此外,即使是数字密集型代码,宿主机和目标机也可能略有不同。编译得益于大量内核,即使频率较低,而执行得益于高频率和可能更少的内核,除非工作易于并行化。

结论

默认情况下不激活-march=native可以让用户更容易上手;因为即使是追求性能的人也可能不太在意它,这意味着得不偿失。

  • 在从一开始默认值为-march=native的替代历史中;用户将用于指定目标体系结构,我们将不进行此讨论。*
qhhrdooz

qhhrdooz2#

-march=native是一个破坏性标志。它使得二进制文件可能在许多硬件上不兼容(基本上是任何CPU,不是用于编译的CPU的直接后代)。默认启用这个标志太危险了。
另一个需要考虑的重要问题是-march=native的主要最终用途是优化,默认的优化标志是-O0(无优化),因此从这个Angular 来看,默认启用它也没有意义。

wh6knrhe

wh6knrhe3#

您是从高级用户的Angular 考虑问题,但是编译器工具链的主要受众不是高级用户,而是开发人员。
大多数开发人员都有独立的开发机器和目标生产系统。对于消费者应用程序来说,这个目标系统是其他人的机器,具有所有的差异。为最常见的特性构建是一个安全的默认值,因为它减少了只发生在开发人员自己的机器之外的错误的机会。
当然,有些情况下,开发人员知道他们将为一台具有已知架构的目标机器开发一个应用程序,但即使在这种情况下,大多数应用程序对性能并不敏感,所以安全选项作为默认选项仍然足够好用,而开发性能敏感应用程序的开发人员通常更愿意花时间调整他们的构建配置。

z5btuh9x

z5btuh9x4#

答案已经回答了,只是显示了O3和3月=本地之间的区别。我正在创建大量的数学3D视频。O3没有设置和3月=本地原始。

100 out of 900 %11.2222 time left: 0:0:7 time since: 1
200 out of 900 %22.3333 time left: 0:0:6 time since: 2
300 out of 900 %33.4444 time left: 0:0:5 time since: 3
400 out of 900 %44.5556 time left: 0:0:6 time since: 5
500 out of 900 %55.6667 time left: 0:0:4 time since: 6
600 out of 900 %66.7778 time left: 0:0:3 time since: 7
700 out of 900 %77.8889 time left: 0:0:2 time since: 8
800 out of 900 %89 time left: 0:0:1 time since: 9
Finished it took 0:0:10

如果我使用march=native进行O3优化,输出如下所示:

100 out of 900 %11.2222 time left: 0:0:0 time since: 0
200 out of 900 %22.3333 time left: 0:0:3 time since: 1
300 out of 900 %33.4444 time left: 0:0:1 time since: 1
400 out of 900 %44.5556 time left: 0:0:2 time since: 2
500 out of 900 %55.6667 time left: 0:0:1 time since: 2
600 out of 900 %66.7778 time left: 0:0:1 time since: 3
700 out of 900 %77.8889 time left: 0:0:1 time since: 4
800 out of 900 %89 time left: 0:0:0 time since: 4
Finished it took 0:0:5

因此,O3优化确实有帮助。
根据新的评论编辑,程序从昨天开始有了一些发展,所以时间有点高。这是O3三月=本地现在:

100 out of 900 %11.2222 time left: 0:0:15 time since: 2
200 out of 900 %22.3333 time left: 0:0:10 time since: 3
300 out of 900 %33.4444 time left: 0:0:9 time since: 5
400 out of 900 %44.5556 time left: 0:0:7 time since: 6
500 out of 900 %55.6667 time left: 0:0:6 time since: 8
600 out of 900 %66.7778 time left: 0:0:4 time since: 9
700 out of 900 %77.8889 time left: 0:0:3 time since: 11
800 out of 900 %89 time left: 0:0:1 time since: 12
Finished it took 0:0:14

如果我把三月=本地人:

100 out of 900 %11.2222 time left: 0:0:15 time since: 2
200 out of 900 %22.3333 time left: 0:0:13 time since: 4
300 out of 900 %33.4444 time left: 0:0:11 time since: 6
400 out of 900 %44.5556 time left: 0:0:9 time since: 8
500 out of 900 %55.6667 time left: 0:0:7 time since: 10
600 out of 900 %66.7778 time left: 0:0:5 time since: 12
700 out of 900 %77.8889 time left: 0:0:3 time since: 14
800 out of 900 %89 time left: 0:0:1 time since: 16
Finished it took 0:0:18

相关问题