Disons que j'ai un projet de test unitaire C++ utilisant cmake comme ceci:
$ tree
.
├── C-API-ConditionVariable-unit-test
│ ├── C-API-ConditionVariable-compile-link-test.c
│ ├── C-API-ConditionVariable-unit-test-0.cpp
│ └── C-API-ConditionVariable-unit-test-1.cpp
├── C-API-Mutex-unit-test
│ ├── C-API-Mutex-compile-link-test.c
│ ├── C-API-Mutex-unit-test-0.cpp
│ └── C-API-Mutex-unit-test-1.cpp
├── some
│ └── deeply
│ └── nested
│ └── path
│ └── SomeFeature-unit-test
│ ├── SomeFeature-compile-link-test.c
│ ├── SomeFeature-unit-test-0.cpp
│ └── SomeFeature-unit-test-1.cpp
└── CMakeLists.txt
Chaque fichier source des sous-dossiers crée un exécutable distinct. J'aimerais que chaque sous-dossier du projet soit un module non autonome, c'est-à-dire que chaque sous-dossier est (plus ou moins) autonome, mais n'est PAS un projet autonome de cmake pouvant être compilé séparément. J'aimerais pouvoir ne construire que tout ou rien. Par exemple, je ne veux pas donner l’impression que vous pouvez exécuter cmake uniquement à partir de some/deeply/nested/path/SomeFeature-unit-test
Pour ne construire que cela.
Quelle option devrais-je choisir?
CMakeLists.txt
Fichier dans chaque sous-dossier + add_subdirectory()
au niveau supérieur CmakeLists.txt
;some-random-name.cmake
Dans chaque sous-dossier + include()
au plus haut niveau CmakeLists.txt
;CMakeLists.txt
, les fichiers cmake supplémentaires uniquement en tant qu'aides (macros, fonctions, ...);La première option est la plus pratique, mais elle suggère que chaque sous-dossier est en fait un projet autonome pouvant être compilé séparément.
La deuxième option semble clairement suggérer qu’il n’ya qu’un seul projet cmake ici. Mais dans chaque some-random-name.cmake
Dans les sous-dossiers, je dois utiliser le chemin d'accès complet aux fichiers sources, ce qui va à l'encontre de mon désir que chacun d'eux soit autonome. S'il n'y a qu'un seul niveau d'imbrication (comme pour les deux premiers exemples de sous-dossiers), c'est bon, mais pour some/deeply/nested/path/SomeFeature-unit-test
, Ce n'est pas très gentil. Je devrais aussi préfixer les noms des fichiers de sortie.
La troisième option semble être un moyen facile de créer rapidement un fichier CMakeLists.txt
Avec une longueur de spaghetti, il est donc possible que je préfère autre chose.
Je voudrais savoir quelle est la voie "préférée" dans un projet cmake "moderne". Tous les tutoriels que j'ai pu trouver pour un projet multi-répertoires traitent du cas où il y a une bibliothèque autonome dans un dossier, une application autonome utilisant cette bibliothèque dans un autre dossier et des tests autonomes utilisant la même bibliothèque dans un autre répertoire. En regardant les projets utilisant cmake, je ne vois aucune cohérence, cela n'aide donc pas beaucoup.
(Je suis un cmake noob, essayant de convertir un projet relativement volumineux pour utiliser cmake)
La règle la plus couramment utilisée est "Un CMakeLists.txt
Par cible". Donc, votre option n ° 1.
Pour ce faire, votre structure de projet devra peut-être s'adapter si "chaque fichier source des sous-dossiers crée un exécutable séparé".
Et la racine CMakeLists.txt
Est votre point de départ et contient la commande project()
.
Il est important de noter que
add_subdirectory()
et CMakeLists.txt
Dans son environnement de construction généré.add_subdirectory()
( la grande différence avec l'utilisation de la commande include()
) )Ce que vous devriez éviter, c'est d'avoir à référencer des fichiers source à partir d'autres sous-répertoires avec quelque chose comme ../some_other_dir/some_other_source.cpp
. Cela montre que votre structure CMake n'est pas configurée conformément à la règle générale citée ci-dessus.
Extraits de documentation
CMake: add_subdirectory()
commande
Ajouter un sous-répertoire à la construction. Le
source_dir
Spécifie le répertoire dans lequel se trouvent la sourceCMakeLists.txt
Et les fichiers de code.
Lorsqu'un projet a la structure complexe et comprend un ou plusieurs sous-répertoires (racine et sous-répertoires du projet), vous pouvez créer des fichiers de sous-répertoire
CMakeList.txt
. Les fichiers de sous-répertoireCMakeLists.txt
Décrivent les règles de construction, de contenu et de cible d'un sous-répertoire.
C++ Now 2017: Daniel Pfeifer "Effective CMake: une sélection aléatoire de meilleures pratiques
Les répertoires contenant un
CMakeLists.txt
Constituent le point d'entrée du générateur de système de génération. Des sous-répertoires peuvent être ajoutés avecadd_subdirectory()
et doivent également contenir unCMakeLists.txt
.
Références