-fprofile-use
和-fauto-profile
之间的区别是什么?
以下是文档的说法:
https://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html#Optimize-Options
-fprofile用途
-fprofile使用=路径
启用配置文件反馈导向的优化,以及通常只有可用的配置文件反馈才能获利的以下优化:[...]
如果指定了path,GCC会查看查找配置文件反馈数据文件的路径。见-fprofile-dir。
并在
下面-fauto轮廓
-fauto轮廓=路径
启用基于采样的反馈导向优化,以及通常只有可用的配置文件反馈才能获利的以下优化:[...]
path是包含AutoFDO配置文件信息的文件的名称。如果省略,则默认为当前目录中的fbdata.afdo。
([...]
-fauto-profile
中的优化列表更长。)
答案 0 :(得分:6)
我偶然发现了一条我无法记住的道路并正在学习这些东西。但是,如果我能从中学到一些东西,我不想看到一个悬而未决的问题!所以我读了。
正如GCC所说,这两种都是应用反馈导向优化的模式。通过运行程序和分析它的作用,它是如何做的,它在哪些函数中花费的时间等等 - 我们可以从结果中促进额外的,定向优化数据。分析器的结果是前馈的'对于优化者。接下来,假设您可以使用您的配置文件优化二进制文件和 ,然后编译另一个FDO版本,依此类推......因此反馈部分这个名字。
真正的答案,这两个开关之间的差异,并没有非常清楚地记录下来,但如果我们只需要进一步了解它就可以使用。
首先,您对-fprofile-use
的引用仅表明它需要 -fprofile-generate
,这是一个没有详细记录的选项:来自{{1}的引用只是告诉您阅读您已经在的页面,在所有情况下,-use
仅被提及但从未定义过。有用! 但是!我们可以参考这个问题的答案:How to use profile guided optimizations in g++?
正如该答案所述,并且此处的GCC文档会轻轻指示 ... -generate
导致 instrumentation 将被添加到输出二进制文件中。正如该页面总结的那样,一个已检测的可执行文件添加了一些内容,以便在运行时进行额外的检查或洞察。
(我所知道的另一种形式的仪器 - 以及我使用的那种 - 是编译器附加库UBSan,我通过GCC's -fsanitize=undefined
option使用它。这会在运行时捕获一些未定义的行为。海湾合作委员会已经透露了UB我可能已经花了很长时间才找到 - 并且让我想知道我的程序是如何运行的!Clang can use this library too,也许还有其他编译器。)
相比之下,-fprofile-generate
是不同的。在你引用它的概要中,关键的区别是暗示,如果不清楚的话:
-fauto-profile
是包含 AutoFDO 个人资料信息的文件的名称。
此模式使用AutoFDO处理分析和后续优化。对谷歌我们去:AutoFDO前几行不能尽可能简洁地解释这一点,我认为最好的摘要埋藏在页面的相当远的地方:
AutoFDO [
path
]和FDO [-fauto-profile
]之间的主要区别在于优化二进制文件上的AutoFDO配置文件而不是检测二进制文件。这使得它在处理方面非常不同克隆功能。
它是如何做到的? -fprofile-use
要求您提供由Linux内核的分析器Perf编写的分析文件,并将其转换为AutoFDO格式。 Perf,而不是添加仪器,使用CPU的硬件功能和操作系统的内核级功能来分析程序运行时的各种统计信息:
-fauto-profile
功能强大:它可以检测CPU性能计数器,跟踪点,kprobes和uprobes(动态跟踪)。它具有轻量级分析功能。 [...]性能计数器是CPU硬件寄存器,用于计算硬件事件,例如执行的指令,遭受的缓存未命中或分支错误预测。它们构成了分析应用程序以跟踪动态控制流和识别热点的基础。
因此,它允许它分析优化程序,而不是仪表化程序。我们可以合理地假设这更能代表您的程序在现实世界中的反应 - 因此可以促进收集更多有用的分析数据并因此应用更有效的优化。
此处总结了如何将所有这些联系在一起并让perf
对您的计划采取措施的工作示例:Feedback directed optimization with GCC and Perf
(也许现在我已经了解了这一切,我有一天会尝试这些选项!)
答案 1 :(得分:0)
underscore_d可以深入了解这些差异。
这是我的看法。
首先通过使用-fprofile-generate
进行编译来执行内部分析,该分析将探查器集成到二进制文件中以进行性能数据收集运行。执行二进制文件,持续10分钟或您认为足以覆盖事件探查器记录时间的任何时间。如果它是多线程应用程序,则使用-fprofile-use
和-fprofile-correction
重新编译。内部事件探查器运行会导致严重的性能下降(在我的情况下为25%),这不能反映真实世界中非事件探查器包含的二进制行为,因此可能会导致分析的准确性降低,但是如果运行探查器时所有活动都启用了带有性能损失,我想应该没关系。
或者,您可以使用特定于内核的perf工具(更容易出错,更省力)(可能还需要构建支持分析,跟踪等的内核)来创建分析数据。可以将其视为外部配置文件,并且在进行概要分析时对应用程序性能的影响可忽略不计。您可以在正常编译的二进制文件上运行它。我找不到将两者进行比较的研究。
perf record -e br_inst_retired:near_taken -b -o perf.data *your_program.unstripped -program -parameters*
然后在不剥离二进制文件的情况下,将分析数据转换为GCC可以理解的内容...
create_gcov --binary=your_program.unstripped --profile=perf.data --gcov=profile.afdo
然后使用-fauto-profile
重新编译应用程序。已知存在Perf和AutoFDO / create_gcov版本特定的问题。我参考了https://blog.wnohang.net/index.php/2015/04/29/feedback-directed-optimization-with-gcc-and-perf/,以获取有关此替代配置文件方法的详细信息。
-fprofile-use
和-fauto-profile
都默认启用许多优化选项,在我的情况下,我所不希望的-funroll-loops对我的应用程序性能产生了负面影响。如果您使用的是脚踏车类型,则可以通过在编译标志中加入禁用对应项来测试选项组合,在本例中为-fno-unroll-loops。
在剥离二进制文件后,使用我的程序进行内部配置,它使大小减少了25%(与原始的非Profiler剥离的二进制文件相比),但是我仅观察到了性能下降和以前报告的工作输出波动程序日志(这是一个加密货币矿工)更加不稳定,而不是像最初那样在哈希率的高峰和低谷之间逐渐上升和下降。
整体,黑暗中的一击。