Cmake
Depuis les années 2000, cmake est devenu la norme pour distribuer les projets écrits en C ou C++. A partir d’un fichier CMakeLists.txt, le logiciel est capable de générer soit un makefile pour construire le projet avec gcc ou clang, soit un fichier .sln pour construire le projet avec visual studio, ou encore un fichier .xcodeproj pour construire le projet avec Xcode. Il permet donc de constuire le projet sous differentes plateformes et évite d’avoir à maintenir plusieurs fichiers de solution logicielle séparés (.sln, makefiles, etc.).
D’autre solutions similaires ayant la même utilité que cmake existent : autotools, meson, MSBuild, scons, bazel, xmake…
Cmake s’est toutefois imposé comme standart de-facto dans le monde C/C++ aujourd’hui.
Les désavantages de Cmake est qu’il ne donne pas
autant de contrôle qu’une solution .sln ou makefile
natif. Il est surement recommandé d’être familier
avec les spécificités de make pour comprendre les
fichiers généres par Cmake.
Pour décrire la structure d’un projet, Cmake s’appuye sur un fichier CMakeLists.txt
qui peut ressembler à ca :
project(MonProjet
VERSION 1.0.2
DESCRIPTION Description du projet
LANGUAGES C OBJC
)
add_library(MaLibrairie STATIC
fichier_lib1.c
fichier_lib2.c
entete_lib.h
)
add_executable(
MonExecutable
source1.m
source2.c
source3.c
source4.c
entete1.h
entete2.h
)
target_link_libraries(MonExecutable PUBLIC MaLibrairie)
Ce fichier contient une succession de “fonctions” décrivant les constituants
du projet : ses programmes, librairies et relations entre elles. La fonction
project() décrit l’aspect général du projet, add_executable()
ajoute un exécutable avec les fichiers necessaires pour le produire,
add_library() déclare de la meme façon une librairie
(statique (.lib) ou dynamique (.so, .dll, …)). target_link_libraries() déclare une
dépendance entre deux librairies, une librairie et un executable…
Si la chose dont on dépend est modifiée, tous les executables
qui en deependent seront recompillés, dans le style des Makefile.
On peut déclarer qu’une relation soit publique ou privée, c’est à dire visible ou non de manière transitive pas les cibles qui dépendent de la cible qui dépend de la librairie.
Procédure
On utilise généralement cmake en ligne de commande, après l’avoir installé, on devrait pouvoir tapper cmake dans un terminal et avoir une message expliquant les options acceptées par la commande.
On commence par creer un dossier où l’on veut construire le projet, il peut être un sous dossier du projet ou être complètement séparé de celui-ci.
cd <le chemin du dossier où se trouve votre CMakeLists.txt>
mkdir _build
pushd _build
cmake ..
Un message d’erreur dit CMake Error: The source directory "/<chemin vers votre projet>" does not appear to contain CMakeLists.txt.
Types de build
Par defaut Cmake proposer 5 types de préréglages pour générer une solution :
Debugajoute l’option-gau compilateur, ce qui permet de l’ouvrir avecgdbet de l’exécuter pas à pas.Releaseajoute l’option-O3 -DNDEBUGqui génère du code très optimisé pour la vitesse, avec du code réagencé et des variables et fonctions élidées. Lesassertsont désactivés.MinSizeRelajoute l’option-Os -DNDEBUGoptimise le programme en mode “small” ce qui génère un résultat de petite taille, aux dépens d’optimisations de vitesse. Lesassertsont désactivés.RelWithDebInfoajoute l’option-O2 -g -DNDEBUGqui produit du code optimisé mais également le débogage pas à pas, il est possible que certaines instructions et variables soient supprimées. Cela rend également le code assembleur plus facile à lire avec les noms de symboles originaux.
Affichage verbeux
Cmake cache par défaut les commandes invoquées par le compilateur et le linker, ce qui peut rendre le debogage difficile.
Pour les afficher, il faut modifier la propriété
CMAKE_VERBOSE_MAKEFILE dans le fichier CMakeCache.txt
à TRUE.
Alternativement en ligne de commande
cmake -DCMAKE_VERBOSE_MAKEFILE:BOOL=ON .. depuis le dossier
de build.
A noter que contrairement à ce que son nom implique la verbosité augmente egalement pour les projets Visual Studio de type .sln.
Testing
Cmake vient avec une solution de testing via l’utilitaire ctest.
La documentation en est ici :
- https://gitlab.kitware.com/cmake/cmake/blob/master/Help/dev/testing.rst 🌍⤴
- https://gitlab.kitware.com/cmake/community/-/wikis/doc/ctest/Testing-With-CTest 🌍⤴
Ressources
- Gérer un large projet cmake (2016) :
🇬🇧 Enhanced source file handling with
target_sources()https://crascit.com/2016/01/31/enhanced-source-file-handling-with-target_sources/ 🌍⤴ - Une bonne explication sur la difference entre
PUBLIC, PRIVATE et INTERFACE (2023) :
🇬🇧
CMake: A Case Study - Hans Vredeveld - ACCU 2023 : https://www.youtube.com/watch?v=8l53O3FaJdM 🌍⤴
Ressources additionelles
- Site officiel : https://cmake.org 🌍⤴