CMake¶
Debuging¶
- Debug output:
-LAH --debug-output --trace-expand - Variable changes in cmake:
variable_watch(CMAKE_INSTALL_LIBDIR)
Dependency graph — [1]:¶
Option 1:
Option 2:
Main commands¶
add_executable(tests testmain.cpp)oradd_library(catch INTERFACE)target_compile_features(catch INTERFACE cxx_std_11)set_target_properties(myTarget PROPERTIES CXX_STANDARD 11 CXX_STANDARD_REQUIRED YES CXX_EXTENSIONS NO)
target_include_directories(catch INTERFACE ${CMAKE_CURRENT_SOURCE_DIR}/include)target_compile_definitions(tests PRIVATE CATCH_CONFIG_CONSOLE_WIDTH=60)target_link_libraries(<target> <PRIVATE|PUBLIC|INTERFACE> <item>... [<PRIVATE|PUBLIC|INTERFACE> <item>...]...)
Create proxy targets¶
Src.
find_package (libjpeg)
if (NOT TARGET libjpeg::libjpeg)
find_package (JPEG REQUIRED)
add_library (libjpeg::libjpeg INTERFACE IMPORTED)
target_link_libraries (libjpeg::libjpeg PUBLIC JPEG::JPEG)
message (STATUS "using system provided JPEG library")
else()
message (STATUS "using conan provided JPEG library")
endif()
target_link_libraries (your_project_target PRIVATE libjpeg::libjpeg)
CMake for monorepos¶
The problem¶
Sometimes the default CMake approach is too monolithic. This is especially relevant in case of monorepos (which tend to be large and include sub-project of multiple teams, which you do not want to build at all).
- For example, with the default cmake, given a monorepo, I cannot build a specific (single) sub-project. I can only build the entire repo.
- Another (even more important) consequence is that the decision as to whether to add
add_subdirectory(dependencyA)in the givenCMakeLists.txtor not, is not local. I know that my target depends ondependencyA, but I do not know (locally, in the givenCMakeLists.txt) whether it has already been included or not by a parentCMakeLists.txt. - Finally, with the default cmake approach I have to remember both: (1) target name
(to specify it in
target_link_libraries()) and (2) target path (to specify it inadd_subdirectory()). Alternatively, we could auto-generate target names based on its path, and require to remember only paths.
The goal¶
The goal is to be able to write CMakeLists in this way:
-
Adding an executable:
-
Adding a library:
-
And configure in this way:
A prototype¶
Implementation of the functions is pretty straighforward — we just need:
- to maintain a list of processed directories (
processed_paths) - and to introduce our own
depends_upon(directory)that willadd_subdirectory(directory)only if it has not yet been added in theprocessed_paths: