如何强制 cmake 在没有完整路径的情况下使用 cl.exe

How do I force cmake to use cl.exe without full path?

本文关键字:情况下 exe cl 路径 cmake 何强制      更新时间:2023-10-16

我正在构建一个使用 CMake 的开源项目(kst,v2.0.8)。我正在使用 CMake v2.8.12.2 和 MSVC 2008 作为编译器,并正在生成 NMake makefile 以在命令行上构建它。我可以通过此设置成功构建它。这些版本是强制性的,因此我目前无法使用更高版本的 CMake 或 MSVC。

我需要能够使用 HP 的 Fortify 对 kst 进行源代码分析,并且能够从命令行使用它,它以两种方式之一工作:

  1. 非接触模式,它创建自己的"cl.exe",在通往实际 cl 的路径之前设置路径.exe因此在构建过程中启动。

  2. 将生成文件中的编译器设置为 Fortify 命令行,例如 sourceanalyzer -b build_id cl而不是cl.

无论哪种方式,我都需要强制 cmake 生成的编译器到其 makefile 中,使其成为 cmake 不会自动检测到的东西。

我尝试在运行 cmake 时按照此问题中的相同方法设置编译器,但 cmake 仍然坚持将 MSVC cl.exe 的完整路径放在 makefile 中。

cmake -DCMAKE_C_COMPILER=cl -DCMAKE_C_COMPILER_FORCED=ON -DCMAKE_CXX_COMPILER=cl -DCMAKE_CXX_COMPILER_FORCED=ON -DCMAKE_BUILD_TYPE=Debug -DCMAKE_INSTALL_PREFIX=%CFITSIO_DIR% -G"NMake Makefiles" ..cfit3250

我还尝试将编译器设置为调用 Fortify,但是当 cmake 测试编译器时,它失败了,说它找不到编译器。(我也尝试过没有 FORCED=ON 参数,在这种情况下,它说编译器失败。

cmake -DCMAKE_C_COMPILER="sourceanalyzer -b %BUILDID% cl" -DCMAKE_C_COMPILER_FORCED=ON -DCMAKE_CXX_COMPILER="sourceanalyzer -b %BUILDID% cl" -DCMAKE_CXX_COMPILER_FORCED=ON -DCMAKE_BUILD_TYPE=Debug -DCMAKE_INSTALL_PREFIX=%CFITSIO_DIR% -G"NMake Makefiles" ..cfit3250

我可能会搜索并替换 makefile 中的所有编译器调用,但我必须记住在每个 cmake 之后都这样做,而且看到有多个项目/生成文件/调用 cl(而不是在 makefile 中定义 CC 变量)会很乏味。我宁愿有一种方法让 cmake 直接从偏移量使用所需的编译器。

更新:测试表明,至少在某些平台上,最初建议的方法没有按预期工作。似乎使用包装器脚本可能是要走的路。

如果您确实想强制使用特定的编译器并绕过 CMake 的编译器检查,则 CMakeForceCompiler 模块可能就是您正在寻找的。指向 CMake 文档的链接包含一个简单的工具链文件示例,该示例显示了如何使用作为没有路径的简单命令调用的特定编译器。不幸的是,CMake 仍然将其转换为绝对路径,因此仅靠它本身,这并不能解决您的问题。但是,您可以使用工具链文件指向包装器脚本,并使用CMakeForceCompiler绕过编译器检查。这种组合应该会产生您要求的行为,但请注意,CMakeForceCompiler现已弃用。

请注意,在使用 CMakeForceCompiler 模块时,您需要承担更多责任来告知 CMake 信息,特别是您要强制使用的特定编译器的编译器 ID,但从 CMake 文档中似乎很清楚,这在您的情况下MSVC

若要使用工具链文件,请使用指向您自己的自定义工具链文件的-DCMAKE_TOOLCHAIN_FILE=path/to/file选项调用 CMake。CMake 文档有一个特定的部分涵盖了工具链的使用,尽管它确实掩盖了一些重要的细节。

正如@Tsyvarev的评论中提到的,使用包装器脚本可能是处理此问题的最佳方法。该包装器脚本只需要将调用转发到通常的编译器命令,而无需指定路径。然后,您负责确保在执行生成时命令将位于 PATH 上。像下面这样简单的东西应该足以作为 Windows 上的包装批处理文件(未经测试):

cl %*

现在,您可以控制Visual Studio编译器或Fortify是否完全由构建看到的PATH调用。就个人而言,我认为这有点脆弱,但这是你所要求的。;)

作为更强大的替代方案,是否可以使用两个完全独立的构建?如果是这样,那么我建议将其作为更好的选择。像往常一样使用默认的Visual Studio编译器构建一个,对于另一个构建,请使用工具链文件指向Fortify编译器,以使CMake绕过其编译器检查。这样,您就不会依赖于以特定方式设置的构建环境。