必须加-g -o0 --coverage:-g提供源码行号,-o0避免优化干扰,--coverage启用插桩;cmake需在cmake_cxx_flags和链接标志中均配置;.gcda运行时生成于.o所在目录,lcov --capture须指定正确路径。

编译必须加 -g -O0 --coverage,缺一不可
不加 -g,lcov 找不到源码行号,报告里全是“no data”;开优化(比如 -O2)会让函数内联、死代码被删,覆盖率统计错位甚至崩溃。有人只加 --coverage 就跑,结果 .gcda 文件为空或无法合并。
推荐命令示例:g++ -g -O0 --coverage -std=c++17 test.cpp -o test
CMake 用户注意:
- 要在
CMAKE_CXX_FLAGS和CMAKE_EXE_LINKER_FLAGS中都加入--coverage - 不要只加在
target_compile_options里漏掉链接阶段
运行测试后才能生成有效的 .gcda 文件
.gcda 是运行时生成的执行计数文件,没跑测试程序,lcov --capture 就只能扫到空数据。常见错误包括:
- 只编译、不运行可执行文件
- 运行了但工作目录不对,导致
.gcda写在别处(比如build/CMakeFiles/xxx.dir/而非源码目录) - 测试进程 crash 或被 kill,
.gcda没写完就丢失
.gcda 默认生成在 .o 所在目录,不是源码目录,也不是可执行文件所在目录。CMake out-of-source 构建时,它就在 build/ 下的中间文件夹里。
lcov --capture 必须指定正确路径,且顺序不能乱
lcov --capture 不是“扫描当前目录下的源码”,而是递归查找 .gcda 并匹配同名 .gcno。如果路径设错,它会静默跳过所有文件。
典型命令:lcov -d build/ -c -o coverage_base.info
过滤必须在 capture 之后做,且用 -r(remove),不是 -e(exclude):lcov -r coverage_base.info '/usr/*' '*/test/*' '*/third_party/*' '*/include/*' -o coverage_filtered.info
注意:
- 路径模式是 shell glob,不是正则;
*/include/*能匹配build/_deps/fmt-src/include/,但/include/*无效 - 单引号包裹通配符,防止 shell 提前展开
- header-only 库(如
fmt、catch2.hpp)的头文件路径也得加进-r列表,否则计入分母拉低覆盖率
genhtml 生成的 index.html 打不开?先看浏览器协议限制
直接双击本地生成的 index.html,Chrome/Firefox 会因 file:// 协议禁止加载内联 JS(比如搜索框、折叠逻辑),页面显示空白或只有骨架。
解决办法:
- 用 Python 快速起服务:
python3 -m http.server 8000,然后访问http://localhost:8000/coverage_report/index.html - 或者把报告目录移到 Web 服务器可访问路径下
- 别把输出目录设成和源码同名(如
src/),也别放在build/里——make clean可能顺手清掉
真正容易被忽略的是:每次重新生成报告前,最好先清旧数据。比如用 lcov --zerocounters -d build/,否则历史 .gcda 可能残留干扰新结果。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











