CMake is a very complicate program worth writing a book about it. But like you, I’ve no time to know every detail of CMake. So I prepare this minimal tutorial for you to use CMake to build existing projects that may be downloaded from github, etc.
If you are used to building programs in Linux/Unix, you must be familiar with the following building steps:
cd src ./configure make make install
The configure step generates the Makefile, the make step compiles/links the executable with the Makefile, and the “make install” step installs the generated executables to some directory on your system.
Using CMake, the build steps would be:
mkdir build cd build cmake srcdir cmake --build . cmake --install .
The “cmake srcdir” corresponds to the “configure” step. The “cmake –build .” corresponds to the “make” step, and “cmake –install .” corresponds to the “make install” step. Note the cmake does shadow build(out of source build). You execute “cmake srcdir” in some directory; the build intermediate files and final executables will be saved in that directory, which makes the source directory clean. You can also run the following command in any directory to configure:
cmake -S sourcedirectory -B builddirectory
This will save all build intermediate files and final executables to builddirectory.
A practical configuration step includes the installation directory which specifies where to install the build results for the later “cmake –install .” command.
cmake -S sourcedirectory -B builddirectory -DCMAKE_INSTALL_PREFIX=installdirectory
CMake is often accompanied by ninja which likes the make command. To use ninja, CMake should not generate Makefile but build.ninja. build.ninja for ninja is just like Makefile for make. The build steps for ninja are:
cmake -G ninja -S sourcedirectory -B builddirectory -DCMAKE_INSTALL_PREFIX=installdirecroty cd builddirectory ninja ninja install
You can see ninja works just like make. Note the CMake term generator(-G ninja option) is used to instruct CMake what kind of makefile(Makefile or build.ninja, or other kinds of file) to generate.
You may wonder if CMake builds the debug version or the release version of program by default. By default, CMake will build debug version of application. But you can tell CMake to build release version as follows:
cmake -G ninja -S sourcedirectory -B builddirectory -DCMAKE_INSTALL_PREFIX=installdirecroty -DCMAKE_BUILD_TYPE=Release cd builddirectory ninja ninja install
Use -DCMAKE_BUILD_TYPE=Release
to build release version and use -DCMAKE_BUILD_TYPE=Debug
to build debug version. However, the CMAKE_BUILD_TYPE CMake option only works for single-configuration generator such as ninja. For multi-configuration generators such “Ninja Multi-Config“, you should specify debug/release in build step, not in configure step:
cmake -G "Ninja Multi-Config" -S sourcedirectory -B builddirectory -DCMAKE_INSTALL_PREFIX=installdirecroty cd builddirectory ninja -f build-Debug.ninja ninja install
For other multi-config generators, you can use the following command to specify debug/release in build step:
cmake --build . --config Debug
The mostly encountered problems you build a project with CMake is that some packages are not found. This is caused by the following statement in CMakeLists.txt(the main build config file of your project, under the project top directory) or xxx.cmake(the cmake config file for sub-projects the main project depends on, in the cmake sub-directory):
find_package(xxx REQUIRED) find_package(yyy CONFIG REQUIRED)
To solve this problem, first install the required package, then set the package installation directory before the find_package command:
SET(xxx_DIR, "xxx installation directory")