【cmake】cmake应用:安装和打包

news2025/8/16 18:41:58

【cmake】cmake应用:安装和打包

在本系列前序的文章中已经介绍了CMake很多内容,在CMake应用:CMakeLists.txt完全指南一文中简略介绍了安装和打包,本文会更加深入地介绍CMake的安装和打包功能。

  • 【cmake】cmake应用:安装和打包
    • 一 安装
      • 1 install命令
        • DESTINATION
        • CONFIGURATIONS
        • PERMISSIONS
          • 设置安装目标的权限,接受的参数是一个权限关键字列表,比如:
      • 2 安装构建目标
      • 3 安装目录
        • TYPE/DESTINATION
        • FILES_MATCHING
        • PATTERN/REGEX
      • 4 安装文件
      • 5 自定义安装脚本
      • 6 执行安装
    • 二 打包
      • 1 CPack
      • 2 CMake打包相关的内置变量
    • 三 实践
      • 1 构建脚本

在本系列前序的文章中已经介绍了CMake很多内容,在CMake应用:CMakeLists.txt完全指南一文中简略介绍了安装和打包,本文会更加深入地介绍CMake的安装和打包功能。

本文主要介绍以下几个方面的内容:

  • 安装库文件、可执行文件和所需要对外提供的头文件
  • 将需要安装的文件打包成压缩包
  • 编译构建脚本编写

本文会先介绍相关命令和知识点,如果想先实践,可直接跳到最后一部分。

一 安装

1 install命令

安装使用install命令,用于指定一个项目的安装规则。其命令格式如下:

install(TARGETS <target>... [...])
install({FILES | PROGRAMS} <file>... [...])
install(DIRECTORY <dir>... [...])
install(SCRIPT <file> [...])
install(CODE <code> [...])
install(EXPORT <export-name> [...])

以上命令概述显示install命令可以安装的目标类型:构建目标、文件、程序、目录等,对应的关键字后面跟上对应要安装的目标。

安装不同的目标的时候,有一些通用的关键字,下面着重介绍几个最常使用的。

DESTINATION

很好理解,就是安装对象的目标安装路径,可以是绝对路径,也可以是相对路径,如果是相对路径,则认为是相对于CMAKE_INSTALL_PREFIX的,所以可以配置CMAKE_INSTALL_PREFIX指定安装目录。

因为cpack并不支持绝对路径,所以建议还是不要使用绝对路径,当然,除非这是开发者自己确切的目的。

CONFIGURATIONS

为不同的配置设置不同的安装规则。假如对Debug和Release两个配置不同的安装路径,代码示例如下:

install(TARGETS target
        CONFIGURATIONS Debug
        RUNTIME DESTINATION Debug/bin)
install(TARGETS target
        CONFIGURATIONS Release
        RUNTIME DESTINATION Release/bin)

PERMISSIONS

设置安装目标的权限,接受的参数是一个权限关键字列表,比如:
install(TARGETS target
        RUNTIME PERMISSIONS OWNER_READ OWNER_WRITE OWNER_EXECUTE)

2 安装构建目标

安装构建目标的命令格式为:

install(TARGETS static_lib shared_lib exe
            RUNTIME DESTINATION bin
            LIBRARY DESTINATION lib
            ARCHIVE DESTINATION lib)

命令第一个参数TARGETS指定需要安装的构建目标的列表,可以是静态库文件、动态库文件、可执行文件;安装时常常按照文件类型安装到不同的子目录,比如库文件放在lib目录,可执行文件放在bin目录。

针对不同文件类型,比如(RUNTIME, ARCHIVE, LIBRARY,PUBLIC_HEADER),可以分开进行配置,比如分别指定安装路径(DESTINATION)、设置文件权限(PERMISSIONS);如果不是在某个类别下的单独配置,那么就是针对所有类型。

值得一提的是,ARCHIVE一般是指静态库,LIBRARY则是指共享库,在不同平台上,略有差异,实际应用感觉不符合预期时查看一下官方文档即可,问题不大。

3 安装目录

安装一个目录,一般用于将头文件安装到目标路径。 在实际使用中,一般把需要安装的头文件放到一个特定目录下,然后直接安装整个目录即可,比如:

install(DIRECTORY "${PROJECT_SOURCE_DIR}/include/"
      DESTINATION "${CMAKE_INSTALL_INCLUDEDIR}")

更加完备的命令格式为:

install(DIRECTORY dirs...
        TYPE <type> | DESTINATION <dir>
        [FILES_MATCHING]
        [[PATTERN <pattern> | REGEX <regex>]
         [EXCLUDE] [PERMISSIONS permissions...]]

TYPE/DESTINATION

安装目录必须执行安装的目录类型TYPE或者安装的目标路径DESTINATION,但是又不可以同时指定;可以使用TYPE指定安装的目录中的文件类型,然后CMake会自动按照类型分配安装目录,不同类型对应的安装路径如下图:
在这里插入图片描述

当然,开发者也可以选择只使用DESTINATION显式指定安装的目录。

FILES_MATCHING

安装目录的时候默认会安装所有的文件,如果使用FILES_MATCHING关键字(在第一个PATTERN或者REGEX之前),则表示必须要满足对应的模式或者正则的文件才能被安装。

比如,如果目录下源文件和头文件混在一起,但是只想安装其中的头文件,则可以这样写:

install(DIRECTORY src/ DESTINATION include/
        FILES_MATCHING PATTERN "*.h")

PATTERN/REGEX

PATTERN表示文件名完全匹配才会被安装,而REGEX则是通过正则表达式匹配目标安装文件(针对目标文件的全路径);在这两个表达式后面还可以加上EXCLUDE表示反选,或者使用PERMISSIONS指定匹配的目标文件的权限。

4 安装文件

和安装目录类似,只不过是安装的是文件列表,核心的参数也是类似的;需要使用TYPE指定文件类型,自行推断安装目录,或者使用DESTINATION显式指定安装目录。命令格式为:

install(<FILES|PROGRAMS> files...
        TYPE <type> | DESTINATION <dir>

FILESPROGRAMS的不同之处在于文件的默认权限,前者是一般文件,而后者为可执行文件,默认有可执行权限,包括:OWNER_EXECUTE,GROUP_EXECUTE和WORLD_EXECUTE。

5 自定义安装脚本

使用install命令还可以在安装的时候执行自定义的脚本,使用的命令格式为:

install([[SCRIPT <file>] [CODE <code>]]
        [COMPONENT <component>] [EXCLUDE_FROM_ALL] [...])

SCRIPT指定安装时需要执行的脚本;CODE指定的是CMake的命令,也在安装期间执行,比如:

install(CODE "MESSAGE(\"Sample install message.\")")

6 执行安装

在构建编译完成之后,可以使用命令执行安装:

cmake --build . --target install
# 或者针对make构建工具
make install

更加优雅的方法是在cmake3.15版本往后,使用cmake --install命令:

cmake --install . --prefix "../output"

--install指定构建目录;--prefix指定安装路径,覆盖安装路径变量CMAKE_INSTALL_PREFIX

二 打包

1 CPack

要使用打包功能,需要执行include(CPack)启用相关的功能。

include(CPack)会在构建路径(Build tree)下生成两个cpack的配置文件,CPackConfig.cmakeCPackSourceConfig.cmake,其实也就对应了两个构建目标:packagepackage_source

配合cpack命令,使用-G参数指定生成器,常用的有ZIPTGZ7Z等,可以同时指定多个,格式也是CMake语法中的列表,例如其默认值"STGZ;TGZ";–config参数可以指定打包配置文件,比如:

cpack -G TGZ --config CPackConfig.cmake
cpack -G TGZ --config CPackSourceConfig.cmake

当然也可以使用cmake命令:

cmake --build . --target package
cmake --build . --target package_source

如果使用make作为构建工具,可以简单地执行:

make package
make package_source

2 CMake打包相关的内置变量

打包的内容就是install命令安装的内容,以目标打包(CPackConfig.cmake)为例,主要的相关变量有:

变量含义
CPACK_GENERATOR打包使用的压缩工具,比如"ZIP";cpack命令的-G参数会覆盖此设置
CPACK_OUTPUT_CONFIG_FILE配置文件,默认为CPackConfig.cmake
CPACK_OUTPUT_FILE_PREFIX打包安装的路径前缀。如果是相对路径,则是相对于构建目录
CPACK_INSTALL_PREFIX打包压缩包的内部目录前缀
CPACK_PACKAGE_FILE_NAME打包压缩包的名称,由CPACK_PACKAGE_NAME、CPACK_PACKAGE_VERSION、CPACK_SYSTEM_NAME三部分构成

需要特别注意的是:以上变量的设置需要在include(CPack)语句之前。

Before including this CPack module in your CMakeLists.txt file, there are a variety of variables that can be set to customize the resulting installers.

其中CPACK_PACKAGE_NAME默认为项目名称,CPACK_PACKAGE_VERSION默认为项目版本号,它们的默认值都是对应project命令所设置的值;但是如果没有指定版本号,则会是CMake的默认值。

假如: CPACK_OUTPUT_FILE_PREFIX设置为/usr/local/packageCPACK_INSTALL_PREFIX设置为RealCoolEngineerCPACK_PACKAGE_FILE_NAME设置为CMakeTemplate-1.0.0; 那么执行打包文件的生成路径为:

/usr/local/package/CMakeTemplate-1.0.0.zip

解压这个包得到的目标文件则会位于路径下:

/usr/local/package/CMakeTemplate-1.0.0/RealCoolEngineer/

对于源文件打包,相关的变量名基本是对应地以CPACK_SOURCE_开头,细节可以查看官方文档。

三 实践

本文仍以开源项目:https://gitee.com/RealCoolEngineer/cmake-template为例,本文对应的commit id为:5713908。

在项目根目录中的CMakeLists.txt文件中,使用安装和打包的语句为:

# Install
install(TARGETS math demo
        RUNTIME DESTINATION bin
        LIBRARY DESTINATION lib
        ARCHIVE DESTINATION lib
        PUBLIC_HEADER DESTINATION include)
file(GLOB_RECURSE MATH_LIB_HEADERS src/c/math/*.h)
install(FILES ${MATH_LIB_HEADERS} DESTINATION include/math)

# Package
set(CPACK_GENERATOR "ZIP")
set(CPACK_SET_DESTDIR ON)  # 支持指定安装目录
set(CPACK_INSTALL_PREFIX "RealCoolEngineer")
include(CPack)

安装打包的内容为项目构建目标可执行文件demo,静态库math,以及math库对应的头文件。

1 构建脚本

为了方便,笔者通常将构建的命令编写为脚本,在脚本内指定文件的安装、打包的目标目录(CMake参数)。

下面针对cmake-template的一个示范,将目标文件安装并打包到项目根目录下的output目录:

#!/bin/bash

set -euf -o pipefail

BUILD_DIR="cmake-build"
INSTALL_DIR=$(pwd)/output
rm -rf "${BUILD_DIR}"


# Configure
BUILD_TYPE=Debug
cmake -B "${BUILD_DIR}" \
    -DCMAKE_INSTALL_PREFIX="${INSTALL_DIR}" \
    -DCMAKE_BUILD_TYPE=${BUILD_TYPE} \
    -DCPACK_OUTPUT_FILE_PREFIX="${INSTALL_DIR}"

# Build
cmake --build "${BUILD_DIR}"

cd "${BUILD_DIR}"
# Test
make test CTEST_OUTPUT_ON_FAILURE=TRUE GTEST_COLOR=TRUE
# GTEST_COLOR=TRUE ctest --output-on-failure

# Install
# cmake --build . --target install
# cmake --install . --prefix "../output" # After cmake 3.15
make install

# Package
# cmake --build . --target package
make package

cd -

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/14838.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

分享500道我在“金九银十”收集的Java架构面试题

前段时间&#xff0c;字节跳动官方就发布消息称在武汉扩招至5000人&#xff0c;放出了2000个岗位名额。可见&#xff0c;互联网大厂岗位需求仍然奇缺。 在已经过去的“金九银十”&#xff0c;我有许多朋友就已经成功的跳槽&#xff0c;有的还在家等候下一步的面试通知。我托朋…

【计算机扫盲】计算机的基础操作你知多少?

计算机的高级操作 控制面板 ​ 控制面板&#xff08;control panel&#xff09;是Windows图形用户界面的一部分&#xff0c;可通过开始菜单访问。它允许用户查看并操作基本的系统设置&#xff0c;比如添加/删除软件&#xff0c;控制用户帐户&#xff0c;更改辅助功能选项。 …

CAS号:60535-02-6,二肽Met-Trp

血管紧张素-1转换酶(ACE)非竞争性抑制剂IC₅₀9.8 μM。 编号: 154290中文名称: 二肽Met-Trp英文名: Met-TrpCAS号: 60535-02-6单字母: H2N-MW-OH三字母: H2N-Met-Trp-COOH氨基酸个数: 2分子式: C16H21N3O3S1平均分子量: 335.42精确分子量: 335.13等电点(PI): 6.11pH7.0时的净电…

服装连锁店管理系统 服装连锁店如何高效管理 服装连锁店管理怎么走捷径

服装连锁店管理繁杂&#xff0c;难以把控&#xff0c;好在有“捷径”可走。 开服装连锁店的老板&#xff0c;来看看这是不是你的“头痛”日常&#xff1a; 新品上市&#xff0c;加盟店全上了&#xff0c;但无法迅速判断出畅销品和滞销品&#xff0c;搜集数据速度慢&#xff0c;…

Coursera自动驾驶1.4——车辆建模

文章目录一、运动学建模&#xff08;二维&#xff09;1.坐标系转换2.两轮机器人运动学建模3.两轮自行车运动学建模&#xff08;1&#xff09;后轴参考点&#xff08;2&#xff09;前轴参考点&#xff08;3&#xff09;重心参考点二、基本动力学模型&#xff08;2D&#xff09;1…

中台和微服务有什么区别?

中台不就是微服务吗&#xff1f;这种说法实际上混淆了中台与微服务的定义&#xff0c;要说清楚这个问题&#xff0c;就要先了解&#xff0c;什么是中台&#xff1f;什么是微服务&#xff1f;中台和微服务之间有什么样的关系&#xff1f; 什么是中台 来自阿里官方的定义&#x…

【强化学习】TensorFlow2实现DQN(处理CartPole问题)

文章目录1. 情景介绍2. DQN&#xff08;Deep Q Network&#xff09;核心思路&#xff1a;3. DQN算法流程4. 代码实现以及注释5. 实验结果文章阅读预备知识&#xff1a;Q Learning算法的基本流程、TensorFlow2多层感知机的实现。1. 情景介绍 CartPole问题&#xff1a;黑色小车上…

【并发编程五】c++进程通信——信号量(semaphore)

【并发编程五】c进程通信——信号量&#xff08;semaphore&#xff09;一、概述二、信号量三、原理四、过程1、进程A过程2、进程B过程五、demo1、进程A2、进程B六、输出七、windows api介绍1. 创建信号量 CreateSemaphore()2. 打开信号量 OpenSemaphore()3. 等待 WaitForSingle…

一种基于IO口的模拟串口(LOG)实现方法

一、使用背景 当MCU的串口不够用时&#xff0c;可以通过IO模拟的方式将任意一个具有输出功能的管脚配置为串口输出&#xff0c;从而方便开发和调试。 二、实现原理 通过IO口模拟串口发送波形&#xff0c;配置对应的波特率等信息&#xff0c;然后映射printf函数&#xff0c;从…

基于粒子群优化算法的冷热电联供型综合能源系统运行优化(Matlab代码实现)

&#x1f468;‍&#x1f393;个人主页&#xff1a;研学社的博客 &#x1f4a5;&#x1f4a5;&#x1f49e;&#x1f49e;欢迎来到本博客❤️❤️&#x1f4a5;&#x1f4a5; &#x1f3c6;博主优势&#xff1a;&#x1f31e;&#x1f31e;&#x1f31e;博客内容尽量做到思维缜…

redis 支持的数据类型

Redis 数据库支持五种数据类型。 字符串&#xff08;string&#xff09; 哈希&#xff08;hash&#xff09; 列表&#xff08;list&#xff09; 集合&#xff08;set&#xff09; 有序集合&#xff08;sorted set&#xff09; 位图 ( Bitmaps ) 基数统计 ( HyperLogLogs ) 字…

Vue3.2 + Element-Plus 二次封装 el-table(Pro版)

前言 &#x1f4d6; ProTable 组件目前已是 2.0版本&#x1f308;&#xff0c;在 1.0版本 中大家提出的问题与功能优化&#xff0c;目前已经得到优化和解决。 &#x1f600; 欢迎大家在使用过程中发现任何问题或更好的想法&#xff0c;都可以在下方评论区留言&#xff0c;或者我…

【计算机网络】局域网体系结构、以太网Ethernet详解

注&#xff1a;最后有面试挑战&#xff0c;看看自己掌握了吗 文章目录局域网LAN决定局域网的要素网络拓扑传输介质局域网的分类以太网令牌环网FDDI网----Fiber Distributed Data InterfaceATM网---Asynchronous Transfer Mode无线局域网WLAN----Wireless Local Area NetworkMAC…

Red Hat Enterprise Linux (RHEL) 9 更新了哪些新特性?

文章目录1. 前言2. 软件3. 支持的硬件架构4. GNOME更新到40版5. 安全和身份6. 构建容器的通用基础镜像7. 改进了用于管理 RHEL 9 的 Cockpit Web 控制台1. 前言 体验一下最新的rhel 9.0 是什么感觉。它会飞吗&#xff1f; Red Hat Enterprise Linux (RHEL) 9现已普遍可用 (GA…

吃柿子的禁忌靠谱吗?

图片来源&#xff1a;pixabay 秋冬是柿子上市的季节&#xff0c;虽然柿子并不是苹果、香蕉这样的大宗水果&#xff0c;但是秋天不吃个柿子&#xff0c;冬天不吃个柿饼&#xff0c;总觉得少了点什么。 关于吃柿子有很多禁忌&#xff0c;比如说柿子不能与螃蟹同时吃&#xff0c;柿…

​怎么保留硬盘数据合并分区 ,如何才能合并且不丢失数据

硬盘分区合并是比较常见的操作&#xff0c;​怎么保留硬盘数据合并分区&#xff0c;还是具有一定的难度。因为在Windows操作系统中&#xff0c;用户可以通过磁盘管理来实现硬盘分区合并&#xff0c;但是要删除该磁盘分区右侧的相邻分区&#xff0c;但是对于部分不懂计算机的用户…

Tailscale的子网路由和出口节点

2 年前&#xff0c;老苏写了 『 外网访问群晖的新方案Tailscale 』&#xff0c;第一次隆重的给大家推荐了 Tailscale&#xff0c;但当时还有很多功能并不具备&#xff0c;比如今天要介绍的 Subnet Router 和 Exit Node 【特别说明】&#xff1a;老苏使用的是DSM6 &#xff0c;所…

RabbitMQ初步到精通-第一章-消息中间件介绍

第一章 消息中间件介绍 1.MQ概述 MQ全称是Message Queue&#xff0c;消息的队列&#xff0c;因为是队列&#xff0c;所以遵循FIFO 先进先出的原则&#xff0c;它是一种跨进程的通信机制&#xff0c;用于上下游传递消息。 在互联网架构中&#xff0c;MQ是一种非常常见的上下游“…

论文阅读笔记 | 三维目标检测——VeloFCN算法

如有错误&#xff0c;恳请指出。 文章目录paper&#xff1a;《Vehicle Detection from 3D Lidar Using Fully Convolutional Network》 对于64线激光雷达全范围扫描出来的点云进行特征图的构建。对于具体的点&#xff08;xyz坐标&#xff09;&#xff0c;其在水平方向上可以通…

一个是证书服务和web安全访问配置,一个是PGP的使用

一个是证书服务和web安全访问配置&#xff0c;一个是PGP的使用 IIS介绍 IIS是本机自带的服务&#xff0c;用于上线web网页&#xff1b;虽然是自带但因为非开发人员用不到&#xff0c;所以属于预安装&#xff1b;在本机搜索下载即可&#xff0c; 打开后 证书服务&#xff0c;认…