我使用gcov库测量我的代码的覆盖率,我想以用户友好的格式生成覆盖率报告.我已经找到了lcov实用程序,但它与Windows环境不兼容(主要是因为解析路径的方式).有谁知道有效支持Windows的lcov端口?
似乎在Windows上运行它会很容易(它认为它甚至可以通过模仿unix shell命令的行为的少量创意批处理/ perl脚本来解决),并且该工具非常有用,所以我想有人可能有已经完成了.
我想使用 gcov 和 lcov 生成覆盖率报告。
到目前为止我所做的:-
1. I compiled my code using --fprofile-arcs and -fprofile-coverage in
g++.
2. I have linked using lcov.
3. I have .gcno files with th e.o location.
4. When I execute binary, it is resulting into .gcda files.
Run Code Online (Sandbox Code Playgroud)
我必须做什么:-
我必须使用这些数据文件 (.gcda),并希望使用 lcov 创建一个干净的报告。
问题:-
有多个目录,其中有源文件,并且在每个目录中我创建一个 obj/ARCH 目录来保存目标文件。
因此最终的目录结构将是:-
proto ----> MJ1 ----> MJ2 ----> MJ3 ----> MJ4 ----> MJ5
MJ1 ----> .cpp
----> obj/linux/*.o *.gcno *.gcda
MJ2 ----> .cpp
----> obj/linux/*.o *.gcno …Run Code Online (Sandbox Code Playgroud) 我需要安装什么Cygwin软件包才能让lcov在Cygwin上运行?
我试图运行lcov并收到以下命令:找不到命令
感谢您的任何帮助.
PS我应该指出gcov确实有效.
在我通过以100%覆盖率启动并运行小型C++测试项目来了解有关自动化测试的更多信息的过程中,我遇到了以下问题 - 即使我的所有实际代码行和所有执行分支都被测试覆盖,lcov仍然报告两行未经测试(它们只包含函数定义),以及一个"重复"的构造函数方法,即使它与我的"真实"构造函数(唯一一个定义和使用过的)完全匹配,也可以是未经测试的.
(跳至编辑最小的复制案例)
如果我使用gcovr python脚本生成相同的覆盖率统计信息(来自相同的源,.gcno和.gcda文件)并将结果传递给Jenkins Cobertura插件,它会给我100%的所有计数 - 行,条件和方法.
这就是我的意思:
Jenkins Cobertura Coverage页面:http://gints.dyndns.info/heap_std_gcovr_jenkins_cobertura.html(一切都在100%).
使用lcov处理相同的.gcda文件:http://gints.dyndns.info/heap_std_lcov.html (标记为未执行的两个函数定义行,即使这些函数中的行被完全覆盖,以及函数Hit =函数Total - 1).
来自lcov的源文件的函数统计信息:http:// gints.dyndns.info/heap_std_lcov_func(显示两个相同的构造函数定义,两者都引用文件中的相同代码行,其中一行标记为命中5次,另一行0次).
如果我查看中间的lcov .info文件:http://gints.dyndns.info/lcov_coverage_filtered.info.txt我看到有两个构造函数定义,两者都应该在同一行:FN:8 ,_ZN4BBOS8Heap_stdC1Ev&FN:8,_ZN4BBOS8Heap_stdC2Ev.
哦,并不介意.uic包含/析构函数周围的混乱,这只是处理gcov报告的析构函数中的分支的一种肮脏方式?当我拍摄这些文件快照时,我碰巧尝试了.
有人建议如何解决这个问题?C++编译器在这里做了一些"幕后"的魔术吗?(特殊目的的构造函数的额外副本,我应该确保从我的测试中调用,也许?)常规函数定义怎么样 - 即使主体已经过全面测试,定义行怎么能不被测试?这只是lcov的一个问题吗?欢迎提出任何建议 - 我想了解为什么会发生这种情况,如果真的有一些功能我的测试没有被发现,而Cobertura没有抱怨......或者如果没有,我如何让lcov明白这一点?
编辑:在下面添加最小的repro方案
lcov_repro_one_bad.cpp:
#include <stdexcept>
class Parent {
public:
Parent() throw() { }
virtual void * Do_stuff(const unsigned m) throw(std::runtime_error) =0;
};
class Child : public Parent {
public:
Child() throw();
virtual void * Do_stuff(const unsigned …Run Code Online (Sandbox Code Playgroud) 我的代码中包含一些日志记录宏,内容如下:
#define LOG_MSG (pri, msg, ... ) \
if (pri > PriorityLevel ) \
printf( msg, ##\__VA_ARGS__);
Run Code Online (Sandbox Code Playgroud)
我知道我可以使用LCOV_EXCL_START,LCOV_EXCL_STOP或LCOV_EXCL_LINE来禁止分支。但这仅在我将其调用LOG_MSG的每个位置添加时才起作用:
LOG_MSG(ERROR, "An Error has occurred\n");//LCOV_EXCL_LINE
我想在宏中包含该注释,但是如果我将其放在其中,LCOV将无法识别它。例如,此代码仍会产生分支。
#define LOG_MSG (pri, msg, ... ) \
if (pri > PriorityLevel ) \
printf( msg, ##\__VA_ARGS__);//LCOV_EXCL_LINE
Run Code Online (Sandbox Code Playgroud)
有没有一种好的方法可以抑制宏本身中的这些分支?
我的项目结构类似:
\n\n\xe2\x94\x9c\xe2\x94\x80\xe2\x94\x80 CMakeLists.txt\n\xe2\x94\x9c\xe2\x94\x80\xe2\x94\x80 src\n\xe2\x94\x82\xc2\xa0\xc2\xa0 \xe2\x94\x9c\xe2\x94\x80\xe2\x94\x80 logic.cpp\n\xe2\x94\x82\xc2\xa0\xc2\xa0 \xe2\x94\x94\xe2\x94\x80\xe2\x94\x80 logic.h\n\xe2\x94\x94\xe2\x94\x80\xe2\x94\x80 test\n \xe2\x94\x9c\xe2\x94\x80\xe2\x94\x80 CMakeLists.txt\n \xe2\x94\x94\xe2\x94\x80\xe2\x94\x80 logic_test.cpp\nRun Code Online (Sandbox Code Playgroud)\n\n主要CMakeLists.txt文件是:
cmake_minimum_required (VERSION 2.8)\nproject (Logic)\nset (Logic_SOURCES ${PROJECT_SOURCE_DIR}/src/logic.cpp)\ninclude_directories (${PROJECT_SOURCE_DIR}/src)\nadd_library (logic SHARED ${Logic_SOURCES})\nadd_subdirectory (test)\nRun Code Online (Sandbox Code Playgroud)\n\n对于CMakeLists.txt测试来说是:
find_package (GTest)\nset (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -O0 -g -march=native -mtune=native -fprofile-arcs -ftest-coverage")\nset (CMAKE_EXE_LINKER_FLAGS "-fprofile-arcs -ftest-coverage")\nset (Test_SOURCES ${Logic_SOURCES} ${PROJECT_SOURCE_DIR}/test/logic_test.cpp)\nadd_executable (logic_test ${Test_SOURCES})\ntarget_link_libraries (${TestName} gtest gtest_main gcov pthread)\nRun Code Online (Sandbox Code Playgroud)\n\n为了处理测试覆盖率报告,我已将自定义目标添加到test/CMakeLists.txt:
set (Coverage_REPORT ${PROJECT_BINARY_DIR}/coverage.info)\nset (Coverage_DIR ${PROJECT_BINARY_DIR}/coverage)\nadd_custom_command (\n OUTPUT ${Coverage_REPORT}\n COMMAND lcov -q -c -f -b . -d ${PROJECT_BINARY_DIR}/test …Run Code Online (Sandbox Code Playgroud) 我在为我的一个项目生成覆盖率报告时遇到了麻烦-似乎从未触及到分支之后子进程中的行,尽管它们显然是现实的。
这是分叉部分的整体报告(结果与lcov + genhtml相同)和构建日志。
该项目使用带有libtool的自动工具进行构建,并将所有内容打包为静态库。(configure.ac,库makefile.am,测试makefile.am)
我尝试将覆盖率标志添加到测试和--coverageCFLAGS中,但无济于事。
最让我感到困扰的是,我试图在一个简单的C文件上重现该行为,如下所示:
#include <stdio.h>
#include <unistd.h>
#include <sys/wait.h>
#include <sys/types.h>
int main(void)
{
pid_t pid;
if (!(pid = fork())) {
puts("In child");
} else {
puts("In parent");
waitpid(pid, NULL, 0);
}
return 0;
}
Run Code Online (Sandbox Code Playgroud)
通过以下shell会话:
/bin/sh ./libtool --tag=CC --mode=compile gcc -DHAVE_CONFIG_H -I. -I./src -Wall -Wextra -Wno-unused-result -Wno-missing-field-initializers -std=gnu99 -fplan9-extensions -I./include/ -I./dependencies/csptr/include/ -O0 --coverage -fprofile-arcs -ftest-coverage -g -O0 -MT test.lo -MD -MP -MF test.Tpo …Run Code Online (Sandbox Code Playgroud) lcov如何确定何时使用绝对路径和相对路径?
我有一个app目录,该目录包含我产品的每个共享库的子目录和几个二进制文件的子目录。像这样:
/home/user/app/libfoo/bar
/home/user/app/libfoo/baz
/home/user/app/libqux
/home/user/app/testsuite
/home/user/app/product
Run Code Online (Sandbox Code Playgroud)
但是,当通过lcov和运行时genhtml,目录如下所示:
/home/user/app/libqux
/home/user/app/testsuite
/home/user/app/product
bar
baz
Run Code Online (Sandbox Code Playgroud)
换句话说,共享库目录之一中的所有内容都使用相对路径,而其他所有内容都使用绝对路径。 为什么?
我对lcov和的调用genhtml非常简单:
cd ~/app
testsuite/run_tests
lcov --capture --directory . --output-file coverage.info --gcov-tool gcov-5 --no-external
genhtml coverage.info --output-directory coverage
Run Code Online (Sandbox Code Playgroud) 我有一个相当大的C++ 库测试套件,行覆盖率接近 100%,但分支覆盖率只有 55.3%。浏览 的结果lcov,似乎大多数错过的分支都可以用 C++ 的多种抛出方法来解释std::bad_alloc,例如每当std::string构造 an 时。
我问自己在这种情况下如何提高分支覆盖率,并认为如果有一个new操作符可以配置std::bad_alloc为在命中测试套件中错过的每个分支所需的分配数量后抛出,那就太好了。
我(天真地)尝试定义一个全局void* operator new (std::size_t)函数,该函数对全局进行倒计时并在到达时int allowed_allocs抛出异常。std::bad_alloc0
但这有几个问题:
new在“第一次”需要之前很难获得呼叫数量throw。我可以执行试运行来计算成功所需的调用,但是如果多个调用可能在同一行中失败,则这无济于事,例如,类似于std::to_string(some_int) + std::to_string(another_int)where every std::to_string、串联 viaoperator+以及初始分配可能会失败。new调用,因此即使我知道我的代码需要多少次调用,也很难猜测测试套件需要多少次额外调用。(更糟糕的是,Catch 有几种“详细”模式,它们会创建大量输出,而这些输出又需要内存......)您知道如何提高分支机构覆盖率吗?
同时,我发现/sf/answers/3060836831/包含一个 Python 脚本的链接,用于过滤 lcov 输出中的异常创建的一些分支。这使我的分支覆盖率达到了 71.5%,但是剩下的未命中的分支仍然很奇怪。例如,我有几个这样的 if 语句:
有四个 (?) 分支,其中一个分支未被击中 (reference_token是 a std::string)。
有谁知道这些分支意味着什么以及如何攻击它们?
我们的 SonarQube 环境详细信息如下:
\n\nSonarQube Version \xe2\x80\x93 6.7.5(LTS).\nsonar-cxx-plugin-1.1.0.jar (Community Plugin).\nRun Code Online (Sandbox Code Playgroud)\n\n使用C++ language和覆盖率均在.info & .html( generated from genhtml command) 中生成。尝试分别在 SonarQube 上上传 lcov 覆盖率.info & .html两种格式,但 \xe2\x80\x99 不起作用。
1)似乎.info & .html无法将直接基于报告上传到sonarqube中。
2)那么我应该按照此链接的指示将它们转换为xml格式 --> https://github.com/eriwen/lcov-to-cobertura-xml
\n\n3) 或者建议将 lcov 覆盖率报告上传到 Sonarqube for C++ 的最佳方法。
\n