CMake究竟是如何运作的?

时间:2013-07-08 11:10:16

标签: cmake

我不是仅仅为自己问这个问题。我希望这个问题可以作为许多喜欢我的新手的参考,发现它对于如此小的CMakeLists.txt文件

后面幕后究竟发生了什么感到非常困惑。
cmake_minimum_required (VERSION 2.6)
project(Tutorial)
add_executable(Tutorial tutorial.cpp)

和这么小的tutorial.cpp

int main() { return 0; } 

生成的文件太多了

CMakeCache.txt  cmake_install.cmake  Makefile
CMakeLists.txt  tutorial.cpp

以及包含如此多文件和文件夹的CMakeFiles文件夹

CMakeCCompiler.cmake               CMakeOutput.log    Makefile.cmake
cmake.check_cache                  CMakeSystem.cmake  progress.marks
CMakeCXXCompiler.cmake             CMakeTmp           TargetDirectories.txt
CMakeDetermineCompilerABI_C.bin    CompilerIdC        Tutorial.dir
CMakeDetermineCompilerABI_CXX.bin  CompilerIdCXX
CMakeDirectoryInformation.cmake    Makefile2

不了解幕后发生的事情(即:为什么文件必须生成以及它们的目的是什么),是能够学习CMake的最大障碍。

如果有人知道,你能为后人解释吗?这些文件的目的是什么,当我键入cmake .时,cmake在构建项目之前的配置和生成究竟是什么?

3 个答案:

答案 0 :(得分:76)

秘诀在于您无需了解生成的文件的作用。

CMake在构建系统中引入了很多复杂性,如果你用它来构建复杂的软件项目,大多数都会得到回报。

好消息是,CMake很好地避免了很多这种混乱:使用out-of-source builds,你甚至不必查看生成的文件。如果你到目前为止没有这样做(我想是这样的,因为你写了cmake .),请在继续之前检查它们。使用CMake混合构建和源目录非常痛苦,而不是系统应该如何使用。

简而言之:而不是

cd <source_dir>
cmake .

始终使用

cd <build_dir_different_from_source_dir>
cmake <source_dir>

代替。我通常在源目录中使用一个空的子文件夹build作为构建目录。

为了减轻您的痛苦,让我快速概述一下CMake生成的相关文件:

  • 项目文件/ Makefile - 您真正感兴趣的内容:在所选生成器下构建项目所需的文件。这可以是从Unix Makefile到Visual Studio解决方案的任何内容。
  • CMakeCache.txt - 这是一个持久的键/值字符串存储,用于在运行之间缓存值。存储在此处的值可以是库依赖项的路径,也可以是是否构建可选组件。变量列表与运行ccmakecmake-gui时看到的变量列表大致相同。这可能会不时用于查看,但我建议尽可能使用上述工具更改任何值。
  • 生成的文件 - 这可以是从自动生成的源文件到导出宏的任何内容,可帮助您将构建的项目与其他CMake项目重新集成。其中大部分只是按需生成,不会出现在一个简单的项目中,例如你问题中的项目。
  • 其他任何都会让构建系统感到高兴。特别是,我从不需要关心CMakeFiles子目录中发生的任何事情。

一般情况下,你不应该搞乱CMake为你生成的任何文件。所有问题都可以在CMakeLists.txt内以某种方式解决。只要结果按预期构建您的项目,您可能就好了。不要太担心血腥的细节 - 因为这是CMake首先试图饶恕你的。

答案 1 :(得分:11)

如其网站所述:

  

Cmake是一个跨平台的开源构建系统,用于使用独立于编译器的方法管理软件的构建过程

在大多数情况下,它用于生成项目/生成文件 - 在您的示例中,它生成了Makefile,用于构建您的软件(主要在Linux / Unix平台上)。

Cmake允许提供跨平台构建文件,这些文件将为特定编译/平台生成特定于平台的项目/ make文件。

例如,您可以尝试使用Visual Studio在Windows上编译软件,然后在您可以启动的CMakeLists.txt文件中使用正确的语法

cmake .

在Windows平台上的项目目录中,Cmake将生成所有必要的项目/解决方案文件(.sln等)。

如果您想在Linux / Unix平台上构建软件,只需转到您拥有CMakeLists.txt文件的源目录并触发相同的cmake .,它将生成所需的所有文件。您可以通过简单的makemake all来构建软件。

在这里,您可以对关键的Cmake功能进行一些非常好的演示http://www.elpauer.org/stuff/learning_cmake.pdf

修改

如果您想制作平台相关的库包含/变量定义等,可以在CMakeLists.txt文件中使用此语法

IF(WIN32)
   ...do something...
 ELSE(WIN32)
   ...do something else...
 ENDIF(WIN32)

还有很多命令可以阻止构建失败,Cmake会通知你,例如你没有增强库filesystemregex安装在您的系统上。为此,您可以使用以下语法:

find_package(Boost 1.45.0 COMPONENTS filesystem regex)

检查它是否会为适当的系统/ IDE /编译器生成makefile。

答案 2 :(得分:0)

对于开发人员来说,CMake的确切工作方式是一个问题,因此在此无法回答。

但是,在何时使用CMake以及何时需要担心其工作原理方面,我们可以提供一些有用的指导。我也不喜欢“哦,它才行”的答案-因为,尤其是在软件中,“永远都行不通”,而您总是必须在某些时候深入细节。

CMake是一种工业实力工具。它自动执行了几个非常复杂的过程,并考虑了许多您可能不知道的变量,特别是作为一个相当新的开发人员,他可能仅对CMake可以处理的所有操作系统和构建工具有所了解。生成这么多文件的原因以及看上去如此复杂的原因是因为所有其他这些系统都是复杂的,必须加以考虑和自动化。此外,还有工具的“缓存”和其他省时功能的问题。了解CMake中的所有内容将意味着了解这些构建工具和OS中的所有内容以及这些变量的所有可能组合,这是您无法想象的。

重要的是要注意,如果您不负责管理大型跨平台构建系统,并且您的代码库是几个KLOC,也许最多100KLOG,那么使用CMake似乎有点像使用100,000美元林业树木清除机可以从2英尺乘2英尺的花园中清除杂草。 (顺便说一句,如果您从未见过这样的机器,那么您应该在youtube上找到它,这真是太棒了)

如果您的构建系统又小又简单,则最好手动编写自己的makefile或自己编写脚本。当makefile变得笨拙或需要在另一个平台上构建系统版本时,可以切换到CMake。到那时,您将有很多问题需要解决,您可以提出更集中的问题。同时,请阅读一些有关CMake的精彩书籍,甚至更好的是自己写一本书! 8)