{"id":1911,"date":"2025-12-04T22:50:56","date_gmt":"2025-12-04T22:50:56","guid":{"rendered":"https:\/\/jaimerios.com\/?p=1911"},"modified":"2025-12-04T22:50:57","modified_gmt":"2025-12-04T22:50:57","slug":"package-management-with-cmakes-cpm","status":"publish","type":"post","link":"https:\/\/jaimerios.com\/?p=1911","title":{"rendered":"Package management with CMake&#8217;s CPM"},"content":{"rendered":"\n<p>I&#8217;ve used <code>conan<\/code> and <code>vcpkg<\/code> with varying levels of success. Recently, I came across <a href=\"https:\/\/github.com\/cpm-cmake\/CPM.cmake\" data-type=\"link\" data-id=\"https:\/\/github.com\/cpm-cmake\/CPM.cmake\" target=\"_blank\" rel=\"noreferrer noopener\">CPM.cmake<\/a> and it works quite well with the projects I have used it in.<\/p>\n\n\n\n<p>For getting CPM.cmake in your own CMake project, you have to download the CPM.cmake code:<\/p>\n\n\n\n<div class=\"wp-block-kevinbatdorf-code-block-pro\" data-code-block-pro-font-family=\"Code-Pro-JetBrains-Mono\" style=\"font-size:.875rem;font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:1.25rem;--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)\"><span style=\"display:flex;align-items:center;padding:10px 0px 0 16px;font-size:0.8em;width:100%;text-align:left;background-color:#1E1E1E;font-style:italic;color:#D4D4D4\"><span style=\"border-bottom:1px solid rgba(234, 191, 191, 0.2)\">CMake<\/span><\/span><span role=\"button\" tabindex=\"0\" style=\"color:#D4D4D4;display:none\" aria-label=\"Copy\" class=\"code-block-pro-copy-button\"><pre class=\"code-block-pro-copy-button-pre\" aria-hidden=\"true\"><textarea class=\"code-block-pro-copy-button-textarea\" tabindex=\"-1\" aria-hidden=\"true\" readonly>project(your_project_name LANGUAGES CXX)\ncmake_minimum_required(VERSION 3.24)\n\n# Download CPM.cmake\nfile(\n  DOWNLOAD\n  https:\/\/github.com\/cpm-cmake\/CPM.cmake\/releases\/download\/v0.40.8\/CPM.cmake\n  ${CMAKE_CURRENT_BINARY_DIR}\/cmake\/CPM.cmake\n  EXPECTED_HASH SHA256=78ba32abdf798bc616bab7c73aac32a17bbd7b06ad9e26a6add69de8f3ae4791\n)\ninclude(${CMAKE_CURRENT_BINARY_DIR}\/cmake\/CPM.cmake)<\/textarea><\/pre><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" style=\"width:24px;height:24px\" fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" stroke-width=\"2\"><path class=\"with-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4\"><\/path><path class=\"without-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2\"><\/path><\/svg><\/span><pre class=\"shiki dark-plus\" style=\"background-color: #1E1E1E\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color: #569CD6\">project<\/span><span style=\"color: #D4D4D4\">(your_project_name LANGUAGES CXX)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #569CD6\">cmake_minimum_required<\/span><span style=\"color: #D4D4D4\">(VERSION 3.24)<\/span><\/span>\n<span class=\"line\"><\/span>\n<span class=\"line\"><span style=\"color: #6A9955\"># Download CPM.cmake<\/span><\/span>\n<span class=\"line\"><span style=\"color: #569CD6\">file<\/span><span style=\"color: #D4D4D4\">(<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">  DOWNLOAD<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">  https:\/\/github.com\/cpm-cmake\/CPM.cmake\/releases\/download\/v0.40.8\/CPM.cmake<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">  <\/span><span style=\"color: #569CD6\">${CMAKE_CURRENT_BINARY_DIR}<\/span><span style=\"color: #D4D4D4\">\/cmake\/CPM.cmake<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">  EXPECTED_HASH SHA256=78ba32abdf798bc616bab7c73aac32a17bbd7b06ad9e26a6add69de8f3ae4791<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #569CD6\">include<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #569CD6\">${CMAKE_CURRENT_BINARY_DIR}<\/span><span style=\"color: #D4D4D4\">\/cmake\/CPM.cmake)<\/span><\/span><\/code><\/pre><\/div>\n\n\n\n<p>The above code will download the CMake module and after that, you can bring in libraries, like Catch2:<\/p>\n\n\n\n<div class=\"wp-block-kevinbatdorf-code-block-pro\" data-code-block-pro-font-family=\"Code-Pro-JetBrains-Mono\" style=\"font-size:.875rem;font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:1.25rem;--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)\"><span style=\"display:flex;align-items:center;padding:10px 0px 0 16px;font-size:0.8em;width:100%;text-align:left;background-color:#1E1E1E;font-style:italic;color:#D4D4D4\"><span style=\"border-bottom:1px solid rgba(234, 191, 191, 0.2)\">CMake<\/span><\/span><span role=\"button\" tabindex=\"0\" style=\"color:#D4D4D4;display:none\" aria-label=\"Copy\" class=\"code-block-pro-copy-button\"><pre class=\"code-block-pro-copy-button-pre\" aria-hidden=\"true\"><textarea class=\"code-block-pro-copy-button-textarea\" tabindex=\"-1\" aria-hidden=\"true\" readonly># ---- Dependencies ----\nCPMAddPackage(\"gh:catchorg\/Catch2@3.4.0\")<\/textarea><\/pre><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" style=\"width:24px;height:24px\" fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" stroke-width=\"2\"><path class=\"with-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4\"><\/path><path class=\"without-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2\"><\/path><\/svg><\/span><pre class=\"shiki dark-plus\" style=\"background-color: #1E1E1E\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color: #6A9955\"># ---- Dependencies ----<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">CPMAddPackage(<\/span><span style=\"color: #CE9178\">&quot;gh:catchorg\/Catch2@3.4.0&quot;<\/span><span style=\"color: #D4D4D4\">)<\/span><\/span><\/code><\/pre><\/div>\n\n\n\n<p>There are examples of how to use the <code>CPMAddPackage<\/code> function call, in folder <a href=\"https:\/\/github.com\/cpm-cmake\/CPM.cmake\/tree\/master\/examples\">https:\/\/github.com\/cpm-cmake\/CPM.cmake\/tree\/master\/examples<\/a><\/p>\n\n\n\n<p>Sometimes, I found, that not all libraries set up properly without a little extra help. Here&#8217;s an example:<\/p>\n\n\n\n<div class=\"wp-block-kevinbatdorf-code-block-pro\" data-code-block-pro-font-family=\"Code-Pro-JetBrains-Mono\" style=\"font-size:.875rem;font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:1.25rem;--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)\"><span style=\"display:flex;align-items:center;padding:10px 0px 0 16px;font-size:0.8em;width:100%;text-align:left;background-color:#1E1E1E;font-style:italic;color:#D4D4D4\"><span style=\"border-bottom:1px solid rgba(234, 191, 191, 0.2)\">CMake<\/span><\/span><span role=\"button\" tabindex=\"0\" style=\"color:#D4D4D4;display:none\" aria-label=\"Copy\" class=\"code-block-pro-copy-button\"><pre class=\"code-block-pro-copy-button-pre\" aria-hidden=\"true\"><textarea class=\"code-block-pro-copy-button-textarea\" tabindex=\"-1\" aria-hidden=\"true\" readonly>CPMAddPackage(\"gh:nothings\/stb#master\")\n\nadd_library(stb INTERFACE)\ntarget_include_directories(stb INTERFACE ${stb_SOURCE_DIR})<\/textarea><\/pre><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" style=\"width:24px;height:24px\" fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" stroke-width=\"2\"><path class=\"with-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4\"><\/path><path class=\"without-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2\"><\/path><\/svg><\/span><pre class=\"shiki dark-plus\" style=\"background-color: #1E1E1E\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color: #D4D4D4\">CPMAddPackage(<\/span><span style=\"color: #CE9178\">&quot;gh:nothings\/stb#master&quot;<\/span><span style=\"color: #D4D4D4\">)<\/span><\/span>\n<span class=\"line\"><\/span>\n<span class=\"line\"><span style=\"color: #569CD6\">add_library<\/span><span style=\"color: #D4D4D4\">(stb INTERFACE)<\/span><\/span>\n<span class=\"line\"><span style=\"color: #569CD6\">target_include_directories<\/span><span style=\"color: #D4D4D4\">(stb INTERFACE <\/span><span style=\"color: #569CD6\">${stb_SOURCE_DIR}<\/span><span style=\"color: #D4D4D4\">)<\/span><\/span><\/code><\/pre><\/div>\n\n\n\n<p>The above project just brings in the header files, and I use the <code>add_library<\/code> and <code>target_include_directories<\/code> CMake functions to create an INTERFACE target that can be used by the projects that need it.<\/p>\n\n\n\n<p>Another example, which has a Config file for CMake, is:<\/p>\n\n\n\n<div class=\"wp-block-kevinbatdorf-code-block-pro\" data-code-block-pro-font-family=\"Code-Pro-JetBrains-Mono\" style=\"font-size:.875rem;font-family:Code-Pro-JetBrains-Mono,ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,monospace;line-height:1.25rem;--cbp-tab-width:2;tab-size:var(--cbp-tab-width, 2)\"><span style=\"display:flex;align-items:center;padding:10px 0px 0 16px;font-size:0.8em;width:100%;text-align:left;background-color:#1E1E1E;font-style:italic;color:#D4D4D4\"><span style=\"border-bottom:1px solid rgba(234, 191, 191, 0.2)\">CMake<\/span><\/span><span role=\"button\" tabindex=\"0\" style=\"color:#D4D4D4;display:none\" aria-label=\"Copy\" class=\"code-block-pro-copy-button\"><pre class=\"code-block-pro-copy-button-pre\" aria-hidden=\"true\"><textarea class=\"code-block-pro-copy-button-textarea\" tabindex=\"-1\" aria-hidden=\"true\" readonly>CPMAddPackage(\"gh:Dav1dde\/glad#v2.0.6\")\n\n# Bring in this folder so we get access to the glad_add_library function\nadd_subdirectory(\"${glad_SOURCE_DIR}\/cmake\" glad_cmake)\n\nglad_add_library(glad\n    REPRODUCIBLE\n    EXCLUDE_FROM_ALL\n    LOADER\n    API gl:core=4.6\n    EXTENSIONS\n        GL_ARB_bindless_texture\n        GL_EXT_texture_compression_s3tc\n)\n<\/textarea><\/pre><svg xmlns=\"http:\/\/www.w3.org\/2000\/svg\" style=\"width:24px;height:24px\" fill=\"none\" viewBox=\"0 0 24 24\" stroke=\"currentColor\" stroke-width=\"2\"><path class=\"with-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2m-6 9l2 2 4-4\"><\/path><path class=\"without-check\" stroke-linecap=\"round\" stroke-linejoin=\"round\" d=\"M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2\"><\/path><\/svg><\/span><pre class=\"shiki dark-plus\" style=\"background-color: #1E1E1E\" tabindex=\"0\"><code><span class=\"line\"><span style=\"color: #D4D4D4\">CPMAddPackage(<\/span><span style=\"color: #CE9178\">&quot;gh:Dav1dde\/glad#v2.0.6&quot;<\/span><span style=\"color: #D4D4D4\">)<\/span><\/span>\n<span class=\"line\"><\/span>\n<span class=\"line\"><span style=\"color: #6A9955\"># Bring in this folder so we get access to the glad_add_library function<\/span><\/span>\n<span class=\"line\"><span style=\"color: #569CD6\">add_subdirectory<\/span><span style=\"color: #D4D4D4\">(<\/span><span style=\"color: #CE9178\">&quot;${glad_SOURCE_DIR}\/cmake&quot;<\/span><span style=\"color: #D4D4D4\"> glad_cmake)<\/span><\/span>\n<span class=\"line\"><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">glad_add_library(glad<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    REPRODUCIBLE<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    EXCLUDE_FROM_ALL<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    LOADER<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    API gl:core=4.6<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">    EXTENSIONS<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        GL_ARB_bindless_texture<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">        GL_EXT_texture_compression_s3tc<\/span><\/span>\n<span class=\"line\"><span style=\"color: #D4D4D4\">)<\/span><\/span>\n<span class=\"line\"><\/span><\/code><\/pre><\/div>\n\n\n\n<p>So like that, you can use CPM.cmake to download dependencies into your CMake project.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>I&#8217;ve used conan and vcpkg with varying levels of success. Recently, I came across CPM.cmake and it works quite well with the projects I have used it in. For getting CPM.cmake in your own CMake project, you have to download the CPM.cmake code: The above code will download the CMake module and after that, you &#8230; <a title=\"Package management with CMake&#8217;s CPM\" class=\"read-more\" href=\"https:\/\/jaimerios.com\/?p=1911\" aria-label=\"Read more about Package management with CMake&#8217;s CPM\">Read more<\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[3,6,7,14,27],"tags":[100,522,143],"class_list":["post-1911","post","type-post","status-publish","format-standard","hentry","category-coding","category-development","category-devops","category-infrastructure","category-software-development","tag-c","tag-cmake","tag-cpp"],"_links":{"self":[{"href":"https:\/\/jaimerios.com\/index.php?rest_route=\/wp\/v2\/posts\/1911","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/jaimerios.com\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/jaimerios.com\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/jaimerios.com\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/jaimerios.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=1911"}],"version-history":[{"count":1,"href":"https:\/\/jaimerios.com\/index.php?rest_route=\/wp\/v2\/posts\/1911\/revisions"}],"predecessor-version":[{"id":1912,"href":"https:\/\/jaimerios.com\/index.php?rest_route=\/wp\/v2\/posts\/1911\/revisions\/1912"}],"wp:attachment":[{"href":"https:\/\/jaimerios.com\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=1911"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/jaimerios.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=1911"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/jaimerios.com\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=1911"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}