cmake使用

2020-10-28 11:39:34 浏览数 (1)

image.png

cmake

image.png

CMake是一个跨平台的安装编译工具,可以用简单的语句来描述所有平台的安装编译过程。

他能够输出各种各样的makefile或者project文件,能测编译器所支持的C 特性,类似UNIX下的automake。只是 CMake 的组态档取名为 CMakeLists.txt。

Cmake 并不直接建构出最终的软件,而是产生标准的建构档(如 Unix 的 Makefile 或 Windows Visual C 的 projects/workspaces),然后再依一般的建构方式使用。

这使得熟悉某个集成开发环境(IDE)的开发者可以用标准的方式建构他的软件,这种可以使用各平台的原生建构系统的能力是 CMake 和 SCons 等其他类似系统的区别之处。

使用实例

步骤一

编写 CMake 配置文件 CMakeLists.txt 。

CMakeLists.txt 实例:

代码语言:javascript复制
# 本CMakeLists.txt的project名称
# 会自动创建两个变量,PROJECT_SOURCE_DIR和PROJECT_NAME
# ${PROJECT_SOURCE_DIR}:本CMakeLists.txt所在的文件夹路径
# ${PROJECT_NAME}:本CMakeLists.txt的project名称
project(xxx)

# 获取路径下所有的.cpp/.c/.cc文件,并赋值给变量中
aux_source_directory(路径 变量)

# 给文件名/路径名或其他字符串起别名,用${变量}获取变量内容
set(变量 文件名/路径/...)

# 添加编译选项
add_definitions(编译选项)

# 打印消息
message(消息)

# 编译子文件夹的CMakeLists.txt
add_subdirectory(子文件夹名称)

# 将.cpp/.c/.cc文件生成.a静态库
# 注意,库文件名称通常为libxxx.so,在这里只要写xxx即可
add_library(库文件名称 STATIC 文件)

# 将.cpp/.c/.cc文件生成可执行文件
add_executable(可执行文件名称 文件)

# 规定.h头文件路径
include_directories(路径)

# 规定.so/.a库文件路径
link_directories(路径)

# 对add_library或add_executable生成的文件进行链接操作
# 注意,库文件名称通常为libxxx.so,在这里只要写xxx即可
target_link_libraries(库文件名称/可执行文件名称 链接的库文件名称)
步骤二

执行命令 cmake PATH 或者 ccmake PATH 生成 Makefile PATH 是 CMakeLists.txt 所在的目录。

步骤三

使用 make 命令进行编译。

CMakeList语法

cmake版本要求
代码语言:javascript复制
cmake_minimum_required( VERSION 2.8 )
工程名字

工程文件名test123,可任取

代码语言:javascript复制
project( test123)
编译模式设置
代码语言:javascript复制
IF(NOT CMAKE_BUILD_TYPE)
  SET(CMAKE_BUILD_TYPE Release)
ENDIF()
set(CMAKE_BUILD_TYPE debug)
添加依赖库

如果包含第三方库,为库形式(此处以静态库为例(.a后缀))

代码语言:javascript复制
set( DBoW3_INCLUDE_DIRS "/usr/local/include")
set( DBoW3_LIBS "/usr/local/lib/libDBoW3.a")

target_link_libraries(${PROJECT_NAME}
${DBoW3_LIBS}
)
设置编译类型
代码语言:javascript复制
add_executable(demo demo.cpp) # 生成可执行文件
add_library(common STATIC util.cpp) # 生成静态库
add_library(common SHARED util.cpp) # 生成动态库或共享库
搜索所有的 cpp 文件

aux_source_directory(dir VAR) 发现一个目录下所有的源代码文件并将列表存储在一个变量中。

代码语言:javascript复制
aux_source_directory(. SRC_LIST) # 搜索当前目录下的所有.cpp文件
add_library(demo ${SRC_LIST})
设置包含的目录
代码语言:javascript复制
include_directories(
    ${CMAKE_CURRENT_SOURCE_DIR}
    ${CMAKE_CURRENT_BINARY_DIR}
    ${CMAKE_CURRENT_SOURCE_DIR}/include
代码语言:javascript复制
设置链接库目录
代码语言:javascript复制
link_directories(
    ${CMAKE_CURRENT_SOURCE_DIR}/libs
)

Linux 下还可以通过如下方式设置包含的目录

代码语言:javascript复制
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -L${CMAKE_CURRENT_SOURCE_DIR}/libs")
设置 target 需要链接的库
代码语言:javascript复制
target_link_libraries( # 目标库
                       demo
 
                       # 目标库需要链接的库
                       # log-lib 是上面 find_library 指定的变量名
                       ${log-lib} )
指定链接动态库或静态库
代码语言:javascript复制
target_link_libraries(demo libface.a) # 链接libface.a
target_link_libraries(demo libface.so) # 链接libface.so
target_link_libraries(demo ${CMAKE_CURRENT_SOURCE_DIR}/libs/libface.a)
target_link_libraries(demo ${CMAKE_CURRENT_SOURCE_DIR}/libs/libface.so)

target_link_libraries(demo
    ${CMAKE_CURRENT_SOURCE_DIR}/libs/libface.a
    boost_system.a
    boost_thread
    pthread)
环境变量

使用环境变量

代码语言:javascript复制
 $ENV{Name}

写入环境变量

代码语言:javascript复制
 set(ENV{Name} value) # 这里没有“$”符号
预定义变量

变量

含义

PROJECT_SOURCE_DIR

工程的根目录

PROJECT_BINARY_DIR

运行 cmake 命令的目录,通常是 ${PROJECT_SOURCE_DIR}/build

PROJECT_NAME

返回通过 project 命令定义的项目名称

CMAKE_CURRENT_SOURCE_DIR

当前处理的 CMakeLists.txt 所在的路径

CMAKE_CURRENT_BINARY_DIR

target 编译目录

CMAKE_CURRENT_LIST_DIR

CMakeLists.txt 的完整路径

CMAKE_CURRENT_LIST_LINE

当前所在的行

CMAKE_MODULE_PATH

定义自己的 cmake 模块所在的路径,SET(CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/cmake),然后可以用INCLUDE命令来调用自己的模块

EXECUTABLE_OUTPUT_PATH

重新定义目标二进制可执行文件的存放位置

LIBRARY_OUTPUT_PATH

重新定义目标链接库文件的存放位置

参考

CMakeLists.txt的超傻瓜手把手教程(附实例源码) CMakeLists.txt 语法介绍与实例演练

0 人点赞