ExternalProject¶
外部專案定義¶
- ExternalProject_Add¶
ExternalProject_Add()
函數建立一個自訂目標,以驅動外部專案的下載、更新/修補、設定、建置、安裝和測試步驟ExternalProject_Add(<name> [<option>...])
如果需要(例如,用於 CDash 提交),可以獨立驅動流程中的個別步驟,並且可以定義額外的自訂步驟,以及控制步驟依賴項的能力。用於管理外部專案的目錄結構也可以自訂。此函數支援大量選項,可用於調整外部專案的行為。
目錄選項¶
在大多數情況下,預設目錄佈局已足夠。這很大程度上是一個實作細節,主專案通常不需要變更。然而,在某些情況下,控制目錄佈局可能是有用或必要的。從主要建置可以使用 ExternalProject_Get_Property()
命令來檢索其值的角度來看,目錄選項可能更有用,從而允許主專案參考外部專案的建置產物。
PREFIX <dir>
外部專案的根目錄。除非另有說明,否則與外部專案相關的所有其他目錄都將在此目錄下建立。
TMP_DIR <dir>
用於儲存臨時檔案的目錄。
STAMP_DIR <dir>
用於儲存每個步驟的時間戳記的目錄。除非被 LOG_DIR 覆蓋(請參閱下方的 *記錄選項*),否則來自個別步驟的日誌檔案也會在此目錄中建立。
LOG_DIR <dir>
在版本 3.14 中新增。
用於儲存每個步驟的日誌的目錄。
DOWNLOAD_DIR <dir>
用於在解壓縮下載檔案之前儲存它們的目錄。此目錄僅供 URL 下載方法使用,所有其他下載方法都直接使用
SOURCE_DIR
。SOURCE_DIR <dir>
來源目錄,下載的內容將解壓縮到其中,或者對於非 URL 下載方法,儲存庫應簽出、複製等的目錄。如果未指定下載方法,則此目錄必須指向外部專案已解壓縮或複製/簽出的現有目錄。
注意
如果指定了下載方法,則可能會刪除來源目錄的任何現有內容。只有 URL 下載方法會檢查此目錄是否遺失或為空,然後才啟動下載,如果目錄不為空,則會停止並顯示錯誤。所有其他下載方法都會靜默捨棄來源目錄的任何先前內容。
BINARY_DIR <dir>
指定建置目錄位置。如果啟用
BUILD_IN_SOURCE
,則會忽略此選項。INSTALL_DIR <dir>
要放置在
<INSTALL_DIR>
佔位符中的安裝前綴。這實際上並不會將外部專案設定為安裝到給定的前綴。必須透過將適當的引數傳遞到外部專案設定步驟來完成,例如使用<INSTALL_DIR>
。
如果未指定上述任何 ..._DIR
選項,則其預設值計算如下。如果給定了 PREFIX
選項或設定了 EP_PREFIX
目錄屬性,則外部專案將在指定的前綴下建置和安裝
TMP_DIR = <prefix>/tmp
STAMP_DIR = <prefix>/src/<name>-stamp
DOWNLOAD_DIR = <prefix>/src
SOURCE_DIR = <prefix>/src/<name>
BINARY_DIR = <prefix>/src/<name>-build
INSTALL_DIR = <prefix>
LOG_DIR = <STAMP_DIR>
否則,如果設定了 EP_BASE
目錄屬性,則外部專案的組件將儲存在指定的基礎目錄下
TMP_DIR = <base>/tmp/<name>
STAMP_DIR = <base>/Stamp/<name>
DOWNLOAD_DIR = <base>/Download/<name>
SOURCE_DIR = <base>/Source/<name>
BINARY_DIR = <base>/Build/<name>
INSTALL_DIR = <base>/Install/<name>
LOG_DIR = <STAMP_DIR>
如果未指定 PREFIX
、EP_PREFIX
或 EP_BASE
,則預設值是將 PREFIX
設定為 <name>-prefix
。相對路徑是相對於呼叫 CMAKE_CURRENT_BINARY_DIR
時的 CMAKE_CURRENT_BINARY_DIR
來解釋。
下載步驟選項¶
如果使用 SOURCE_DIR
選項指向現有的非空目錄,則可以省略下載方法。否則,必須指定以下下載方法之一(不應給出多個下載方法)或提供自訂的 DOWNLOAD_COMMAND
。
DOWNLOAD_COMMAND <cmd>...
覆寫用於下載步驟的命令(支援
產生器 表達式
)。如果指定了此選項,則所有其他下載選項都將被忽略。為<cmd>
提供空字串實際上會停用下載步驟。
URL¶
URL <url1> [<url2>...]
外部專案來源的路徑和/或 URL 清單。當給出多個 URL 時,將依次嘗試它們,直到其中一個成功。URL 可以是本機檔案系統中的普通路徑(在這種情況下,它必須是唯一提供的 URL)或
file(DOWNLOAD)
命令支援的任何可下載 URL。本機檔案系統路徑可以指向現有目錄或封存檔案,而 URL 預期指向可以視為封存的檔案。當使用封存時,除非設定了DOWNLOAD_NO_EXTRACT
選項以防止解壓縮,否則將自動解壓縮封存。封存類型是透過檢查實際內容而不是使用基於檔案副檔名的邏輯來確定的。在版本 3.7 中變更:允許多個 URL。
URL_HASH <algo>=<hashValue>
要下載的封存檔案的雜湊值。引數的格式應為
<algo>=<hashValue>
,其中algo
可以是file()
命令支援的任何雜湊演算法。強烈建議為 URL 下載指定此選項,因為它可以確保下載內容的完整性。它也用作先前下載檔案的檢查,如果本機目錄中已經有來自較早下載且與指定雜湊值相符的檔案,則可以完全避免連線到遠端位置。URL_MD5 <md5>
等效於
URL_HASH MD5=<md5>
。DOWNLOAD_NAME <fname>
用於下載檔案的檔案名稱。如果未給定,則使用 URL 的結尾來確定檔案名稱。此選項很少需要,預設名稱通常適用,並且通常不在
ExternalProject
模組內部的程式碼之外使用。DOWNLOAD_EXTRACT_TIMESTAMP <bool>
在版本 3.24 中新增。
當指定為 true 值時,解壓縮檔案的時間戳記將與封存中的時間戳記相符。當為 false 時,解壓縮檔案的時間戳記將反映執行解壓縮的時間。如果下載 URL 變更,則基於封存中的時間戳記可能會導致相依目標在可能應該重建時未重建。因此,除非檔案時間戳記在某些方面對專案很重要,否則請使用 false 值作為此選項。如果未給定
DOWNLOAD_EXTRACT_TIMESTAMP
,則預設為 false。請參閱原則CMP0135
。DOWNLOAD_NO_EXTRACT <bool>
在版本 3.6 中新增。
允許透過為此選項傳遞布林值 true 來停用下載步驟的解壓縮部分。如果未給定此選項,則下載的內容將在需要時自動解壓縮。如果已停用解壓縮,則下載檔案的完整路徑在後續步驟中或作為具有
ExternalProject_Get_Property()
命令的DOWNLOADED_FILE
屬性可用為<DOWNLOADED_FILE>
。DOWNLOAD_NO_PROGRESS <bool>
可用於停用記錄下載進度。如果未給定此選項,則將記錄下載進度訊息。
TIMEOUT <seconds>
檔案下載操作允許的最長時間。
INACTIVITY_TIMEOUT <seconds>
在版本 3.19 中新增。
在一段非活動時間後終止操作。
HTTP_USERNAME <username>
在版本 3.7 中新增。
如果需要驗證,則用於下載操作的使用者名稱。
HTTP_PASSWORD <password>
在版本 3.7 中新增。
如果需要驗證,則用於下載操作的密碼。
HTTP_HEADER <header1> [<header2>...]
在版本 3.7 中新增。
為下載操作提供任意 HTTP 標頭清單。這對於存取 AWS 等系統中的內容可能很有用。
TLS_VERSION <min>
在版本 3.30 中新增。
為
https://
URL 指定最小 TLS 版本。如果未提供此選項,則將改為使用CMAKE_TLS_VERSION
變數或CMAKE_TLS_VERSION
環境變數的值(請參閱file(DOWNLOAD)
)。此選項也適用於
git clone
叫用,儘管預設行為有所不同。如果未指定TLS_VERSION
選項、CMAKE_TLS_VERSION
變數或CMAKE_TLS_VERSION
環境變數,則行為將由 git 的預設值或使用者可能在全域層級設定的http.sslVersion
git config 選項決定。TLS_VERIFY <bool>
指定是否應為
https://
URL 執行憑證驗證。如果未提供此選項,則將改為使用CMAKE_TLS_VERIFY
變數或CMAKE_TLS_VERIFY
環境變數的值(請參閱file(DOWNLOAD)
)。如果這兩者都未設定,則不會執行憑證驗證。在無法提供URL_HASH
的情況下,此選項可以是替代的驗證措施。此選項也適用於
git clone
叫用,儘管預設行為有所不同。如果未指定TLS_VERIFY
選項、CMAKE_TLS_VERIFY
變數或CMAKE_TLS_VERIFY
環境變數,則行為將由 git 的預設值 (true) 或使用者可能在全域層級設定的http.sslVerify
git config 選項決定。在版本 3.6 中變更:先前此選項不適用於
git clone
叫用。在版本 3.30 中變更:先前未檢查
CMAKE_TLS_VERIFY
環境變數。TLS_CAINFO <file>
指定自訂憑證授權單位檔案,以在啟用
TLS_VERIFY
時使用。如果未指定此選項,則將改為使用CMAKE_TLS_CAINFO
變數的值(請參閱file(DOWNLOAD)
)NETRC <level>
在版本 3.11 中新增。
指定是否要將
.netrc
檔案用於操作。如果未指定此選項,則將改為使用CMAKE_NETRC
變數的值(請參閱file(DOWNLOAD)
)。有效層級為IGNORED
.netrc
檔案被忽略。這是預設值。OPTIONAL
.netrc
檔案是可選的,並且 URL 中的資訊是首選。將掃描檔案以尋找 URL 中未指定的任何資訊。REQUIRED
.netrc
檔案是必要的,並且 URL 中的資訊被忽略。
NETRC_FILE <file>
在版本 3.11 中新增。
如果
NETRC
層級為OPTIONAL
或REQUIRED
,則指定替代的.netrc
檔案,而不是您主目錄中的檔案。如果未指定此選項,則將改為使用CMAKE_NETRC_FILE
變數的值(請參閱file(DOWNLOAD)
)
在版本 3.1 中新增:新增了對 tbz2、.tar.xz、.txz 和 .7z 副檔名的支援。
Git¶
注意:如果使用此下載方法,則需要 1.6.5 或更高版本的 git。
GIT_REPOSITORY <url>
git 儲存庫的 URL。
git
命令理解的任何 URL 都可以使用。在版本 3.27 中變更:相對 URL 將根據父專案的遠端解析,但受
CMP0150
限制。請參閱原則文件,瞭解如何選取遠端,包括遠端選取可能會失敗的條件。本機檔案系統遠端應始終使用絕對路徑。GIT_TAG <tag>
Git 分支名稱、標籤或提交雜湊。請注意,分支名稱和標籤通常應指定為遠端名稱(即
origin/myBranch
而不是簡單的myBranch
)。這可確保如果遠端端點的標籤已移動或分支已重新基準化或歷史記錄已重寫,則本機複製仍將正確更新。但是,一般而言,出於多種原因,應優先指定提交雜湊如果本機複製已經具有與雜湊對應的提交,則每次重新執行 CMake 時都不需要執行
git fetch
來檢查變更。如果使用許多外部專案,這可以顯著加快速度。使用特定的 git 雜湊可確保主專案本身的歷史記錄可以完全追溯到外部專案演進中的特定點。如果改為使用分支或標籤名稱,則簽出主專案的特定提交不一定將整個建置釘選到外部專案生命週期中的特定點。缺乏這種確定性行為會使主專案失去可追溯性和可重複性。
如果啟用了
GIT_SHALLOW
,則GIT_TAG
僅適用於分支名稱和標籤。不允許使用提交雜湊。請注意,如果未提供,
GIT_TAG
預設為master
,而不是預設的 Git 分支名稱。GIT_REMOTE_NAME <name>
遠端的選用名稱。如果未指定此選項,則預設為
origin
。GIT_SUBMODULES <module>...
也應更新的特定 git 子模組。如果未提供此選項,則將更新所有 git 子模組。
在版本 3.16 中變更:當
CMP0097
設定為NEW
時,如果此值設定為空字串,則不會初始化或更新子模組。GIT_SUBMODULES_RECURSE <bool>
在版本 3.17 中新增。
指定 git 子模組(如果有的話)是否應透過將
--recursive
旗標傳遞給git submodule update
來遞迴更新。如果未指定,則預設為開啟。GIT_SHALLOW <bool>
在版本 3.6 中新增。
啟用此選項後,
git clone
操作將被賦予--depth 1
選項。這會執行淺層複製,從而避免下載整個歷史記錄,而是僅檢索由GIT_TAG
選項表示的提交。GIT_PROGRESS <bool>
在版本 3.8 中新增。
啟用後,此選項指示
git clone
操作透過傳遞--progress
選項來報告其進度。如果沒有此選項,則大型專案的複製步驟可能會顯示為使建置停滯,因為在複製操作完成之前不會記錄任何內容。雖然此選項可用於提供進度以防止建置出現停滯現象,但如果使用許多外部專案,它也可能使建置過於嘈雜。GIT_CONFIG <option1> [<option2>...]
在版本 3.8 中新增。
指定要傳遞給
git clone
的配置選項清單。列出的每個選項都將轉換為git clone
命令列上的其自身的--config <option>
,每個選項都需要採用key=value
形式。GIT_REMOTE_UPDATE_STRATEGY <strategy>
在版本 3.18 中新增。
當
GIT_TAG
引用遠端分支時,可以使用此選項來指定更新步驟的行為方式。<strategy>
必須是以下其中之一CHECKOUT
忽略本機分支,並始終簽出由
GIT_TAG
指定的分支。REBASE
嘗試將當前分支重新基準化到由
GIT_TAG
指定的分支。如果存在本機未提交的變更,它們將首先被暫存,並在重新基準化後再次彈出。如果重新基準化或彈出暫存的變更失敗,則中止重新基準化並停止並顯示錯誤。當不存在GIT_REMOTE_UPDATE_STRATEGY
時,這是預設策略,除非預設值已被CMAKE_EP_GIT_REMOTE_UPDATE_STRATEGY
覆寫(請參閱下文)。請注意,如果GIT_TAG
中指定的分支與當前正在追蹤的上游分支不同,則執行重新基準化是不安全的。在這種情況下,REBASE
將靜默地被視為CHECKOUT
。REBASE_CHECKOUT
與
REBASE
相同,但如果重新基準化失敗,則將在重新基準化之前的原始HEAD
位置建立帶註解的標籤,然後像CHECKOUT
策略一樣簽出GIT_TAG
。儲存在帶註解標籤上的訊息將提供有關嘗試的資訊,並且標籤名稱將包含時間戳記,以便每次失敗的執行都會新增一個新標籤。此策略可確保不會遺失任何變更,但如果GIT_TAG
引用有效的 ref,則更新應始終成功,除非存在無法成功彈出的未提交變更。
可以設定變數
CMAKE_EP_GIT_REMOTE_UPDATE_STRATEGY
以覆寫預設策略。專案不應設定此變數,它旨在供使用者設定。它主要用於持續整合腳本中,以確保當遠端分支上的歷史記錄被重寫時,建置不會以意外的變更或由於重新基準化操作期間的衝突而導致的建置失敗結束。
Subversion¶
SVN_REPOSITORY <url>
Subversion 儲存庫的 URL。
SVN_REVISION -r<rev>
要從 Subversion 儲存庫簽出的修訂版本。
SVN_USERNAME <username>
Subversion 簽出和更新的使用者名稱。
SVN_PASSWORD <password>
Subversion 簽出和更新的密碼。
SVN_TRUST_CERT <bool>
指定是否信任 Subversion 伺服器站點憑證。如果啟用,則
--trust-server-cert
選項將傳遞到svn
簽出和更新命令。
Mercurial¶
HG_REPOSITORY <url>
mercurial 儲存庫的 URL。
HG_TAG <tag>
Mercurial 分支名稱、標籤或提交 ID。
CVS¶
CVS_REPOSITORY <cvsroot>
CVS 儲存庫的 CVSROOT。
CVS_MODULE <mod>
要從 CVS 儲存庫簽出的模組。
CVS_TAG <tag>
要從 CVS 儲存庫簽出的標籤。
更新步驟選項¶
每當重新執行 CMake 時,預設情況下,如果下載方法支援更新(例如,如果 GIT_TAG
未引用特定提交,則會檢查 git 儲存庫),則外部專案的來源將會更新。
UPDATE_COMMAND <cmd>...
覆寫下載方法 (download method) 的更新步驟 (update step),使用自訂命令。此命令可使用
產生器 表達式
。UPDATE_DISCONNECTED <bool>
在版本 3.2 中新增。
啟用後,此選項會略過更新步驟(但請參閱下文瞭解變更行為,在某些情況下並非如此)。它不會阻止下載步驟。更新步驟仍然可以作為步驟目標新增(請參閱
ExternalProject_Add_StepTargets()
),並手動呼叫。如果您希望允許開發人員在斷開網路連線時建置專案,這會很有用(儘管下載步驟可能仍然需要網路連線)。在版本 3.27 中變更:當
UPDATE_DISCONNECTED
為 true 時,如果更新或下載步驟的任何詳細資訊變更,則將會執行更新步驟。此外,如果使用 git 下載/更新方法,更新邏輯將會修改為略過連線遠端伺服器的嘗試。如果GIT_TAG
提及本機未知的 ref,更新步驟將會停止並出現嚴重錯誤。當此選項存在時,通常建議將該值設為開發人員可控制的快取變數,而不是硬式編碼。如果未提供此選項,則預設值取自
EP_UPDATE_DISCONNECTED
目錄屬性。如果該屬性也未定義,則更新會照常執行。EP_UPDATE_DISCONNECTED
目錄屬性旨在方便控制專案目錄階層中整個區段的UPDATE_DISCONNECTED
行為,並且可能是讓開發人員控制是否執行更新的更方便方法(假設專案也提供快取變數或一些其他方便的方法來設定目錄屬性)。這可能會導致自動為
download
步驟建立步驟目標。請參閱政策CMP0114
。
修補步驟選項¶
PATCH_COMMAND <cmd>...
指定自訂命令,在更新後修補來源。預設情況下,未定義修補命令。請注意,定義適當且穩健執行的修補命令可能非常困難,尤其是對於 git 等下載方法,其中變更
GIT_TAG
不會捨棄先前修補程式的變更,但在更新到新標籤後,修補命令將再次被呼叫。
設定步驟選項¶
設定步驟在下載和更新步驟之後執行。預設情況下,外部專案會被假定為 CMake 專案,但如果需要,可以覆寫此設定。
CONFIGURE_COMMAND <cmd>...
預設設定命令會執行 CMake,並帶有一些基於主要專案的選項。新增的選項通常僅是使用與主要專案相同產生器所需的選項,但可以指定
CMAKE_GENERATOR
選項來覆寫此設定。專案負責新增任何工具鏈詳細資訊、旗標或它想要從主要專案重複使用或以其他方式指定的設定(請參閱下文的CMAKE_ARGS
、CMAKE_CACHE_ARGS
和CMAKE_CACHE_DEFAULT_ARGS
)。對於非 CMake 外部專案,必須使用
CONFIGURE_COMMAND
選項來覆寫預設設定命令(支援產生器 表達式
)。對於不需要設定步驟的專案,請指定此選項,並使用空字串作為要執行的命令。CMAKE_COMMAND /.../cmake
為設定步驟指定替代的 cmake 可執行檔(使用絕對路徑)。通常不建議這樣做,因為通常希望在整個建置過程中使用相同的 CMake 版本。如果已使用
CONFIGURE_COMMAND
指定自訂設定命令,則會忽略此選項。CMAKE_GENERATOR <gen>
覆寫用於設定步驟的 CMake 產生器。如果沒有此選項,將會使用與主要建置相同的產生器。如果已使用
CONFIGURE_COMMAND
選項指定自訂設定命令,則會忽略此選項。CMAKE_GENERATOR_PLATFORM <platform>
在版本 3.1 中新增。
將產生器特定的平台名稱傳遞給 CMake 命令(請參閱
CMAKE_GENERATOR_PLATFORM
)。如果沒有CMAKE_GENERATOR
選項就提供此選項,則會發生錯誤。CMAKE_GENERATOR_TOOLSET <toolset>
將產生器特定的工具集名稱傳遞給 CMake 命令(請參閱
CMAKE_GENERATOR_TOOLSET
)。如果沒有CMAKE_GENERATOR
選項就提供此選項,則會發生錯誤。CMAKE_GENERATOR_INSTANCE <instance>
在版本 3.11 中新增。
將產生器特定的執行個體選取傳遞給 CMake 命令(請參閱
CMAKE_GENERATOR_INSTANCE
)。如果沒有CMAKE_GENERATOR
選項就提供此選項,則會發生錯誤。CMAKE_ARGS <arg>...
指定的引數會傳遞至 cmake 命令列。它們可以是 cmake 命令可理解的任何引數,而不僅限於由
-D...
引數定義的快取值(另請參閱CMake 選項
)。在版本 3.3 中新增:引數可以使用
產生器 表達式
。CMAKE_CACHE_ARGS <arg>...
這是指定快取變數的替代方法,在命令列長度問題可能成為問題時使用。引數應為
-Dvar:STRING=value
格式,然後將其轉換為 CMakeset()
命令,並使用FORCE
選項。這些set()
命令會寫入預先載入指令碼,然後使用cmake -C
命令列選項套用。在版本 3.3 中新增:引數可以使用
產生器 表達式
。CMAKE_CACHE_DEFAULT_ARGS <arg>...
在版本 3.2 中新增。
這與
CMAKE_CACHE_ARGS
選項相同,只是set()
命令不包含FORCE
關鍵字。這表示這些值僅作為初始預設值,並且不會覆寫先前執行中已設定的任何變數。請謹慎使用此選項,因為它可能會導致不同的行為,具體取決於建置是從全新的建置目錄開始,還是重複使用先前的建置內容。在版本 3.15 中新增:如果 CMake 產生器是
Green Hills MULTI
且未被覆寫,則原始專案的 GHS 工具集和目標系統自訂快取變數的設定會傳播到外部專案中。SOURCE_SUBDIR <dir>
在版本 3.7 中新增。
當未指定
CONFIGURE_COMMAND
選項時,設定步驟會假定外部專案在其來源樹狀結構的頂層(即在SOURCE_DIR
中)具有CMakeLists.txt
檔案。SOURCE_SUBDIR
選項可用於指向來源樹狀結構中的替代目錄,以用作 CMake 來源樹狀結構的頂層。這必須是相對路徑,並且將被解釋為相對於SOURCE_DIR
。在版本 3.14 中新增:當啟用
BUILD_IN_SOURCE
選項時,BUILD_COMMAND
用於指向來源樹狀結構中的替代目錄。CONFIGURE_HANDLED_BY_BUILD <bool>
在版本 3.20 中新增。
啟用此選項會放寬設定步驟對其他外部專案的依賴性,使其僅為順序依賴 (order-only)。這表示設定步驟將在建置其外部專案依賴項之後執行,但當其外部專案依賴項之一重建時,它不會被標記為 dirty。當建置步驟足夠聰明,可以判斷設定步驟是否需要重新執行時,可以啟用此選項。CMake 和 Meson 是建置系統的範例,其建置步驟足夠聰明,可以知道設定步驟是否需要重新執行。
建置步驟選項¶
如果設定步驟假定外部專案使用 CMake 作為其建置系統,則建置步驟也將如此。否則,建置步驟將假定為基於 Makefile 的建置,並且僅執行不帶引數的 make
作為預設建置步驟。如果需要,可以使用自訂建置命令覆寫此設定。
如果主要專案和外部專案都使用 make 作為其建置工具,則外部專案的建置步驟會使用 $(MAKE)
作為遞迴 make 呼叫。這會將一些建置工具設定從主要專案傳遞到外部專案。如果主要專案或外部專案都沒有使用 make,則除了設定步驟建立的設定之外,不會將任何建置工具設定傳遞到外部專案(即,即使主要專案也使用 ninja
作為其建置工具,在主要專案中執行 ninja -v
也**不會**將 -v
傳遞到外部專案的建置步驟)。
BUILD_COMMAND <cmd>...
覆寫預設建置命令(支援
產生器 表達式
)。如果未提供此選項,將會選擇預設建置命令,以便以最合適的方式與主要建置整合(例如,對於 Makefile 產生器使用遞迴make
,或者如果專案使用 CMake 建置,則使用cmake --build
)。可以將此選項指定為空字串作為命令,使建置步驟不執行任何操作。BUILD_IN_SOURCE <bool>
啟用此選項後,建置將直接在外部專案的來源樹狀結構中完成。通常應避免這樣做,通常首選使用單獨的建置目錄,但當外部專案假定為 in-source 建置時,它可能很有用。如果在 in-source 建置,則不應指定
BINARY_DIR
選項。BUILD_ALWAYS <bool>
啟用此選項會強制始終執行建置步驟。這可能是穩健地確保評估外部專案自身建置依賴項的最簡單方法,而不是依賴基於預設成功時間戳記的方法。除非開發人員預期會以無法透過步驟目標依賴性檢測到的方式修改外部專案建置所依賴的某些內容,否則通常不需要此選項(例如,
SOURCE_DIR
在沒有下載方法的情況下使用,並且開發人員可能會修改SOURCE_DIR
中的來源)。BUILD_BYPRODUCTS <file>...
在版本 3.2 中新增。
指定將由建置命令產生的檔案,但這些檔案的修改時間可能會或可能不會在後續建置中更新。當使用
Ninja
產生器時,這也可能是顯式宣告依賴項所必需的。這些最終會作為BYPRODUCTS
傳遞到建置步驟自身對add_custom_command()
的底層呼叫,其中有其他文件記錄。BUILD_JOB_SERVER_AWARE <bool>
在版本 3.28 中新增。
指定建置步驟知道 GNU Make 工作伺服器。請參閱
add_custom_command()
文件中關於其JOB_SERVER_AWARE
選項的詳細資訊。此選項僅在指定顯式BUILD_COMMAND
時相關。
安裝步驟選項¶
如果設定步驟假定外部專案使用 CMake 作為其建置系統,則安裝步驟也將如此。否則,安裝步驟將假定為基於 Makefile 的建置,並且僅執行 make install
作為預設建置步驟。如果需要,可以使用自訂安裝命令覆寫此設定。
INSTALL_COMMAND <cmd>...
外部專案自身的安裝步驟會作為主要專案的建置一部分被呼叫。它在外部專案的建置步驟之後完成,並且可能在外部專案的測試步驟之前或之後(請參閱下文的
TEST_BEFORE_INSTALL
選項)。外部專案的安裝規則不是主要專案安裝規則的一部分,因此如果主要建置中應安裝來自外部專案的任何內容,則需要在主要建置中將這些內容指定為額外的install()
命令。預設安裝步驟會建置外部專案的install
目標,但可以使用此選項的自訂命令覆寫此設定(支援產生器 表達式
)。將空字串作為<cmd>
傳遞會使安裝步驟不執行任何操作。INSTALL_BYPRODUCTS <file>...
在版本 3.26 中新增。
指定將由安裝命令產生的檔案,但這些檔案的修改時間可能會或可能不會在後續安裝中更新。當使用
Ninja
產生器時,這也可能是顯式宣告依賴項所必需的。這些最終會作為BYPRODUCTS
傳遞到安裝步驟自身對add_custom_command()
的底層呼叫,其中有其他文件記錄。INSTALL_JOB_SERVER_AWARE <bool>
在版本 4.0 中新增。
指定安裝步驟知道 GNU Make 工作伺服器。請參閱
add_custom_command()
文件中關於其JOB_SERVER_AWARE
選項的詳細資訊。此選項僅在指定顯式INSTALL_COMMAND
時相關。
注意
如果在建置主要專案時設定了 CMAKE_INSTALL_MODE
環境變數,則只有在滿足以下條件時才會生效:
主要專案的設定步驟假定外部專案使用 CMake 作為其建置系統。
外部專案的安裝命令實際上會執行。請注意,由於
ExternalProject
可能在內部使用時間戳記的方式,如果安裝步驟依賴的任何內容都不需要重新執行,則安裝命令也可能不需要執行。
另請注意,ExternalProject
不會檢查 CMAKE_INSTALL_MODE
環境變數是否從一次執行變更為另一次執行。
測試步驟選項¶
僅當提供至少一個以下 TEST_...
選項時,才會定義測試步驟。
TEST_COMMAND <cmd>...
覆寫預設測試命令(支援
產生器 表達式
)。如果未提供此選項,測試步驟的預設行為是建置外部專案自身的test
目標。可以將此選項指定為<cmd>
作為空字串,這允許仍然定義測試步驟,但它將不執行任何操作。如果提供空字串作為測試命令,請勿指定任何其他TEST_...
選項,但如果不需要測試步驟目標,則最好完全省略所有TEST_...
選項。TEST_BEFORE_INSTALL <bool>
啟用此選項後,測試步驟將在安裝步驟之前執行。預設行為是測試步驟在安裝步驟之後執行。
TEST_AFTER_INSTALL <bool>
此選項主要用作指示需要測試步驟但所有預設行為都已足夠的方式。使用布林值 true 值指定此選項可確保定義測試步驟,並且它在安裝步驟之後執行。如果同時啟用
TEST_BEFORE_INSTALL
和TEST_AFTER_INSTALL
,則後者會被靜默忽略。TEST_EXCLUDE_FROM_MAIN <bool>
在版本 3.2 中新增。
如果啟用,主要建置的預設 ALL 目標將不依賴於測試步驟。這可能是確保定義測試步驟但僅在手動請求時才呼叫它的有用方法。這可能會導致自動為
install
或build
步驟建立步驟目標。請參閱政策CMP0114
。
輸出記錄選項¶
以下每個 LOG_...
選項可用於將相關步驟包裝在指令碼中,以將其輸出捕獲到檔案。記錄檔將在提供的 LOG_DIR
中建立,否則將在 STAMP_DIR
目錄中建立,並使用步驟特定的檔案名稱。
LOG_DOWNLOAD <bool>
啟用後,下載步驟的輸出會記錄到檔案。
LOG_UPDATE <bool>
啟用後,更新步驟的輸出會記錄到檔案。
LOG_PATCH <bool>
在版本 3.14 中新增。
啟用後,修補步驟的輸出會記錄到檔案。
LOG_CONFIGURE <bool>
啟用後,設定步驟的輸出會記錄到檔案。
LOG_BUILD <bool>
啟用後,建置步驟的輸出會記錄到檔案。
LOG_INSTALL <bool>
啟用後,安裝步驟的輸出會記錄到檔案。
LOG_TEST <bool>
啟用後,測試步驟的輸出會記錄到檔案。
LOG_MERGED_STDOUTERR <bool>
在版本 3.14 中新增。
啟用後,對於任何輸出記錄到檔案的步驟,stdout 和 stderr 將會合併。
LOG_OUTPUT_ON_FAILURE <bool>
在版本 3.14 中新增。
僅當至少啟用其他
LOG_<step>
選項之一時,此選項才有效。如果啟用檔案記錄的步驟發生錯誤,並且LOG_OUTPUT_ON_FAILURE
設定為 true,則該步驟的輸出將會列印到主控台。對於記錄大量輸出的情況,可能只會將該輸出的結尾列印到主控台。
終端機存取選項¶
在版本 3.4 中新增。
在某些情況下,可以讓步驟直接存取終端機。讓步驟存取終端機可能允許它接收所需的終端機輸入,例如未由其他選項提供的驗證詳細資訊。使用 Ninja
產生器,這些選項將步驟放置在 console
工作 池
中。可以透過以下選項單獨讓每個步驟存取終端機:
USES_TERMINAL_DOWNLOAD <bool>
讓下載步驟存取終端機。
USES_TERMINAL_UPDATE <bool>
讓更新步驟存取終端機。
USES_TERMINAL_PATCH <bool>
在版本 3.23 中新增。
讓修補步驟存取終端機。
USES_TERMINAL_CONFIGURE <bool>
讓設定步驟存取終端機。
USES_TERMINAL_BUILD <bool>
讓建置步驟存取終端機。
USES_TERMINAL_INSTALL <bool>
讓安裝步驟存取終端機。
USES_TERMINAL_TEST <bool>
讓測試步驟存取終端機。
目標選項¶
DEPENDS <targets>...
指定外部專案所依賴的其他目標。其他目標將在執行外部專案的任何步驟之前更新到最新狀態。由於外部專案在內部為每個步驟使用額外的自訂目標,因此
DEPENDS
選項是確保所有這些步驟都依賴於其他目標的最方便方法。僅執行add_dependencies(<name> <targets>)
不會使任何步驟依賴於<targets>
。EXCLUDE_FROM_ALL <bool>
啟用後,此選項會將外部專案從主要建置的預設 ALL 目標中排除。
STEP_TARGETS <step-target>...
為指定的步驟產生自訂目標。如果需要手動觸發步驟,或者如果需要將它們用作其他目標的依賴項,則這是必需的。如果未指定此選項,則預設值取自
EP_STEP_TARGETS
目錄屬性。請參閱下文的ExternalProject_Add_StepTargets()
,以進一步討論此選項的效果。INDEPENDENT_STEP_TARGETS <step-target>...
自版本 3.19 起已棄用:僅當政策
CMP0114
未設定為NEW
時,才允許使用。為指定的步驟產生自訂目標,並阻止將通常的依賴項套用至這些目標。如果未指定此選項,則預設值取自
EP_INDEPENDENT_STEP_TARGETS
目錄屬性。此選項主要用於允許獨立驅動個別步驟,例如對於 CDash 設定,其中每個步驟應單獨啟動和報告,而不是作為一個完整的建置。請參閱下文的ExternalProject_Add_StepTargets()
,以進一步討論此選項的效果。
雜項選項¶
LIST_SEPARATOR <sep>
對於任何各種
..._COMMAND
選項,以及CMAKE_ARGS
,ExternalProject
將在指定的命令列中將<sep>
替換為;
。這可用於確保命令中包含文字;
,在直接使用時,否則會被解釋為 CMake API 的引數分隔符號。請注意,應選擇分隔符號以避免與序列的非清單分隔符號用法混淆。例如,使用LIST_SEPARATOR
允許將清單值傳遞到命令列上的 CMake 快取變數ExternalProject_Add(example ... # Download options, etc. LIST_SEPARATOR "," CMAKE_ARGS "-DCMAKE_PREFIX_PATH:STRING=${first_prefix},${second_prefix}" )
COMMAND <cmd>...
任何其他
..._COMMAND
選項都可以透過在它們後面加上所需數量的COMMAND ...
選項來附加其他命令(支援產生器 表達式
)。例如ExternalProject_Add(example ... # Download options, etc. BUILD_COMMAND ${CMAKE_COMMAND} -E echo "Starting $<CONFIG> build" COMMAND ${CMAKE_COMMAND} --build <BINARY_DIR> --config $<CONFIG> COMMAND ${CMAKE_COMMAND} -E echo "$<CONFIG> build complete" )
還應注意,每個建置步驟都是透過呼叫 ExternalProject_Add_Step()
建立的。請參閱該命令的文件記錄,瞭解某些選項支援的自動替換。
取得專案屬性¶
- ExternalProject_Get_Property¶
ExternalProject_Get_Property()
函數檢索外部專案目標屬性ExternalProject_Get_Property(<name> <prop1> [<prop2>...])
此函數將屬性值儲存在同名的變數中。屬性名稱對應於
ExternalProject_Add()
的關鍵字引數名稱。例如,來源目錄可以像這樣檢索ExternalProject_Get_property(myExtProj SOURCE_DIR) message("Source dir of myExtProj = ${SOURCE_DIR}")
顯式步驟管理¶
ExternalProject_Add()
函數本身通常足以將外部專案整合到主要建置中。某些情境需要額外的工作來實現所需的行為,例如加入自訂步驟或使步驟可作為手動觸發的目標。 ExternalProject_Add_Step()
、ExternalProject_Add_StepTargets()
和 ExternalProject_Add_StepDependencies
函數提供了實現此類步驟級功能的更低層級控制。
- ExternalProject_Add_Step¶
ExternalProject_Add_Step()
函數為先前呼叫ExternalProject_Add()
定義的外部專案指定額外的自訂步驟ExternalProject_Add_Step(<name> <step> [<option>...])
<name>
與傳遞給原始ExternalProject_Add()
呼叫的名稱相同。指定的<step>
不得為預定義步驟之一 (mkdir
、download
、update
、patch
、configure
、build
、install
或test
)。支援的選項如下COMMAND <cmd>...
此自訂步驟要執行的命令列 (支援
generator expressions
)。此選項可以重複多次以指定要依序執行的多個命令。COMMENT "<text>..."
自訂步驟執行時要列印的文字。
DEPENDEES <step>...
此步驟所依賴的其他步驟 (自訂或預定義)。
DEPENDERS <step>...
依賴此新自訂步驟的其他步驟 (自訂或預定義)。
DEPENDS <file>...
此自訂步驟所依賴的檔案。
INDEPENDENT <bool>
在版本 3.19 中新增。
指定此步驟是否獨立於
ExternalProject_Add()
的DEPENDS
選項指定的外部依賴項。預設值為FALSE
。標記為獨立的步驟可能僅依賴於其他標記為獨立的步驟。請參閱政策CMP0114
。請注意,此處「獨立」一詞的使用僅指獨立於
DEPENDS
選項指定的外部目標,並且與步驟對其他步驟的依賴性正交。如果透過
ExternalProject_Add()
STEP_TARGETS
選項或ExternalProject_Add_StepTargets()
函數為獨立步驟建立步驟目標,則它將不依賴於外部目標,但可能依賴於其他步驟的目標。BYPRODUCTS <file>...
在版本 3.2 中新增。
此自訂步驟將產生的檔案,但這些檔案的修改時間可能或可能不會在後續建置中更新。當使用
Ninja
產生器時,也可能需要明確宣告依賴項。此檔案清單最終將作為BYPRODUCTS
選項傳遞給用於在內部實作自訂步驟的add_custom_command()
,該函數具有額外的文件說明。ALWAYS <bool>
啟用後,此選項指定自訂步驟應始終執行 (即始終被視為過時)。
JOB_SERVER_AWARE <bool>
在版本 3.28 中新增。
指定自訂步驟知道 GNU Make 工作伺服器。請參閱
add_custom_command()
文件中關於其JOB_SERVER_AWARE
選項的詳細資訊。EXCLUDE_FROM_MAIN <bool>
啟用後,此選項指定外部專案的主要目標不依賴於自訂步驟。這可能會導致自動為此步驟所依賴的步驟建立步驟目標。請參閱政策
CMP0114
。WORKING_DIRECTORY <dir>
指定在執行自訂步驟命令之前要設定的工作目錄。如果未指定此選項,則目錄將為呼叫
ExternalProject_Add_Step()
時CMAKE_CURRENT_BINARY_DIR
的值。LOG <bool>
如果設定,這會導致自訂步驟的輸出被捕獲到外部專案的
LOG_DIR
(如果提供) 或STAMP_DIR
中的檔案。USES_TERMINAL <bool>
如果啟用,這會讓自訂步驟在可能的情況下直接存取終端機。
每個標準和自訂步驟的命令列、註解、工作目錄和副產品都會經過處理,以將符記
<SOURCE_DIR>
、<SOURCE_SUBDIR>
、<BINARY_DIR>
、<INSTALL_DIR>
<TMP_DIR>
、<DOWNLOAD_DIR>
和<DOWNLOADED_FILE>
替換為原始ExternalProject_Add()
呼叫中定義的對應屬性值。Added in version 3.3: 符記替換擴展到副產品。
Added in version 3.11:
<DOWNLOAD_DIR>
替換符記。
- ExternalProject_Add_StepTargets¶
ExternalProject_Add_StepTargets()
函數為列出的步驟產生目標。每個建立的目標的名稱格式為<name>-<step>
ExternalProject_Add_StepTargets(<name> <step1> [<step2>...])
為步驟建立目標使其可以用作另一個目標的依賴項或手動觸發。為特定步驟設定目標也允許透過在建置命令列上指定目標來獨立驅動它們。例如,您可能正在提交到基於子專案的儀表板,您希望驅動建置的配置部分,然後提交到儀表板,然後是建置部分,然後是測試。如果您調用依賴於步驟依賴鏈中途的步驟的自訂目標,則也會執行所有先前的步驟,以確保一切都是最新的。
在內部,
ExternalProject_Add()
呼叫ExternalProject_Add_Step()
來建立每個步驟。如果指定了任何STEP_TARGETS
,則在ExternalProject_Add_Step()
之後也會呼叫ExternalProject_Add_StepTargets()
。即使STEP_TARGETS
選項中未提及步驟,仍然可以在稍後呼叫ExternalProject_Add_StepTargets()
以手動定義步驟的目標。ExternalProject_Add()
的STEP_TARGETS
選項通常是確保為感興趣的特定步驟建立目標的最簡單方法。對於自訂步驟,如果也應為該自訂步驟建立目標,則必須明確呼叫ExternalProject_Add_StepTargets()
。這兩個選項的替代方案是填入EP_STEP_TARGETS
目錄屬性。它充當步驟目標選項的預設值,並且可以節省在定義多個外部專案時必須重複指定相同的步驟目標集。Added in version 3.19: 如果
CMP0114
設定為NEW
,步驟目標完全負責保存實作其步驟的自訂命令。ExternalProject_Add
建立的主要目標依賴於步驟目標,而步驟目標彼此依賴。目標級依賴性與每個步驟的自訂命令使用的檔案級依賴性相符。使用ExternalProject_Add_Step()
的INDEPENDENT
選項建立的步驟目標不依賴於ExternalProject_Add()
的DEPENDS
選項指定的外部目標。預定義步驟mkdir
、download
、update
和patch
是獨立的。如果
CMP0114
不是NEW
,則可以使用以下已棄用的行為可以在
<name>
之後和第一個步驟之前立即指定已棄用的NO_DEPENDS
選項。如果指定了NO_DEPENDS
選項,則步驟目標將不依賴於外部專案的依賴項 (即不依賴於ExternalProject_Add()
建立的<name>
自訂目標的任何依賴項)。對於download
、update
和patch
步驟,這通常是安全的,因為它們通常不需要更新和建置依賴項。但是,為任何其他預定義步驟使用NO_DEPENDS
可能會破壞並行建置。僅在確定命名的步驟確實沒有依賴項時才使用NO_DEPENDS
。對於自訂步驟,請考慮自訂命令是否需要配置、建置和安裝依賴項。ExternalProject_Add()
的INDEPENDENT_STEP_TARGETS
選項或EP_INDEPENDENT_STEP_TARGETS
目錄屬性告訴函數在內部使用指定步驟的NO_DEPENDS
選項呼叫ExternalProject_Add_StepTargets()
。
- ExternalProject_Add_StepDependencies¶
在版本 3.2 中新增。
ExternalProject_Add_StepDependencies()
函數可用於為步驟新增依賴項。新增的依賴項必須是 CMake 已知的目標 (這些可以是普通的執行檔或程式庫目標、自訂目標,甚至另一個外部專案的步驟目標)ExternalProject_Add_StepDependencies(<name> <step> <target1> [<target2>...])
此函數會注意設定目標和檔案層級的依賴項,並確保並行建置不會中斷。當為
ExternalProject
模組產生的一些步驟目標新增依賴項時,應使用此函數代替add_dependencies()
。
範例¶
以下範例示範如何從 github 下載和建置一個名為 FooBar 的假設專案
include(ExternalProject)
ExternalProject_Add(foobar
GIT_REPOSITORY git@github.com:FooCo/FooBar.git
GIT_TAG origin/release/1.2.3
)
為了範例的緣故,也定義第二個名為 SecretSauce 的假設外部專案,它從 Web 伺服器下載。提供兩個 URL 以利用更快的內部網路 (如果可用),並回退到較慢的外部伺服器。該專案是一個典型的 Makefile
專案,沒有配置步驟,因此覆蓋了一些預設命令。建置僅需要建置 sauce 目標
find_program(MAKE_EXE NAMES gmake nmake make)
ExternalProject_Add(secretsauce
URL http://intranet.somecompany.com/artifacts/sauce-2.7.tgz
https://www.somecompany.com/downloads/sauce-2.7.zip
URL_HASH MD5=d41d8cd98f00b204e9800998ecf8427e
CONFIGURE_COMMAND ""
BUILD_COMMAND ${MAKE_EXE} sauce
)
假設 secretsauce
的建置步驟需要先建置 foobar
。這可以像這樣強制執行
ExternalProject_Add_StepDependencies(secretsauce build foobar)
另一種替代方案是為 foobar
的建置步驟建立自訂目標,並使 secretsauce
依賴於該目標,而不是整個 foobar
專案。這意味著 foobar
只需要建置,它不需要在可以建置 secretsauce
之前執行其安裝或測試步驟。依賴項也可以與 secretsauce
專案一起定義
ExternalProject_Add_StepTargets(foobar build)
ExternalProject_Add(secretsauce
URL http://intranet.somecompany.com/artifacts/sauce-2.7.tgz
https://www.somecompany.com/downloads/sauce-2.7.zip
URL_HASH MD5=d41d8cd98f00b204e9800998ecf8427e
CONFIGURE_COMMAND ""
BUILD_COMMAND ${MAKE_EXE} sauce
DEPENDS foobar-build
)
目標可以與 foobar
專案本身一起定義,而不是呼叫 ExternalProject_Add_StepTargets()
ExternalProject_Add(foobar
GIT_REPOSITORY git@github.com:FooCo/FooBar.git
GIT_TAG origin/release/1.2.3
STEP_TARGETS build
)
如果許多外部專案應具有相同的步驟目標集,則設定目錄屬性可能更方便。可以在使用 ExternalProject_Add()
建立外部專案之前,透過設定 EP_STEP_TARGETS
目錄屬性來自動建立 build
步驟目標
set_property(DIRECTORY PROPERTY EP_STEP_TARGETS build)
最後,假設 secretsauce
提供了一個名為 makedoc
的腳本,可用於產生自己的文件。進一步假設腳本期望輸出目錄作為唯一參數提供,並且應從 secretsauce
來源目錄執行。可以像這樣定義自訂步驟和觸發腳本的自訂目標
ExternalProject_Add_Step(secretsauce docs
COMMAND <SOURCE_DIR>/makedoc <BINARY_DIR>
WORKING_DIRECTORY <SOURCE_DIR>
COMMENT "Building secretsauce docs"
ALWAYS TRUE
EXCLUDE_FROM_MAIN TRUE
)
ExternalProject_Add_StepTargets(secretsauce docs)
然後可以從主要建置中觸發自訂步驟,如下所示
cmake --build . --target secretsauce-docs