通过cmakelist生成与调用C++动态链接库

文章目录

  • 前言
  • 生成动态链接库
    • 样例项目说明
    • 修改cmakelist
  • 调用动态链接库
    • 修改配置文件
    • 修改原来外层的CMakeLists.txt
  • 总结


前言

此前有写过用编译工具链直接通过命令行的方式生成与调用C++动态链接库的方法,本文记录下通过cmake来实现so的生成。


生成动态链接库

样例项目说明

以下笔者通过具体的开源项目代码进行演示。
在这里插入图片描述

通过以上项目的层级结构,我们可以看到有两个CMakeLists.txt。
其中外层CMakeLists.txt内容为:

# Copyright (c) Huawei Technologies Co., Ltd. 2021. All rights reserved.
  
# 最低CMake版本
cmake_minimum_required(VERSION 3.5.1)

# 项目名
project(HelmetIdentification)

# 配置环境变量MX_SDK_HOME,如:/home/xxxxxxx/MindX_SDK/mxVision,可在远程环境中用指令env查看
set(MX_SDK_HOME $ENV{MX_SDK_HOME})

if (NOT DEFINED ENV{MX_SDK_HOME})
    set(MX_SDK_HOME "/usr/local/Ascend/mindx_sdk")
    message(STATUS "set default MX_SDK_HOME: ${MX_SDK_HOME}")
else ()
    message(STATUS "env MX_SDK_HOME: ${MX_SDK_HOME}")
endif()

add_subdirectory("./src")

src中的CMakeLists.txt内容为:

# CMake lowest version requirement
cmake_minimum_required(VERSION 3.5.1)
# project information
project(Individual)

# Compile options
add_definitions(-D_GLIBCXX_USE_CXX11_ABI=0 -Dgoogle=mindxsdk_private)
add_compile_options(-std=c++11 -fPIC -fstack-protector-all -Wall -D_FORTIFY_SOURCE=2 -O2)

set(CMAKE_RUNTIME_OUTPUT_DIRECTORY  "../../")
set(CMAKE_CXX_FLAGS_DEBUG "-g")
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -Wl,-z,relro,-z,now,-z,noexecstack -s -pie -pthread")
set(CMAKE_SKIP_RPATH TRUE)

SET(CMAKE_BUILD_TYPE "Debug")
SET(CMAKE_CXX_FLAGS_DEBUG "$ENV{CXXFLAGS} -O0 -Wall -g2 -ggdb")
SET(CMAKE_CXX_FLAGS_RELEASE "$ENV{CXXFLAGS} -O3 -Wall")

# Header path
include_directories(
    ${MX_SDK_HOME}/include/
    ${MX_SDK_HOME}/opensource/include/
    ${MX_SDK_HOME}/opensource/include/opencv4/
    /home/HwHiAiUser/Ascend/ascend-toolkit/latest/include/
    ./
)

# add host lib path
link_directories(
    ${MX_SDK_HOME}/lib/
    ${MX_SDK_HOME}/lib/modelpostprocessors
    ${MX_SDK_HOME}/opensource/lib/
    ${MX_SDK_HOME}/opensource/lib64/
    /usr/lib/aarch64-linux-gnu/
    /home/HwHiAiUser/Ascend/ascend-toolkit/latest/lib64/
    /usr/local/Ascend/driver/lib64/
    ./
)


aux_source_directory(. sourceList)

add_executable(main ${sourceList})

target_link_libraries(main mxbase opencv_world boost_filesystem glog avformat avcodec avutil cpprest yolov3postprocess ascendcl acl_dvpp_mpi)

install(TARGETS main DESTINATION ${CMAKE_RUNTIME_OUTPUT_DIRECTORY})

项目的主要目的是把src中的main.cpp文件编译成可执行文件输出到指定的地址。我们需要做的是把除main.cpp以外的文件编译成一个so,通过so来编译main.cpp,而不是通过源码的方式。(为了方便,我下面实现的时候把main.cpp也打包进了so)

修改cmakelist

src中的cmakelist,将原来:

aux_source_directory(. sourceList)

add_executable(main ${sourceList})

target_link_libraries(main mxbase opencv_world boost_filesystem glog avformat avcodec avutil cpprest yolov3postprocess ascendcl acl_dvpp_mpi)

install(TARGETS main DESTINATION ${CMAKE_RUNTIME_OUTPUT_DIRECTORY})

修改为:

aux_source_directory(. sourceList)

# add_executable(main ${sourceList})

add_library(ai_detection310 SHARED ${sourceList})

target_link_libraries(ai_detection310 mxbase opencv_world boost_filesystem glog avformat avcodec avutil cpprest yolov3postprocess ascendcl acl_dvpp_mpi)

install(TARGETS ai_detection310 DESTINATION ${CMAKE_RUNTIME_OUTPUT_DIRECTORY})

在这里插入图片描述

编译运行后将会得到ai_detection310.so

调用动态链接库

修改配置文件

将生成的ai_detection310.so移动台指定的位置,为了方便我在原来的同级目录下,新建了test_so的文件夹,把需要用的文件都复制了过来,结构如下:
在这里插入图片描述
其中test_so中的CMakeLists.txt为src中的文件的拷贝,然后再对test_so中的CMakeLists.txt进行修改:
将CMakeLists.txt中:

aux_source_directory(. sourceList)

# add_executable(main ${sourceList})

add_library(ai_detection310 SHARED ${sourceList})

target_link_libraries(ai_detection310 mxbase opencv_world boost_filesystem glog avformat avcodec avutil cpprest yolov3postprocess ascendcl acl_dvpp_mpi)

install(TARGETS ai_detection310 DESTINATION ${CMAKE_RUNTIME_OUTPUT_DIRECTORY})

修改为:

include_directories(${PROJECT_SOURCE_DIR}/include/)

message(STATUS "Include directories: ${PROJECT_SOURCE_DIR}")

add_executable(main ${PROJECT_SOURCE_DIR}/main.cpp)

target_link_libraries(main mxbase opencv_world boost_filesystem glog avformat avcodec avutil cpprest yolov3postprocess ascendcl acl_dvpp_mpi)

target_link_libraries(main ${PROJECT_SOURCE_DIR}/lib/libai_detection310.so)

install(TARGETS main DESTINATION ${CMAKE_RUNTIME_OUTPUT_DIRECTORY})

修改原来外层的CMakeLists.txt

将原来外层CMakeLists.txt中:

add_subdirectory("./src")

修改为:

add_subdirectory("./test_so")

编译运行后将会得到main的可执行文件。


总结

通过cmake进行so编译还是比较简单的,主要是用add_library(ai_detection310 SHARED ${sourceList})生成so替换原来add_executable(main ${sourceList})生成的可执行文件,然后对main.cpp进行配置,能够正确调用生成的so。这样我们就实现了通过cmakelist生成与调用C++动态链接库。
如果阅读本文对你有用,欢迎一键三连呀!!!
2024年5月14日16:25:40在这里插入图片描述

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

C++指针和动态内存分配细节,反汇编,面试题05

文章目录 20. 指针 vs 引用21. new vs malloc 20. 指针 vs 引用 指针是实体,占用内存空间,逻辑上独立;引用是别名,与变量共享内存空间,逻辑上不独立。指针定义时可以不初始化;引用定义时必须初始化。指针的…

Java 对象序列化

序列化:把对象转化为可传输的字节序列过程称为序列化。 反序列化:把字节序列还原为对象的过程称为反序列化 序列化的作用是方便存储和传输,细节可参考如下文章: 序列化理解起来很简单 - 知乎序列化的定义 序列化:把对…

代码随想录训练营Day38、39:Leetcode509、70、746、62、63

Leetcode509: 问题描述: 斐波那契数 (通常用 F(n) 表示)形成的序列称为 斐波那契数列 。该数列由 0 和 1 开始,后面的每一项数字都是前面两项数字的和。也就是: F(0) 0,F(1) 1 F(n) F(n -…

什么是MVC?什么是SpringMVC?什么是三层架构?

文章目录 应用分层什么是MVC?什么是 SpringMVC?三层架构三层架构和MVC的关系 应用分层 在讲解什么是MVC之前,先来理解一下什么是应用分层。 应用分层是一种软件开发设计思想,将应用程序划分成N个层次,每个层次都分别负责自己的…

本地安装nvm,管理多版本node

先卸载本地的nodejs(14.16.1) 卸载的直接可以点击win10图标→设置→应用→应用和功能 卸载nodejs即可 2. 安装nvm,地址:https://github.com/coreybutler/nvm-windows/releases 安装目录时尽量不要出现特殊字符还有空格,否则会在nvm use xxx的…

mysql实现隔离性——锁

锁主要解决写-写问题,mvcc用来解决读-写问题 MyISAM不使用行级锁,主要使用表锁 MyISAM存储引擎主要使用表锁(table-level locking),并不支持行级锁(row-level locking)。当MyISAM存储引擎执行…

OpenCV人脸识别,报错缺少haarcascade_frontalface_default.xml文件解决方案(随手记)

使用pip安装的opencv库可能会缺少进行人脸识别的haarcascade_frontalface_default.xml等文件。 可以通过github直接进行下载,再放到需要使用的python文件目录下 单击连接,github人脸识别库-link 找到对应需要的xml文件,这里我举例为haarcas…

01软件下载安装和P解

凯哥英语视频 软件下载安装和P解 凯哥英语视频1.官网直接下,专业版安装不会有人不会吧实在下载不到就去我这百度云吧结语 1.官网直接下,专业版 点击前往逛网下载https://www.jetbrains.com/pycharm/ 下载专业版,奶茶外卖都能点,只…

《企业科技与发展》是什么级别的期刊?是正规期刊吗?

问题解答 问:《企业科技与发展》期刊怎么样? ​答:企业科技与发展》(月刊)1985年创刊,由广西科学技术厅主管、广西科学技术情报研究所主办,国内外公开发行。主要栏目:科技对策与研究、企业科技…

优化Mac系统,TinkerTool一键掌控!

TinkerTool System for Mac是一款专为Mac用户设计的系统设置维护工具。这款软件不仅具备执行系统维护任务的能力,如管理文件和调整系统或用户设置,还包含一系列功能强大的工具,旨在帮助用户解决、修复、排除故障或修复系统错误和损坏的帐户等…

大企业总部与分部组网方案

在全球化的经济环境中,大企业往往设有总部和多个地理分散的分部。为了确保信息的快 速流通、资源的优化配置以及管理的高效运作,构建一个稳定、安全且高效的组网方案显 得尤为重要。本文将探讨大企业如何通过技术手段和管理策略,实现总部与分…

Python专题:十三、日期和时间(2)

datetime 模块 today()函数 date类型 year month day

用suno创作歌曲音乐的8个技巧

导读 Suno Ai可以将文本转化为高度逼真的音乐和语音。 该系统包括多种音乐风格,如电影、RAP、翻唱等,并提供了多语言和不同性别的播音员选择。 用户可以使用命令来生成音频并进行个性化设置。 用suno.ai所生成的歌曲质量非常高,而且完美支…

http代理有什么作用?

HTTP代理在网络环境中扮演着重要角色,同时具有多种作用,包括加速网络访问、提高安全性、突破地域限制、访问控制和安全、访问授权和监控、突破IP限制、访问内部资源、充当防火墙以及节省IP资源等。 接下来,为大家详细介绍: 加速网…

Linux使用脚本删除多个版本的jar包

问题描述:在进行测试的过程中发现,有一个导出xls文件的功能,文件正常到导出来了,但是页面上显示的是中文,但是导出来的xls文件取的确是数据库的存值,没有转换 前端一看代码说没问题,那没办法重…

pycharm如何有效读取到win10设置的环境变量

参考链接: 参考文章 该参考文章的第一种方法:设置win10环境变量。 在设置完环境变量后,在pycharm终端上不能有效读取到刚刚设置的环境变量的,需要启动win的cmd,在项目路径下执行脚本。如下所示的对比: cm…

chorme浏览器或者edge浏览器使用开发者模式

本篇文章主要讲解edge,因为它内核是chorme,还可以使用微软账号同步,谷歌翻译也凉凉了,edge还可以用翻译,推荐国内windows用户用它。 打开开发者模式 直接按F12点击右上角三个点...,点击更多工具&#xff…

基于Vue3+ElementPlus项目,复制文字到剪贴板功能实践指南,揭秘使用js-tool-big-box工具库的核心优势

在前端开发项目中,很多时候有那么一个场景,就是要求将一段文案复制下来,这段文案可能是一串很长的id,可能是一条命令语句,可能是一小段文案,复制到剪贴板上。这样有利于用户复制到其他地方去,使…

RuoYi-Vue-Plus (Logback 和 logback-plus.xml 、p6spy)

项目后本地日志 一、logback依赖 打开最外层的 pom.xml,查看 SpringBoot的依赖配置。 <dependencyManagement><dependencies><!-- SpringBoot的依赖配置--><dependency><groupId>org.springframework.boot</groupId><artifactId>s…

国外新闻媒体推广:多元化媒体分发投放-大舍传媒

前言 &#xff1a;随着全球化的进程&#xff0c;国外新闻市场呈现出快速发展的趋势。在这个趋势下&#xff0c;国外新闻媒体推广成为了各行业企业宣传业务的重要一环。本文将重点介绍大舍传媒的多元化媒体分发投放服务&#xff0c;以及对国外新闻媒体推广的意义。 1. 多元化媒…