CMake语法复习

前言

此文总结了库的制作和一些CMake常用的一些语法。

一:创建静态库和动态库

静态库的生成和使用

CMake语法复习_第1张图片

 动态库的生成和使用

CMake语法复习_第2张图片

二:使用CMake来生成Makefile,生成可执行文件

顶层目录下的CMakeLists.txt

CMake语法复习_第3张图片

project(HELLO)
add_subdirectory(libhello)
add_subdirectory(src)

libhello目录下的CMakeLists.txt

CMake语法复习_第4张图片

set(LIBRARY_OUTPUT_PATH ${PROJECT_BINARY_DIR}/lib)
add_library(libhello hello.c)
set_target_properties(libhello PROPERTIES OUTPUT_NAME "hello")

src目录下的CMakeLists.txt

CMake语法复习_第5张图片

include_directories(${PROJECT_SOURCE_DIR}/libhello)
set(EXECUTABLE_OUTPUT_PATH ${PROJECT_BINARY_DIR}/bin)
add_executable(helloApp main.c)
target_link_libraries(helloApp libhello)

最后进入到build目录下进行cmake ../,make之后,helloApp会在build/bin目录下,libhello.a会在/build/lib目录下

CMake语法复习_第6张图片

三:list相关操作

工程文件目录

CMake语法复习_第7张图片

对list进行一些操作

cmake_minimum_required(VERSION 3.22)
project(HELLO)
add_subdirectory(src)
add_subdirectory(libhello)

set(helloList "hello world")
message(${helloList})

aux_source_directory(src list1)
message("list1 = ${list1}")

aux_source_directory(libhello list2)
message("list2 = ${list2}")

list(LENGTH helloList helloListLength)
message("helloListLength = ${helloListLength}")

list(APPEND list1 ${list2})
message("after append list1 = ${list1}")

list(GET list1 0 VAR1)
message("var1 in list1 after append = ${VAR1}")

打印结果

CMake语法复习_第8张图片

 四:头文件和库

CMake语法复习_第9张图片

CMake语法复习_第10张图片

private、interface、public三个参数的区别

CMake语法复习_第11张图片

⚫ 当使用 PRIVATE 关键字修饰时,意味着 包含目录列表仅用于当前目标;
⚫ 当使用 INTERFACE 关键字修饰时,意味着 包含目录列表不用于当前目标、只能用于依赖该目标的其它目标,也就是说 cmake 会将 包含目录列表传递给当前目标的依赖目标;
⚫ 当使用 PUBLIC 关键字修饰时,这就是以上两个的集合, 包含目录列表既用于当前目标、也会传递给当前目标的依赖目标。

target_link_libraries(hello_world INTERFACE hello):表示目标 hello_world 不需要链接 hello 库,但是对于 hello_world 目标的依赖目标(依赖于 hello_world 的目标)它们需要链接 hello 库。

五:部分变量

在src目录下的CMakeLists.txt中添加PROJECT_SOURCE_DIR、PROJECT_BINARY_DIR、CMAKE_CURRENT_SOURCE_DIR、CMAKE_CURRENT_BINARY_DIR。在build目录下进行cmake ../编译。

CMake语法复习_第12张图片

打印结果

CMake语法复习_第13张图片

可执行程序和库文件的输出路径EXECUTABLE_OUTPUT_PATH、LIBRARY_OUTPUT_PATH

六:循环语句(foreach)

foreach语句

cmake_minimum_required(VERSION 3.22)
project(HELLO)
add_subdirectory(src)
add_subdirectory(libhello)

set(myList happy qixi festival lm)
foreach(temp ${myList})
    message("${temp}")
endforeach()

foreach(temp "${myList}")
    message("${temp}")
endforeach()

CMake语法复习_第14张图片

 打印结果

CMake语法复习_第15张图片

七:数学运算math

cmake_minimum_required(VERSION 3.22)
project(HELLO)
add_subdirectory(src)
add_subdirectory(libhello)

math(EXPR RET1 "100 + 200")
math(EXPR RET2 "100 * 200")
math(EXPR RET3 "1 & 0")
message("${RET1}, ${RET2}, ${RET3}")

CMake语法复习_第16张图片

打印结果

CMake语法复习_第17张图片

八:函数(function)

通过 function()定义的函数它的使用范围是全局的,并不局限于当前源码、可以在其子源码或者父源码中被使用

function(myprintf arg1 arg2)
    message("${arg1} ${arg2}")
endfunction()

myprintf(hello world)

打印结果

CMake语法复习_第18张图片

函数内的局部变量

ARGVX X 是一个数字,譬如 ARGV0、ARGV1,ARGV0 为第一个参数、ARGV1 位第二个参数
ARGV  实际调用时传入的参数会存放在 ARGV 变量中(如果是多个参数,那它就是一个参数列表)
ARGN  假如定义函数时参数为 2 个,实际调用时传入了 4 个,则 ARGN 存放了剩下的 2 个参数(如果是多个参数,那它也是一个参数列表)
ARGC 调用函数时,实际传入的参数个数
cmake_minimum_required(VERSION 3.22)
project(HELLO)
add_subdirectory(src)
add_subdirectory(libhello)
 
function(myprintf arg1 arg2)
    message("ARGC = ${ARGC}")
    message("ARGV = ${ARGV}")
    message("ARGN = ${ARGN}")
    message("ARGV0 = ${ARGV0}")
 
    set(i 0)
    foreach(var ${ARGV})
        message("var${i} = ${var}")
        math(EXPR i "${i} + 1")
    endforeach()
    
endfunction()
 
myprintf(hello world impressive)

打印结果

CMake语法复习_第19张图片

九:文件操作(file)

WRITE 文件不存在就新建一个文件,如果文件存在就覆盖写
APPEND 在文件末追加
READ 读取文件,可以以二进制的形式读(HEX)
GENERATE 通过文件(INPUT)或内容(CONTENT)来生成新文件
STRINGS 以字符串形式读取
RENAME 重命名
REMOVE 删除文件
cmake_minimum_required(VERSION 3.22)
project(HELLO)
add_subdirectory(src)
add_subdirectory(libhello)

file(WRITE test.txt "impressiv and attractive\n")
file(APPEND test.txt "ONU and OLT")

file(GENERATE OUTPUT out1.txt INPUT "${PROJECT_SOURCE_DIR}/test.txt")
file(GENERATE OUTPUT out2.txt CONTENT "hello world")

file(READ "${PROJECT_SOURCE_DIR}/test.txt" read_buf)
message("!!!read from test.txt: !!!\n" ${read_buf})
file(READ "${PROJECT_SOURCE_DIR}/test.txt" outvar1 OFFSET 0 LIMIT 6)
message("outvar1 OFFSET 0 LIMIT 6 is \n" ${outvar1})
file(READ "${PROJECT_SOURCE_DIR}/test.txt" outvar2 OFFSET 0 LIMIT 6 HEX)
message("outvar2 OFFSET 0 LIMIT 6 HEX is \n" ${outvar2})

file(STRINGS "${PROJECT_SOURCE_DIR}/test.txt" outvar3 LENGTH_MAXIMUM 6)
message("outvar3 LENGTH_MAXIMUM 6 is \n" "${outvar3}")
file(STRINGS "${PROJECT_SOURCE_DIR}/test.txt" outvar4 LENGTH_MINIMUM 4)
message("outvar4 LENGTH_MINIMUM 2 is \n" "${outvar4}")
file(STRINGS "${PROJECT_SOURCE_DIR}/test.txt" outvar5 LIMIT_COUNT 1)
message("outvar5 LIMIT_COUNT 1 is \n" "${outvar5}")

file(WRITE "${PROJECT_SOURCE_DIR}/temp.txt" "")
file(RENAME "${PROJECT_SOURCE_DIR}/temp.txt" "${PROJECT_SOURCE_DIR}/change.txt")
file(REMOVE "${PROJECT_SOURCE_DIR}/change.txt")

message打印内容

CMake语法复习_第20张图片

十:设置交叉编译链

总结

以上就是本文的全部内容了,希望可以帮到你。

你可能感兴趣的:(脚本用法,linux,运维,服务器,CMake)