我将从你的最后一个问题开始:
如果这不可行或不利于 CMake 理念,那么在 cmake 命令行中执行等效操作的最简单方法是什么?换句话说,我该如何处理像 cmake 这样的东西-DCFG_TEST ...
并取得通过的结果-DCFG_TEST
给编译器?
Think a little有点在盒子外面。 CMake 是一个构建系统发电机。配置 CMake 后,就可以很容易地生成所需数量的构建系统。您可以生成两个构建系统:一个用于“正常”模式,另一个用于“测试”模式:
cmake -S srcs -B build_normal
cmake -S srcs -B build_test -DCMAKE_CXX_FLAGS="-DCFG_TEST"
要将其作为宏传递给编译器,请使用add_compile_definitions or target_compile_definitions. Ex.
target_compile_definitions(my_target PUBLIC "CFG_TEST=${CFG_TEST}")
我想说这是在 CMake 中做事的一种非常“惯用”的方式。权衡成本是两个构建系统及其工件的磁盘空间成本,但好处是能够并排使用它们:您可以使用一个,然后快速使用另一个,而无需切换标志并重新配置 +重建。
话虽如此,为了回答你最初的问题,
如何将简单的 #define 传递到 C/C++ 编译器而无需重新运行 CMake?这还有道理吗?
我不确定你所要求的是否可能 - 至少与Unix Makefiles
生成器,并且无需构建修改后的 CMake 可执行文件。
编写Makefile时,您可以指定变量并像这样使用它们$(foo)。据我所知,CMake 生成的 Makefile 没有任何可供用户使用并插入编译命令的“自由浮动”变量。
例如,我在我的机器上生成了一个 Unix Makefiles 构建系统的一个非常小的 CMake 项目,在其目标生成的文件中有一行CMakeFiles/example.dir/build.make
像这样的文件:
/usr/bin/c++ $(CXX_DEFINES) $(CXX_INCLUDES) $(CXX_FLAGS) -S /.../test.cpp -o CMakeFiles/example.dir/test.cpp.s
并且标志被生成到目标的CMakeFiles/example.dir/flags.make
像这样:
CXX_DEFINES = ...
CXX_INCLUDES = ...
CXX_FLAGS = ...
这些东西的价值来自于诸如CMAKE_CXX_FLAGS, target_compile_options, target_compile_definitions, etc.
因此,当调用生成的构建系统时,请执行以下操作如何将宏定义从“make”命令行参数(-D)传递到C源代码?,从技术上来说你可以做这样的事情:
make CXX_FLAGS=-DCFG_TEST
or (see the cmake --build命令文档为了什么 ”--
“ 方法):
cmake --build <build_dir> -- CXX_FLAGS=-DCFG_TEST
但这将覆盖您告诉 CMake 为生成的任何值CXX_FLAGS
Makefile 变量,所以如果你真的想这样做,你需要复制完整生成的值CXX_FLAGS
然后在命令行上使用它的粘贴以及您想要添加的任何内容覆盖它,以避免丢失任何内容。
如果您想插入自己的 Makefile 变量“槽”而不是覆盖生成的变量,例如CXX_DEFINES
, CXX_INCLUDES
, and CXX_FLAGS
,我很确定您需要构建并安装 CMake 的修改版本。要修改的相关文件是cmMakefileTargetGenerator::WriteObjectRuleFiles
in the 源/cmMakefileTargetGenerator.cxx.
如果您决定修改已配置的构建系统的变量缓存并在重建之前重新生成它(老实说,这可能根本不是什么大问题(就所花费的时间而言),具体取决于项目的具体情况),您可以使用 CMake 缓存编辑工具,例如ccmake or cmake-gui,然后运行配置命令,然后调用构建系统。或者看有没有一种安全的方法可以从命令行编辑缓存变量?(TL;DR 您也可以使用-D争论)。您要么正在编辑CMAKE_CXX_FLAGS
变量或类似变量,或者您自己定义的变量,然后用作编译定义,例如target_compile_definitions(<target_name> <visibility> "<name_of_your_cache_variable>=${<name_of_your_cache_variable>}")
.