cmakelist基本语法
一、幾個基本概念:
1、GCC
a、由GUN開發的編譯器,支持C/C++,Java等語言.
b、項目簡單時,可以使用gcc/g++來進行編譯.
c、項目復雜時,只使用gcc來進行編譯會變得非常復雜.
2、make
a、主要負責一個軟件工程中多個源代碼的自動編譯工作
b、注意每個平臺的make不一樣,makefile的語法也不一樣
c、make工具可以識別出工程中哪些文件已經被修改,并且在再次編譯的時候只編譯這些文件,從而提高編譯的效率;
d、make的主要任務是根據 makefile 文件(一個腳本文件)中定義的規則和步驟,根據各個模塊的更新情況,自動完成整個軟件項目的維護和目標程序生成工作。
3、Makefile
a、Makefile是有條理的gcc編譯命令文件.
b、利用make工具執行Makefile文件,來達到編譯的目的.
c、程序簡單時,可以使用Makefile.
d、程序復雜時,有局限性.
4、CMake
a、全稱:Cross Platform CMake,是一個跨平臺的安裝(編譯)工具.
b、利用cmake工具讀取CMakeList.txt配置文件,并最終生成Makefile文件.
c、CMake開發簡單,易于理解.
d、編程效率高.
5、CMakelist
a、CMakeList其實就是適配CMake語法的一個配置文件。
b、不需要關注不同的Make工具需要的不同格式的MakeFile文件,而是直接使用Cmake 構建出適應當前平臺的Makefile進而進行代碼編譯(因此cmake具有跨平臺特點)。
6、Kconfig
kconfig用來做系統配置,生成menuconfig的配置文件:
a、供cmake使用:CMakeList會使用這些參數
b、用于編譯源碼
7、ninja
a、ninja根據.ninja文件將源碼生成目標程序
b、類似make,但是處理速度更快
8、.ninja
a、包含一系列編譯規則和命令的文件
b、類似Makefile,但是語法更簡單
9、GN
a、大規模工程的跨平臺構建工具,類似cmake,但是構建速度更快。
b、GN(generate ninja)是一種元構建系統,生成Ninja構建文件(Ninja build files),即利用GN工具把.gn文件轉換成.ninja文件
c、gn和ninja的關系就與cmake和make的關系差不多
10、build.gn
a、項目構建文件,不直接構建項目,而是產生構建項目的ninja文件,然后再用ninja去構建項目
b、類似cmakelist,但是語法更簡單
原始跨平臺:
編寫makefile文件,使用各平臺上的make(微軟的MS nmake、GNU的make)來編譯makefile文件,這種做法的缺點是各平臺的make實現不同,導致這種原始的做法其實復用度并不高,需要針對各平臺單獨編寫差異巨大的makefile文件,那為什么要介紹它呢,因為這是跨平臺的根,所有跨平臺工具,最終都是要依賴各平臺應用的集成開發環境的編譯器來執行編譯,這是固定不變的,也就是說各平臺的編譯,最終還是需要各平臺的makefile,這一點是無法逃避的,而怎么由人工轉為自動化,才是跨平臺編譯的進階之路。
進階跨平臺:
使用cmake,編寫統一的makefile文件,最后由cmake自動生成各平臺相關的makefile文件執行編譯,這一點上,cmake已經是比較好的跨平臺工具了,一般的跨平臺工程基本已經滿足需求了。
現代跨平臺:
當工程規模增大到難以想象的量級時,編譯速度和工程模塊的劃分變得尤為重要,其中chromium工程就遇到這兩個問題,于是最初誕生了gyp,最后演化升級為gn,其旨在追求工程更加清晰的模塊和結構呈現,以及更快的編譯速度。前者通過語法層面實現,后者則依靠ninja來提升編譯速度,因為大型工程的編譯,很大一部分時間都花在了源文件編譯依賴樹的分析這塊,而ninja更像是一個編譯器的預處理,其主要目的是舍棄gcc、msvc、clang等編譯器在編譯過程中遞歸查找依賴的方式,因為這里存在很多重復的依賴查找,而ninja改進了這一過程,提前生成編譯依賴樹,編譯期間按照編譯依賴樹的順序依次編譯,這樣就大大減少了編譯期間雜亂的編譯順序造成的重復依賴關系查找。
二、CMakelist編寫(CMake基本指令)
1、configure_file
功能:
cmake 中的 configure_file 指令通過讀取輸入文件中的內容,將 CMakeLists.txt 文件中的變量轉變為 C/C++ 中可識別的宏定義,然后存入另一個文件中。其語法格式如下。其中,input 為輸入的文件,output 為輸出的文件。通常,輸入文件為 http://xxx-config.h.in,輸出文件為 xxx-config.h。
語法:
configure_file(<input> <output>
?????????????? [NO_SOURCE_PERMISSIONS | USE_SOURCE_PERMISSIONS |
??????????????? FILE_PERMISSIONS <permissions>...]
?????????????? [COPYONLY] [ESCAPE_QUOTES] [@ONLY]
?????????????? [NEWLINE_STYLE [UNIX|DOS|WIN32|LF|CRLF] ])
主要參數說明:
input:輸入的文件名,通常為 xxx-config.h.in;
output:輸出的文件名,通常為 xxx-config.h;
@ONLY:在 <input> 文件中只使用 @VAR@ 的方式獲取變量值,不適用 ${VAR} 的方式;
示例:
a、判斷變量是否定義
輸入文件xxx-config.h.in語法:
#cmakedefine VAR
用途:
源碼中不關心變量值,只關心變量是否被定義。如果 CMakeLists.txt 文件中,定義了變量 VAR,那么在轉化出來的輸出文件中就會存在 #define VAR 的語句。否則,在輸出文件中就會顯示 /*undef VAR*/。然后,在源碼中使用 #ifdef 語句進行使用——#ifdef VAR。
b、判斷選項是否開啟
輸入文件xxx-config.h.in語法:
#cmakedefine01 VAR
用途:
CMakelists.txt 中的 option(VAR ...) 用于開關操作,并且可以使用 cmake -DVAR=ON/OFF .. 修改其變量值。上述指令根據 CMakeLists.txt 中 VAR 的值為 ON 或 OFF,將其轉換為輸出文件中的 #define VAR 1 或 #define VAR 0。然后在源碼中使用 #if 進行引用——#if VAR。當然,該語句也可用于使用 set(VAR xxx) 定義的變量,但是用于 option(VAR ...) 更合適。
c、獲取變量值
輸入文件xxx-config.h.in語法(其中的 @VAR@ 可以替換為 ${VAR}):
#cmakedefine VAR @VAR@
或
#define SELF_DEFINE_MACRO_NAME @VAR@
用途:
CMakeLists.txt 文件中,變量 VAR 多用于定義某些信息,比如版本號,作者,項目描述,調試等級等。然后在源碼中輸出這些值到固定位置,起到提示的作用。
總結:
使用configure_file()可以省去很多的類似add_compile_options()指令。只需在 CMakeLists.txt 文件中定義變量,然后再在xxx-config.h.in 文件中使用 #cmakedefine 進行引用即可,即通過cmakelist控制宏變量的使用。
2、set
功能:
用來顯式定義變量。
語法:
SET(VAR [VALUE] [CACHE TYPE DOCSTRING [FORCE]])
主要參數說明:
VAR:要設置的變量名
VALUE:變量的值
示例:
SET (SRC_LST STRING)
說明: 用變量代替值,例子中定義SRC_LST代替后面的字符串。
3、if
功能:
對項目進行有條件編譯。
語法:
if(<condition>)
? <commands>
elseif(<condition>) # optional block, can be repeated
? <commands>
else()????????????? # optional block
? <commands>
endif()
主要參數說明:
condition:如果為1、ON、TRUE等值,則條件為真,否則為變量(則判斷變量是否已經定義)
commands:為真時執行的命令
4、add_library
功能:
使用指定的源文件向工程中添加一個目標庫。
語法:
add_library(<name> [STATIC | SHARED | MODULE]
??????????? [EXCLUDE_FROM_ALL]
??????????? [<source>...])
主要參數說明:
name:構建成的庫名,必須全局唯一
STATIC|SHARED|MOUDLE:庫的類型,STATIC(靜態庫) SHARED(動態庫) MODULE(模塊庫)
EXCLUDE_FROM_ALL:加了此屬性的target在默認編譯的時候,不會被編譯,只能手動編譯
source:構建庫的源文件,可以直接指定,也可以后續使用target_sources()指定
示例:
add_library(hello_library STATIC
??? src/Hello.cpp
)
5、target_compile_definitions
功能:
向目標添加編譯標志。
語法:
target_compile_definitions(<target>
? <INTERFACE|PUBLIC|PRIVATE> [items1...]
? [<INTERFACE|PUBLIC|PRIVATE> [items2...] ...])
主要參數說明:
target:編譯目標,必須已經通過add_executable() 或者add_library() 創建,并且must not be an ALIAS target(輸入工程).
關鍵字INTERFACE,PUBLIC和PRIVATE用來指定其后參數的作用域。PRIVATE 和 PUBLIC 項將產生的COMPILE_DEFINITIONS 屬性。PUBLIC和INTERFACE 項將產生的INTERFACE_COMPILE_DEFINITIONS 屬性。
items:參數指定編譯定義。重復調用相同的目標將按照調用順序追加(定義)。
示例:
target_compile_definitions(cmake_examples_compile_flags
PRIVATE CONFIG_FSM_DEBUG=1
)
說明:為編譯目標cmake_examples_compile_flags設置編譯標志CONFIG_FSM_DEBUG=1
6、set_target_properties
功能:
設置目標的屬性,語法是列出想要更改的所有目標,然后提供接下來想要設置的值,可以使用該命令任何所需的鍵值對。
語法:
set_target_properties(target1 target2 ...
????????????????????? PROPERTIES prop1 value1
????????????????????? prop2 value2 ...)
主要參數說明:
target1、target2…:要設置屬性的目標1、目標2
PROPERTIES:屬性關鍵字
prop1 value1、prop2 value2:鍵值對1、鍵值對2
示例:
set_target_properties(
Thirdlib
PROPERTIES IMPORTED_LOCATION
${CMAKE_CURRENT_SOURCE_DIR}/jniLibs/libThirdlib.so
)
說明:為目標Thirdlib設置導入位置屬性
7、target_include_targets
功能:
為目標添加庫
語法:
# Set a target to include all interface directories of depended targets.
# The arguments must be target.
function(target_include_targets target type)
??? foreach(arg ${ARGN})
??????? target_include_directories(${target} ${type}
??????????? $<TARGET_PROPERTY:${arg},INTERFACE_INCLUDE_DIRECTORIES>)
??? endforeach()
endfunction()
主要參數說明:
示例:
target_include_targets(appstart
PRIVATE atr ats diag nvm)
說明:為目標appstart添加庫atr ats diag nvm
注意:此為extesion.cmake中的擴展指令,就像CMakeList.txt的庫一樣,加載后可以在CMakeList.txt中使用它的一些自定義函數和定義
8、target_include_targets_if
功能:
有條件的為目標添加庫
語法:
# Helper to link libraries with conditions
macro(target_include_targets_if)? # <conditon> THEN <command>
??? cmake_parse_arguments(MY "" "" "THEN" ${ARGN})
??? if(${MY_UNPARSED_ARGUMENTS})
??????? target_include_targets(${MY_THEN})
??? endif()
endmacro()
主要參數說明:
示例:
target_include_targets_if(CONFIG_AT_BT_APP_SUPPORT THEN
appstart PRIVATE bt_app)
說明:如果定義了CONFIG_AT_BT_APP_SUPPORT,則為目標appstart添加庫bt_app
注意:此為extesion.cmake中的擴展指令,就像CMakeList.txt的庫一樣,加載后可以在CMakeList.txt中使用它的一些自定義函數和定義
9、target_include_directories
功能:
為特定目標 target 添加頭文件目錄
語法:
target_include_directories(<target> [SYSTEM] [AFTER|BEFORE]
? ??????????????????????????????? ???<INTERFACE|PUBLIC|PRIVATE> [items1...]
? ??????????????????????????????? ??[<INTERFACE|PUBLIC|PRIVATE> [items2...] ...])
主要參數說明:
<target>: 構建目標,使用 add_executable() 或 add_library 聲明,不可為 ALIAS 目標;
[SYSTEM]: 指定是否平臺相關,若該屬性與 PUBLIC 或 INTERFACE 一同設置,CMake 將使用指定的目錄初始化目標的 INTERFACE_SYSTEM_INCLUDE_DIRECTORIES 屬性;
INTERFACE_SYSTEM_INCLUDE_DIRECTORIES: 該屬性為含有平臺相關頭文件的目錄,常用于抑制編譯器警告;
[AFTER|BEFORE]: 指定相應目錄添加的順序,在后添加/在前添加。
[INTERFACE|PUBLIC|PRIVATE]: 指定頭文件的可見性,若設置PRIVATE或PUBLIC,CMake 將使用指定的目錄初始化目標的INCLUDE_DIRECTORIES 屬性,若設置為PUBLIC或 INTERFACE,CMake 將使用指定的目錄初始化目標的 INTERFACE_INCLUDE_DIRECTORIES 屬性;
INCLUDE_DIRECTORIES: 該屬性為目標的頭文件目錄;
INTERFACE_INCLUDE_DIRECTORIES: 該屬性為目標的開放頭文件目錄;
[items]: 指定要添加的頭文件目錄,可以使用相對路徑或絕對路徑,相對路徑為相對于當前路徑 CMAKE_CURRENT_SOURCE_DIR,也可以使用 CMake 提供的 generator expression。
示例:
target_include_directories(appstart
PRIVATE //kaihong/kh_platform/interfaces/kits/nativeapi)
說明:為目標appstart添加頭文件目錄//kaihong/kh_platform/interfaces/kits/nativeapi
注意:為目標添加當前目錄或子目錄下的頭文件目錄時使用PUBLIC,否則使用PRIVATE
10、set_if
功能:
條件設置目標
語法:
# Helper to set variable with conditions
macro(set_if var) # <condition> THEN <val_true> OTHERWISE <val_false>
??? cmake_parse_arguments(MY "" "" "THEN;OTHERWISE" ${ARGN})
??? if(${MY_UNPARSED_ARGUMENTS})
??????? if(MY_THEN)
??????????? set(${var} ${MY_THEN})
??????? endif()
??? else()
??????? if (MY_OTHERWISE)
??????????? set(${var} ${MY_OTHERWISE})
??????? endif()
??? endif()
endmacro()
主要參數說明:
示例:
set_if(ldscript ?????? CONFIG_APP_RUN_ON_FLASH
THEN ?????????? ${SOURCE_TOP_DIR}/components/hal/ldscripts/flashrun.ld
?? ? OTHERWISE ${SOURCE_TOP_DIR}/components/hal/ldscripts/ddrrun.ld )
說明:如果定義了CONFIG_APP_RUN_ON_FLASH,則鏈接器鏈接${SOURCE_TOP_DIR}/components/hal/ldscripts/flashrun.ld,否則鏈接${SOURCE_TOP_DIR}/components/hal/ldscripts/ddrrun.ld
注意:此為extesion.cmake中的擴展指令,就像CMakeList.txt的庫一樣,加載后可以在CMakeList.txt中使用它的一些自定義函數和定義
11、link_directories
功能:
添加鏈接器尋找庫的目錄
語法:
link_directories([AFTER|BEFORE] directory1 [directory2 ...])
主要參數說明:
Directory:要尋找的庫的路徑
示例:
link_directories (${OHOS_OUT_PATH}/libs)
12、target_link_libraries
功能:
將目標與庫文件鏈接
語法:
target_link_libraries(<target>
????????????????????? <PRIVATE|PUBLIC|INTERFACE> <item>...
????????????????????? [<PRIVATE|PUBLIC|INTERFACE> <item>...]...)
主要參數說明:
<target>:目標
<item>:庫文件
示例:
target_link_libraries(${BUILD_TARGET} PRIVATE all_libs appstart)
13、target_link_whole_archive
功能:
設置連接器將庫中的符號全部加載到鏈接的庫中
語法:
# Link targets with --whole-archive. PUBLIC/PRIVATE is required as parameter,
# but PRIVATE will be used forcedly.
function(target_link_whole_archive target signature)
??? target_link_libraries(${target} PRIVATE -Wl,--whole-archive)
??? foreach(arg ${ARGN})
??????? target_link_libraries(${target} PRIVATE ${arg})
??? endforeach()
??? target_link_libraries(${target} PRIVATE -Wl,--no-whole-archive)
endfunction()
主要參數說明:
示例:
target_link_whole_archive(${BUILD_TARGET} PRIVATE? ${OHOS_FORCE_LINK_LIBS})
注意:此為extesion.cmake中的擴展指令,就像CMakeList.txt的庫一樣,加載后可以在CMakeList.txt中使用它的一些自定義函數和定義
14、target_link_group
功能:
為目標添加鏈接庫組
語法:
# Link targets with --start-group. PUBLIC/PRIVATE is required as parameter,
# but PRIVATE will be used forcedly.
function(target_link_group target signature)
??? target_link_libraries(${target} PRIVATE -Wl,--start-group)
??? foreach(arg ${ARGN})
??????? target_link_libraries(${target} PRIVATE ${arg})
??? endforeach()
??? target_link_libraries(${target} PRIVATE -Wl,--end-group)
endfunction()
主要參數說明:
示例:
target_link_group(${BUILD_TARGET}
PRIVATE
all_libs ${OHOS_ALL_BASE_LIBS} ${OHOS_SERIES_PORT_PARAM} ${libcpp_file_name})
注意:此為extesion.cmake中的擴展指令,就像CMakeList.txt的庫一樣,加載后可以在CMakeList.txt中使用它的一些自定義函數和定義
15、relative_glob
功能:
產生一個匹配的文件列表并將它存儲到變量中。如果 RELATIVE 標志位被設定,將返回指定路徑的相對路徑。
語法:
macro(relative_glob var)
??? file(GLOB ${var} RELATIVE ${CMAKE_CURRENT_SOURCE_DIR} ${ARGN})
endmacro()
主要參數說明:
示例:
relative_glob(srcs include/*.h src/*.c src/*.h)
說明:產生一個匹配include/*.h、src/*.c、src/*.h的文件列表并將它存儲到變量srcs中。
注意:此為extesion.cmake中的擴展指令,就像CMakeList.txt的庫一樣,加載后可以在CMakeList.txt中使用它的一些自定義函數和定義
16、beautify_c_code
功能:
將編譯后的文件放在和代碼文件相同的文件夾中,并且設置格式化選項,使用自定義的排版格式。
語法:
function(beautify_c_code target)
??? if(ARGN)
??????? set(beautify_target beautify_${target})
??????? if(NOT TARGET ${beautify_target})
??????????? add_custom_target(${beautify_target})
??????????? add_dependencies(beautify ${beautify_target})
??????? endif()
??????? add_custom_command(TARGET ${beautify_target} POST_BUILD
??????????? COMMAND clang-format -i ${ARGN}
??????????? WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR})
??? endif()
endfunction()
主要參數說明:
示例:
beautify_c_code(appstart ${srcs})
注意:此為extesion.cmake中的擴展指令,就像CMakeList.txt的庫一樣,加載后可以在CMakeList.txt中使用它的一些自定義函數和定義
17、cmake_minimum_required
功能:
指明對cmake的最低(高)版本的要求。
語法:
cmake_minimum_required(VERSION <min>[...<max>] [FATAL_ERROR])
主要參數說明:
VERSION:指明后面的參數為版本號,這個參數是必須的。
min:指定cmake要求的最低版本號,如果cmake實際版本號低于min指定的版本號,cmake的執行過程會終止。
max:指定cmake要求的最高版本號,要求該參數不能小于min。
FATAL_ERROR: 該參數在cmake的2.6及以后的版本被忽略,在cmake的2.4及以前的版本,需要指明該參數,以便cmake能提示失敗而不僅僅是一個警告。
示例:
cmake_minimum_required(VERSION 3.13)
說明:cmake要求的最低版本號為3.13
補充:cmake的版本號格式為major.minor[.patch[.tweak]],例如cmake的版本號為3.10.2
18、include
功能:
載入并運行來自于文件或模塊的 CMake 代碼
語法:
include(<file|module> [OPTIONAL] [RESULT_VARIABLE <VAR>] [NO_POLICY_SCOPE])
主要參數說明:
示例:
include(cmake/extension.cmake)
19、define_property
功能:
定義和記錄自定義屬性。在作用域中定義一個用于set_property()和get_property()命令的屬性。它主要用于定義屬性的初始化或繼承方式。
語法:
define_property(<GLOBAL | DIRECTORY | TARGET | SOURCE |
???????????????? TEST | VARIABLE | CACHED_VARIABLE>
???????????????? PROPERTY <name> [INHERITED]
???????????????? [BRIEF_DOCS <brief-doc> [docs...]]
???????????????? [FULL_DOCS <full-doc> [docs...]]
???????????????? [INITIALIZE_FROM_VARIABLE <variable>])
主要參數說明:
第一個參數確定應在其中使用屬性的范圍類型。它必須是下列之一:
GLOBAL??? = associated with the global namespace
DIRECTORY = associated with one directory
TARGET??? = associated with one target
SOURCE??? = associated with one source file
TEST????? = associated with a test named with add_test
VARIABLE? = documents a CMake language variable
CACHED_VARIABLE = documents a CMake cache variable
PROPERTY:屬性關鍵字
<name>:要定義的屬性名稱
BRIEF_DOCS:關鍵字,表示簡要文檔
<brief-doc>:簡要文檔與屬性關聯的字符串
FULL_DOCS:關鍵字,表示完整文檔
<full-doc>:完整文檔與屬性關聯的字符串
示例:
# Use a global property to collect all application libraries
define_property(GLOBAL
PROPERTY app_libraries
BRIEF_DOCS "app libraries"
??? ???????????????????? FULL_DOCS "app libraries" )
說明:為所有應用庫設置全局屬性“app_libraries”,關聯字符串為“app libraries”
20、message
功能:
在終端顯示消息,類似printf
語法:
message([<mode>] "message text" ...)
主要參數說明:
mode 的值包括 FATAL_ERROR、WARNING、AUTHOR_WARNING、STATUS、VERBOSE等。常用其中2個——FATAL_ERROR、STATUS。
FATAL_ERROR:產生 CMake Error,會停止編譯系統的構建過程;
STATUS:最常用的命令,常用于查看變量值,類似于編程語言中的 DEBUG 級別信息。
"message text"為顯示在終端的內容。
示例:
message("CMAKE_CURRENT_SOURCE_DIR dir: ${CMAKE_CURRENT_SOURCE_DIR}")
message("CMAKE_CURRENT_BINARY_DIR dir: ${CMAKE_CURRENT_BINARY_DIR}")
說明:在cmakelist.txt所在目錄執行cmake .命令即可在終端輸出如下目錄信息
CMAKE_CURRENT_SOURCE_DIR dir: /home/jwl/safehat/device/soc/unisoc/8910dm/fibocom_l610/liteos_m/sdk
CMAKE_CURRENT_BINARY_DIR dir: /home/jwl/safehat/device/soc/unisoc/8910dm/fibocom_l610/liteos_m/sdk
21、find_package
功能:
引入外部依賴包
語法:
find_package(<PackageName> [version] [EXACT] [QUIET] [MODULE]
???????????? [REQUIRED] [[COMPONENTS] [components...]]
???????????? [OPTIONAL_COMPONENTS components...]
???????????? [NO_POLICY_SCOPE])
主要參數說明:
PackageName:依賴包名稱,必須項;
version:版本號,若指定,則find_package一定要檢查找到的包是否與version版本兼容;
EXACT:如果指定,表示必須完全匹配version指定版本的包而不是僅僅兼容就可以;
QUIET:如果指定,表示disable信息輸出,即命令運行時不輸出相關message,即使沒有找到該包。但是如果REQUIRED被指定,還是會有信息輸出;
MODULE:表示只用于module模式,即使沒有找到也不會進入CONFIG模式;
REQUIRED:表示此包是必須的,如果沒有找到,構建程序報錯并終止;
[COMPONENTS] [components…]:表示查找的包中必須要找到的組件(components),如果有任何一個找不到就算失敗,類似于REQUIRED,導致cmake停止執行;
OPTIONAL_COMPONENTS components…:可選的依賴組件,即使找不到也不會影響cmake繼續執行;
NO_POLICY_SCOPE:cmake policy,參見:cmake_policy
注:上述參數中,除了PackageName必需,其他都是可選參數。
示例:
find_package(Git)
說明:通過在Modules路徑下尋找FindGit.cmake引入Git包
補充:cmake本身不提供任何搜索庫的便捷方法,所有搜索庫并給變量賦值的操作必須由cmake代碼完成,比如FindXXX.cmake和XXXConfig.cmake。只不過,庫的作者通常會提供這兩個文件,以方便使用者調用。find_package采用兩種模式搜索庫:
Module模式:搜索CMAKE_MODULE_PATH指定路徑下的FindXXX.cmake文件,執行該文件從而找到XXX庫。其中,具體查找庫并給XXX_INCLUDE_DIRS和XXX_LIBRARIES兩個變量賦值的操作由FindXXX.cmake模塊完成。
Config模式:搜索XXX_DIR指定路徑下的XXXConfig.cmake文件,執行該文件從而找到XXX庫。其中具體查找庫并給XXX_INCLUDE_DIRS和XXX_LIBRARIES兩個變量賦值的操作由XXXConfig.cmake模塊完成。
不過cmake默認采取Module模式,如果Module模式未找到庫,才會采取Config模式,Config模式是一個備選策略。
22、execute_process
功能:
從當前正在執行的CMake進程中派生一個或多個子進程,從而提供了在配置項目時運行任意命令的方法。可以在一次調用 execute_process 時執行多個命令。但請注意,每個命令的輸出將通過管道傳輸到下一個命令中。
語法:
execute_process(COMMAND <cmd1> [<arguments>]
??????????????? [COMMAND <cmd2> [<arguments>]]...
??????????????? [WORKING_DIRECTORY <directory>]
???????????? ???[TIMEOUT <seconds>]
??????????????? [RESULT_VARIABLE <variable>]
??????????????? [RESULTS_VARIABLE <variable>]
??????????????? [OUTPUT_VARIABLE <variable>]
??????????????? [ERROR_VARIABLE <variable>]
??????????????? [INPUT_FILE <file>]
??????????????? [OUTPUT_FILE <file>]
??????????????? [ERROR_FILE <file>]
??????????????? [OUTPUT_QUIET]
??????????????? [ERROR_QUIET]
??????????????? [COMMAND_ECHO <where>]
??????????????? [OUTPUT_STRIP_TRAILING_WHITESPACE]
??????????????? [ERROR_STRIP_TRAILING_WHITESPACE]
??????????????? [ENCODING <name>]
??????????????? [ECHO_OUTPUT_VARIABLE]
??????????????? [ECHO_ERROR_VARIABLE]
??????????????? [COMMAND_ERROR_IS_FATAL <ANY|LAST>])
主要參數說明:
COMMAND:子進程命令行。
WORKING_DIRECTORY:指定應該在哪個目錄中執行命令。
TIMEOUT:如果在指定的時間內(以秒為單位計算,允許有小數位)子進程執行仍未完成,則將會被中斷。
RESULT_VARIABLE:包含進程運行的結果。這要么是一個整數表示執行成功,要么是一個帶有錯誤條件的字符串。
RESULTS_VARIABLE:變量將被設置為以分號分隔的列表形式包含所有進程的結果,按給定命令參數的順序排列。每個條目都是對應子項的整數返回碼或描述錯誤條件的字符串。
OUTPUT_VARIABLE和ERROR_VARIABLE將包含執行命令的標準輸出和標準錯誤。由于命令的輸出是通過管道傳輸的,因此只有最后一個命令的標準輸出才會保存到OUTPUT_VARIABLE中。
INPUT_FILE:指定標準輸入重定向的文件名。
OUTPUT_FILE:指定標準輸出重定向的文件名。
ERROR_FILE:指定標準錯誤輸出重定向的文件名。
OUTPUT_QUIET和ERROR_QUIET:CMake將靜默地忽略標準輸出和標準錯誤。
COMMAND_ECHO <where>:正在運行的命令將被回送到<where>,而<where>將被設置為STDERR、STDOUT或NONE中的一個。
OUTPUT_STRIP_TRAILING_WHITESPACE:刪除運行命令的標準輸出中的任何尾隨空格。
ERROR_STRIP_TRAILING_WHITESPACE:刪除運行命令的錯誤輸出中的任何尾隨空格。
ENCODING <name>:適用于windows平臺,編碼名稱有NONE、AUTO、ANSI、OEM、UTF8或UTF-8。
ECHO_OUTPUT_VARIABLE, ECHO_ERROR_VARIABLE:標準輸出或標準錯誤不會被專門重定向到配置的變量。
示例:
execute_process(COMMAND "${GIT_EXECUTABLE}" describe --abbrev=8 --always --dirty WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
OUTPUT_VARIABLE ??????? BUILD_GIT_REVISION
OUTPUT_STRIP_TRAILING_WHITESPACE)
23、set_property
功能:
在作用域的零個或多個對象上設置一個屬性。
語法:
set_property(<GLOBAL????????????????? ????|
????????????? DIRECTORY [<dir>]?????????? |
????????????? TARGET??? [<target1> ...]?? |
????????????? SOURCE??? [<src1> ...]
??????????????????????? [DIRECTORY <dirs> ...] |
??????????????????????? [TARGET_DIRECTORY <targets> ...]
????????????? INSTALL?? [<file1> ...]???? |
????????????? TEST????? [<test1> ...]???? |
????????????? CACHE???? [<entry1> ...]??? >
???????????? [APPEND] [APPEND_STRING]
???????????? PROPERTY <name> [<value1> ...])
主要參數說明:
第一個參數決定該屬性設置所在的域,它必須為下面中的其中之一:
GLOBAL域是唯一的,并且不接特殊的任何名字。
DIRECTORY域默認為當前目錄,但也可以用全路徑或相對路徑指定其他的目錄(前提是該目錄已經被CMake處理)。
TARGET域可命名零或多個已經存在的目標。
SOURCE域可命名零或多個源文件。注意:源文件屬性只對在相同目錄下的目標是可見的(CMakeLists.txt)。
TEST域可命名零或多個已存在的測試。
CACHE域必須命名零或多個已存在條目的cache.
必選項PROPERTY后面緊跟著要設置的屬性的名字。其他的參數用于構建以分號隔開的列表形式的屬性值。如果指定了APPEND選項,則指定的列表將會追加到任何已存在的屬性值當中。如果指定了APPEND_STRING選項,則會將值作為字符串追加到任何已存在的屬性值。
示例:
set_property(DIRECTORY APPEND PROPERTY CMAKE_CONFIGURE_DEPENDS ${partinfogen_py} ${CONFIG_PARTINFO_JSON_PATH})
24、project
功能:
指定camke工程的名字,還可指定版本號、描述、主頁鏈接以及編譯工程所使用的的語言。
語法:
project(<PROJECT-NAME> [<language-name>...])
project(<PROJECT-NAME>
??????? [VERSION <major>[.<minor>[.<patch>[.<tweak>]]]]
??????? [DESCRIPTION <project-description-string>]
??????? [HOMEPAGE_URL <url-string>]
?? ?????[LANGUAGES <language-name>...])
主要參數說明:
PROJECT_NAME : 必選,用來設置工程名,設置后,會把設置的值存儲在CMAKE_PROJECT_NAME變量中
**VERSION **:可選,工程版本號,有主版本號、次版本號、補丁版本號
**DESCRIPTION **:工程簡單的的描述
**HOMEPAGE_URL **:工程主頁url
**LANGUAGES **:工程使用的語言,默認為C或CXX
示例:
project(${BUILD_TARGET} C CXX ASM)
25、include_directories
功能:
將指定目錄添加到編譯器的頭文件搜索路徑之下,指定的目錄被解釋成當前源碼路徑的相對路徑。
語法:
include_directories ([AFTER|BEFORE] [SYSTEM] dir1 [dir2 ...])
主要參數說明:
示例:
include_directories(${SOURCE_TOP_DIR}/components/newlib/include)
26、add_custom_target
功能:增加一個沒有輸出的目標(不在all target中),使得它總是被構建,該目標需要手動指定才能執行,類似make clean這種命令(單獨make不會執行,需要指定目標ckean)。
語法:
add_custom_target(Name [ALL] [command1 [args1...]]
????????????????? [COMMAND command2 [args2...] ...]
????????????????? [DEPENDS depend depend depend ... ]
????????????????? [BYPRODUCTS [files...]]
????????????????? [WORKING_DIRECTORY dir]
????????????????? [COMMENT comment]
????????????????? [JOB_POOL job_pool]
????????????????? [VERBATIM] [USES_TERMINAL]
????????????????? [COMMAND_EXPAND_LISTS]
????????????????? [SOURCES src1 [src2...]])
主要參數說明:
Name:target名字
COMMAND:指定要在構建時執行的命令行;
DEPENDS:指定命令所依賴的文件;
COMMENT:在構建時執行命令之前顯示給定消息;
WORKING_DIRECTORY:使用給定的當前工作目錄執行命令。如果它是相對路徑,它將相對于對應于當前源目錄的構建樹目錄;
BYPRODUCTS:指定命令預期產生的文件。
示例
add_custom_target(finish
???????????????? COMMAND ${CMAKE_COMMAND} -E echo compile finish)
27、get_property
功能:
獲取一個屬性值
語法:
get_property(<variable>
?????????????? <GLOBAL???????????? |
??????????????? DIRECTORY [dir]??? |
??????????????? TARGET??? <target> |
??????????????? SOURCE??? <source> |
??????????????? TEST????? <test>?? |
??????????????? CACHE???? <entry>? |
??????????????? VARIABLE>
??????? ???????PROPERTY <name>
?????????????? [SET | DEFINED |BRIEF_DOCS | FULL_DOCS])
主要參數說明:
示例:
get_property(app_libraries GLOBAL PROPERTY app_libraries)
28、add_custom_command
功能:
自定義生成輸出文件
語法:
add_custom_command(OUTPUT output1 [output2 ...]
??????????????????? COMMAND command1 [ARGS] [args1...]
??????????????????? [COMMAND command2 [ARGS] [args2...] ...]
??????????????????? [MAIN_DEPENDENCY depend]
??????????????????? [DEPENDS [depends...]]
??????????????????? [BYPRODUCTS [files...]]
??????? ????????????[IMPLICIT_DEPENDS <lang1> depend1
???????????????????????????????????? [<lang2> depend2] ...]
??????????????????? [WORKING_DIRECTORY dir]
??????????????????? [COMMENT comment]
??????????????????? [DEPFILE depfile]
??????????????????? [JOB_POOL job_pool]
??????????????????? [VERBATIM] [APPEND] [USES_TERMINAL]
??????????????????? [COMMAND_EXPAND_LISTS])
主要參數說明:
OUTPUT:目標文件名稱,代表下方的命令;
COMMAND:需要執行的命令;
DEPENDS:執行命令時需要的依賴;
示例:
add_custom_command(OUTPUT printout
??????????????????? COMMAND ${CMAKE_COMMAND} -E echo compile finish
??????????????????? VERBATIM
?????????????????? )
29、add_dependencies
功能:
為目標添加一個依賴關系,編譯時目標中的符號定義找不到時就可以添加其他庫依賴。
語法:
add_dependencies(<target> [<target-dependency>]...)
主要參數說明:
示例:
add_dependencies(${target} build_${target})
30、add_subdirectory_if_exist
功能:
添加一個子目錄并構建該子目錄,子目錄下應該包含CMakeLists.txt文件和代碼文件。
語法:
add_subdirectory_if_exist (source_dir [binary_dir] [EXCLUDE_FROM_ALL])
主要參數說明:
source_dir:必選參數。該參數指定一個子目錄,子目錄下應該包含CMakeLists.txt文件和代碼文件。子目錄可以是相對路徑也可以是絕對路徑,如果是相對路徑,則是相對當前目錄的一個相對路徑。
示例:
add_subdirectory_if_exist(appstart)
總結
以上是生活随笔為你收集整理的cmakelist基本语法的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 物联网架构图
- 下一篇: JavaFast企业级快速开发平台-常见