当程序仅在 ctrl+c (sigint) 上退出时,如何使用 llvm 正确分析 C++ 程序?

问题描述 投票:0回答:1

我正在尝试使用 llvm 分析 C++ 程序,并使用相应的标志通过 clang 进行编译

-fprofile-instr-generate -fcoverage-mapping

但是,程序没有“自然”的生命终结,只能使用信号退出。退出时,default.profraw 为空。我尝试使用信号处理程序并在捕获签名时执行以下代码:

                void (*_mcleanup)(void);
                _mcleanup = (void (*)(void))dlsym(RTLD_DEFAULT, "_mcleanup");
                if (_mcleanup == NULL)
                {
                    cout <<  "Unable to find gprof exit hook";
                }

                else _mcleanup();

...我在另一个线程中偶然发现的。这会生成一个实际上包含数据的 profraw 文件,但是,似乎会损坏 default.profraw 文件到无法解压缩的程度,从而在使用时生成错误:

llvm-profdata merge default.profraw -o default.profdata 

错误消息几乎表明 zlib 无法解压缩 profraw 文件。

是否有其他人有尝试分析仅使用信号退出的 C++ 程序的经验?

c++ clang llvm profiling code-coverage
1个回答
0
投票

默认情况下,llvm 使用 atexit()

在程序退出时转储分析数据,因此在收到信号后退出应该足够了。

signal(SIGINT, exit);
如果您的程序在发送不同信号的主管下运行,您可以添加更多处理程序,或使用像这样的包装器脚本。

#!/bin/sh my-program & pid=$! trap "kill -SIGINT ${pid}" SIGTERM wait


或者,llvm 有一个“连续模式”,即使被信号或崩溃杀死,据说也能够转储完整的覆盖数据。可以通过使用标志编译来启用它

-fprofile-generate -mllvm -runtime-counter-relocation

并在运行时添加 
%c

说明符,例如

export LLVM_PROFILE_FILE='profile-%m%c.profdata'
my-program

但是,这对我不起作用,因为 llvm-profdata 抱怨“配置文件数据被截断”。事实上,文档警告了

连续模式不支持 PGO 的值分析,目前仅在 Darwin 上支持。对 Linux 的支持可能已基本完成,但需要测试...

© www.soinside.com 2019 - 2024. All rights reserved.