从 cmake 生成的命令中取消设置 cppcheck 分析中的定义

Posted

技术标签:

【中文标题】从 cmake 生成的命令中取消设置 cppcheck 分析中的定义【英文标题】:Unset define in cppcheck analyze from cmake generated command 【发布时间】:2020-07-17 11:04:24 【问题描述】:

我有使用 cppcheck 1.90 检查的项目,但我想取消设置几个定义,因为检查所有定义需要很长时间。

例如:tests.cpp:

int main() 
  int x,y;
#ifdef A
  x = 5;
#else
  x = 10;
#endif

#ifdef B
  y = 5;
#else
  y = 10;
#endif

#ifdef C
  y = 5*x;
#else
  y = 10*x;
#endif

  int c = x+y;

当我使用没有项目的文件时 - 没有问题:

cppcheck ../tests.cpp --force -UB
Checking ../tests.cpp ...
Checking ../tests.cpp: A...
Checking ../tests.cpp: C...

我取消定义 B - 并且 cppcheck 不检查 B 的编译路径。 但是如何处理从 cmake 项目生成的文件呢?

cmake ../ -DCMAKE_EXPORT_COMPILE_COMMANDS=ON
cppcheck --project=./compile_commands.json --force -UB
Checking /home/builder/bugs/test_cppcheck/tests.cpp ...
Checking /home/builder/bugs/test_cppcheck/tests.cpp: A...
Checking /home/builder/bugs/test_cppcheck/tests.cpp: B...
Checking /home/builder/bugs/test_cppcheck/tests.cpp: C...

我可以看到 cppcheck 被忽略“-U”键。在这种情况下有什么方法可以取消定义吗?

为测试示例添加cmakefile:

CMakeLists.txt
cmake_minimum_required(VERSION 3.6)

project(tests)

set(SRC
    tests.cpp
)

set(NAME test)
add_executable($NAME $SRC)

【问题讨论】:

你试过设置 C++ 标志吗? CMakeLists 文件set(CMAKE_CXX_FLAGS "-D*your_flags*"),发布您的 CMakeLists 文件可能会有所帮助。 这是cppcheck 的问题,您很可能]应该报告他们的错误。 @joepol,谢谢!但最好取消定义! 【参考方案1】:

您可以选择只编辑一次 CMakeLists 文件并根据需要传递参数,为此您应该

在 CMakeLists 文件中添加:

set(CMAKE_CXX_FLAGS "$CMAKE_CXX_FLAGS *hard_coded_flags*")

命令行:

从命令行调用cmake 时,添加CMAKE_CXX_FLAGS = -UB=1(或任何其他cppcheck 标志),这会将-UB=1 连接到hard_coded_flags

【讨论】:

【参考方案2】:

另一种方法是让cmake 自己运行cppcheck。这可以通过设置CMAKE_CXX_CPPCHECK 来完成(参见documentation)。您可以在CMakeLists.txt 中设置CMAKE_CXX_CPPCHECK,也可以在调用cmake 的命令行中设置它。

这确实有一些缺点(例如,每个源文件都是单独检查的,所以跨文件检查不起作用)。

但有几个优点:

无需单独调用cppcheck。 如果您在CMakeLists.txt 中设置CMAKE_CXX_CPPCHECK,您还可以添加cppcheck 命令行选项来控制它的作用。在您的情况下,您可以添加 -UB。 这有助于将有关如何构建和检查项目的所有知识封装到一个文件中 (CMakeLists.txt)。

我通常在我的CMakeLists.txt 中遵循类似这样的模式:

option(ENABLE_CODE_ANALYSIS "Run code analysis" OFF)
if(ENABLE_CODE_ANALYSIS)
    find_program(cppcheck cppcheck)
    message(STATUS "cppcheck    $cppcheck")
    if(NOT (cppcheck MATCHES "NOTFOUND"))
        set(CMAKE_CXX_CPPCHECK "$cppcheck"
            "--enable=all"
            "--inconclusive"
            "--inline-suppr"
            "--quiet"
            "--suppress=missingInclude"
            "--suppress=unmatchedSuppression"
            "--suppress=unusedFunction"
            "--template='file:line: warning: id (severity): message'")
    endif()
endif(ENABLE_CODE_ANALYSIS)

然后就可以通过cmake -DENABLE_CODE_ANALYSIS=ON进行代码分析了。

【讨论】:

【参考方案3】:

一个可能的决定是更改 CMakeLists 文件(取消定义):

cmake_minimum_required(VERSION 3.6)
project(tests)
set(SRC
    tests.cpp
)
set(CMAKE_CXX_FLAGS "-UB=1")
set(NAME test)
add_executable($NAME $SRC)

输出是:

$ cmake ../ -DCMAKE_EXPORT_COMPILE_COMMANDS=ON
-- Configuring done
-- Generating done
-- Build files have been written to: /home/builder/bugs/test_cppcheck/build
$ cppcheck --project=./compile_commands.json --force
Checking /home/builder/bugs/test_cppcheck/tests.cpp ...
Checking /home/builder/bugs/test_cppcheck/tests.cpp: A...
Checking /home/builder/bugs/test_cppcheck/tests.cpp: C...

没有“B”路径检查。 但是,如果存在不改变 CMakeLists 的解决方案 - 它会更好。

【讨论】:

以上是关于从 cmake 生成的命令中取消设置 cppcheck 分析中的定义的主要内容,如果未能解决你的问题,请参考以下文章

从命令行在CMake项目上设置MSVC运行时

cmake 在Windows 命令行怎么指定编译器

cmake怎么取消cuda

CMAKE_INSTALL_PREFIX如何设置默认值,并且保留从命令行覆盖的能力?

CMake学习笔记一

使用 cmake 从命令行使用 /MT 标志编译