CMake如何工作?


157

我不仅要问我一个人。我希望这个问题能为像我这样的许多新手提供参考,他们发现对于这么小的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配置和生成的确切内容是什么?


1
我知道源代码外的版本。如果任何人都没有进行源代码外的构建,并且仍在寻找清除生成的文件的方法,则此技术效果很好:stackoverflow.com/a/12055610/453673
2013年

3
aosabook.org/en/cmake.html上有不错的描述,并且可能是对问题的深入解答(在此不能简要介绍)。
parasrish

@SebTu断开的链接。cmake.html页面不存在。
导航

3
@Nav Yap,弄乱了标记语法,很抱歉。因此,这里是更正后的版本:对于不熟悉cmake的人们,我真的建议阅读cmake的体系结构。它提供了足够的信息,可以让您感觉到cmake的工作原理,而又不会失去细节。
SebNag

Answers:


92

秘密在于您不必了解生成的文件的功能。

CMake在构建系统中引入了很多复杂性,只有当您将其用于构建复杂的软件项目时,其中的大多数才能物有所值。

好消息是,CMake很好地避免了您的麻烦:使用源代码外的构建,您甚至不必查看生成的文件。如果您到目前为止还没有这样做(我想是这样,因为您已经写过cmake .),请在进行操作之前先检查一下。在CMake中,将构建目录和源目录混合在一起确实很麻烦,而不是应该如何使用系统。

概括地说:

cd <source_dir>
cmake .

总是使用

cd <build_dir_different_from_source_dir>
cmake <source_dir>

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

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

  • 项目文件/ Makefiles-您实际上感兴趣的是:在选定的生成器下构建项目所需的文件。从Unix Makefile到Visual Studio解决方案,任何东西都可以。
  • CMakeCache.txt-这是一个持久键/值字符串存储,用于缓存两次运行之间的值。此处存储的值可以是库依赖关系的路径,也可以是是否要构建任何可选组件的路径。变量列表与运行ccmake或时看到的变量列表基本相同cmake-gui。这对于不时查看很有用,但是我建议尽可能使用上述工具来更改任何值。
  • 生成的文件 -可以是任何内容,从自动生成的源文件到导出宏,都可以帮助您将生成的项目与其他CMake项目重新集成。其中大多数仅按需生成,不会出现在简单的项目中,例如您提出的问题。
  • 任何其他因素都足以使构建系统满意。特别是,我从不需要关心CMakeFiles子目录中正在发生的任何事情。

通常,您不应该将CMake为您生成的任何文件弄乱。所有问题都可以CMakeLists.txt以一种或另一种方式从内部解决。只要结果能按预期构建您的项目,就可以了。不必太担心血腥的细节-因为这是CMake最初要为您节省的。


谢谢。知道了源代码之外的版本,但是如您所见,提出这个问题的目的是要了解更多。答案的CMakeCache.txt部分确实有帮助。我一直在寻找这种解释。另外,我的问题的最后一句话:“ 在构建项目之前,cmake配置和生成的确切含义是什么?
Nav

1
CMakeFiles该目录包含此文件CMakeError.logCMakeOutput.log对于CMake构建故障排除很重要。
Serge Rogatch

1
有时需要在CMakeFiles/target_name.dir目录中签入的两件事是flags.makelink.txt文件。我不得不在复杂的项目中检查这些项目,该项目从上游项目继承了flags / linked-stuff。例如:我有一些错误,因为TPL A依赖于TPLB。另外,我的项目也依赖于B,我在本地安装了它。但是A使用了我系统中的B版本(而不是本地安装),该版本具有不同的启用选项,并且它排在第一位,从而导致我的项目出错。仅查看link.txt,我就能发现发生了这种情况。
bartgol

13

如其网站上所述:

Cmake是跨平台的开源构建系统,用于使用与编译器无关的方法来管理软件的构建过程

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

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

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

cmake .

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

如果您想在Linux / Unix平台上构建软件,则只需转到源目录即可,该目录中有您的CMakeLists.txt文件并触发该文件cmake .,它会生成您通过simple make或来构建软件所需的所有文件 make all

在这里,您可以很好地介绍关键的Cmake功能http://www.elpauer.org/stuff/learning_cmake.pdf

编辑

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

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

您还可以使用许多命令来防止构建失败,并且Cmake会通知您例如您没有Boost库filesystemregex已安装在系统上。为此,您可以使用以下语法:

find_package(Boost 1.45.0 COMPONENTS filesystem regex)

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


1
谢谢Patryk。有用的答案,但您链接到的pdf,大部分解释了学习CMake的第二阶段,该阶段基本上是CMake的实现。我问的是第一阶段的解释,一个人必须了解CMake到底发生了什么!
2013年

@Nav我扩大了我的答案。您仍然可以在网上搜索更多信息。
Patryk

这离回答所提问题还很遥远。
SenhorLucas

1

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

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

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

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

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

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.