diff options
author | Craig Scott <craig.scott@crascit.com> | 2020-08-23 08:38:47 (GMT) |
---|---|---|
committer | Craig Scott <craig.scott@crascit.com> | 2020-08-23 08:38:47 (GMT) |
commit | b972e25276186ea43879dccfab50f43024f44390 (patch) | |
tree | 9541ac0c0c4f316e3e1a2aab0491a695ae39212b | |
parent | 269d1a86249ea037a2884133daffc8c44a38d926 (diff) | |
download | CMake-b972e25276186ea43879dccfab50f43024f44390.zip CMake-b972e25276186ea43879dccfab50f43024f44390.tar.gz CMake-b972e25276186ea43879dccfab50f43024f44390.tar.bz2 |
FetchContent: Fix SOURCE_DIR, BUILD_DIR when disconnected or overridden
Fixes: #21123
-rw-r--r-- | Modules/FetchContent.cmake | 41 | ||||
-rw-r--r-- | Tests/RunCMake/FetchContent/DirOverrides.cmake | 25 | ||||
-rw-r--r-- | Tests/RunCMake/FetchContent/DirOverridesDisconnected.cmake | 18 | ||||
-rw-r--r-- | Tests/RunCMake/FetchContent/RunCMakeTest.cmake | 15 |
4 files changed, 86 insertions, 13 deletions
diff --git a/Modules/FetchContent.cmake b/Modules/FetchContent.cmake index c85e2d8..acf2a94 100644 --- a/Modules/FetchContent.cmake +++ b/Modules/FetchContent.cmake @@ -1038,6 +1038,11 @@ function(FetchContent_Populate contentName) message(FATAL_ERROR "Content ${contentName} already populated in ${${contentNameLower}_SOURCE_DIR}") endif() + __FetchContent_getSavedDetails(${contentName} contentDetails) + if("${contentDetails}" STREQUAL "") + message(FATAL_ERROR "No details have been set for content: ${contentName}") + endif() + string(TOUPPER ${contentName} contentNameUpper) set(FETCHCONTENT_SOURCE_DIR_${contentNameUpper} "${FETCHCONTENT_SOURCE_DIR_${contentNameUpper}}" @@ -1045,14 +1050,35 @@ function(FetchContent_Populate contentName) if(FETCHCONTENT_SOURCE_DIR_${contentNameUpper}) # The source directory has been explicitly provided in the cache, - # so no population is required + # so no population is required. The build directory may still be specified + # by the declared details though. set(${contentNameLower}_SOURCE_DIR "${FETCHCONTENT_SOURCE_DIR_${contentNameUpper}}") - set(${contentNameLower}_BINARY_DIR "${FETCHCONTENT_BASE_DIR}/${contentNameLower}-build") + + cmake_parse_arguments(savedDetails "" "BINARY_DIR" "" ${contentDetails}) + + if(savedDetails_BINARY_DIR) + set(${contentNameLower}_BINARY_DIR ${savedDetails_BINARY_DIR}) + else() + set(${contentNameLower}_BINARY_DIR "${FETCHCONTENT_BASE_DIR}/${contentNameLower}-build") + endif() elseif(FETCHCONTENT_FULLY_DISCONNECTED) - # Bypass population and assume source is already there from a previous run - set(${contentNameLower}_SOURCE_DIR "${FETCHCONTENT_BASE_DIR}/${contentNameLower}-src") - set(${contentNameLower}_BINARY_DIR "${FETCHCONTENT_BASE_DIR}/${contentNameLower}-build") + # Bypass population and assume source is already there from a previous run. + # Declared details may override the default source or build directories. + + cmake_parse_arguments(savedDetails "" "SOURCE_DIR;BINARY_DIR" "" ${contentDetails}) + + if(savedDetails_SOURCE_DIR) + set(${contentNameLower}_SOURCE_DIR ${savedDetails_SOURCE_DIR}) + else() + set(${contentNameLower}_SOURCE_DIR "${FETCHCONTENT_BASE_DIR}/${contentNameLower}-src") + endif() + + if(savedDetails_BINARY_DIR) + set(${contentNameLower}_BINARY_DIR ${savedDetails_BINARY_DIR}) + else() + set(${contentNameLower}_BINARY_DIR "${FETCHCONTENT_BASE_DIR}/${contentNameLower}-build") + endif() else() # Support both a global "disconnect all updates" and a per-content @@ -1072,11 +1098,6 @@ function(FetchContent_Populate contentName) unset(quietFlag) endif() - __FetchContent_getSavedDetails(${contentName} contentDetails) - if("${contentDetails}" STREQUAL "") - message(FATAL_ERROR "No details have been set for content: ${contentName}") - endif() - set(__detailsQuoted) foreach(__item IN LISTS contentDetails) string(APPEND __detailsQuoted " [==[${__item}]==]") diff --git a/Tests/RunCMake/FetchContent/DirOverrides.cmake b/Tests/RunCMake/FetchContent/DirOverrides.cmake index 50eef16..ad61a00 100644 --- a/Tests/RunCMake/FetchContent/DirOverrides.cmake +++ b/Tests/RunCMake/FetchContent/DirOverrides.cmake @@ -4,18 +4,23 @@ include(FetchContent) FetchContent_Declare( t1 SOURCE_DIR ${CMAKE_CURRENT_BINARY_DIR}/savedSrc - DOWNLOAD_COMMAND ${CMAKE_COMMAND} -E make_directory <SOURCE_DIR> + BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR}/savedBin + DOWNLOAD_COMMAND ${CMAKE_COMMAND} -E make_directory <SOURCE_DIR> <BINARY_DIR> ) FetchContent_Populate(t1) if(NOT IS_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/savedSrc) message(FATAL_ERROR "Saved details SOURCE_DIR override failed") endif() +if(NOT IS_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/savedBin) + message(FATAL_ERROR "Saved details BINARY_DIR override failed") +endif() # Test direct population FetchContent_Populate( t2 SOURCE_DIR ${CMAKE_CURRENT_BINARY_DIR}/directSrc - DOWNLOAD_COMMAND ${CMAKE_COMMAND} -E make_directory <SOURCE_DIR> + BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR}/directBin + DOWNLOAD_COMMAND ${CMAKE_COMMAND} -E make_directory <SOURCE_DIR> <BINARY_DIR> ) if(NOT IS_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/directSrc) message(FATAL_ERROR "Direct details SOURCE_DIR override failed") @@ -44,3 +49,19 @@ FetchContent_Populate( if(IS_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/savedNobuildDir-build) message(FATAL_ERROR "Direct details BINARY_DIR override failed") endif() + +# Test overriding the source directory by reusing the one from t1 +set(FETCHCONTENT_SOURCE_DIR_T5 ${CMAKE_CURRENT_BINARY_DIR}/savedSrc) +FetchContent_Declare( + t5 + SOURCE_DIR ${CMAKE_CURRENT_BINARY_DIR}/doesNotExist + BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR}/wontBeCreated + DOWNLOAD_COMMAND ${CMAKE_COMMAND} -E false +) +FetchContent_Populate(t5) +if(NOT "${t5_SOURCE_DIR}" STREQUAL "${CMAKE_CURRENT_BINARY_DIR}/savedSrc") + message(FATAL_ERROR "Wrong SOURCE_DIR returned: ${t5_SOURCE_DIR}") +endif() +if(NOT "${t5_BINARY_DIR}" STREQUAL "${CMAKE_CURRENT_BINARY_DIR}/wontBeCreated") + message(FATAL_ERROR "Wrong BINARY_DIR returned: ${t5_BINARY_DIR}") +endif() diff --git a/Tests/RunCMake/FetchContent/DirOverridesDisconnected.cmake b/Tests/RunCMake/FetchContent/DirOverridesDisconnected.cmake new file mode 100644 index 0000000..768a82e --- /dev/null +++ b/Tests/RunCMake/FetchContent/DirOverridesDisconnected.cmake @@ -0,0 +1,18 @@ +include(FetchContent) + +# Test using saved details. We are re-using a SOURCE_DIR from a previous test +# so the download command should not be executed. +FetchContent_Declare( + t1 + SOURCE_DIR ${CMAKE_CURRENT_BINARY_DIR}/savedSrc + BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR}/savedBin + DOWNLOAD_COMMAND ${CMAKE_COMMAND} -E false +) +FetchContent_Populate(t1) + +if(NOT "${t1_SOURCE_DIR}" STREQUAL "${CMAKE_CURRENT_BINARY_DIR}/savedSrc") + message(FATAL_ERROR "Wrong SOURCE_DIR returned: ${t1_SOURCE_DIR}") +endif() +if(NOT "${t1_BINARY_DIR}" STREQUAL "${CMAKE_CURRENT_BINARY_DIR}/savedBin") + message(FATAL_ERROR "Wrong BINARY_DIR returned: ${t1_BINARY_DIR}") +endif() diff --git a/Tests/RunCMake/FetchContent/RunCMakeTest.cmake b/Tests/RunCMake/FetchContent/RunCMakeTest.cmake index f3ed3e2..ad9e48e 100644 --- a/Tests/RunCMake/FetchContent/RunCMakeTest.cmake +++ b/Tests/RunCMake/FetchContent/RunCMakeTest.cmake @@ -10,12 +10,25 @@ run_cmake(DownloadFile) run_cmake(SameGenerator) run_cmake(VarDefinitions) run_cmake(GetProperties) -run_cmake(DirOverrides) run_cmake(UsesTerminalOverride) run_cmake(MakeAvailable) run_cmake(MakeAvailableTwice) run_cmake(MakeAvailableUndeclared) +function(run_FetchContent_DirOverrides) + set(RunCMake_TEST_BINARY_DIR ${RunCMake_BINARY_DIR}/DirOverrides-build) + file(REMOVE_RECURSE "${RunCMake_TEST_BINARY_DIR}") + file(MAKE_DIRECTORY "${RunCMake_TEST_BINARY_DIR}") + + run_cmake(DirOverrides) + + set(RunCMake_TEST_NO_CLEAN 1) + run_cmake_with_options(DirOverridesDisconnected + -D FETCHCONTENT_FULLY_DISCONNECTED=YES + ) +endfunction() +run_FetchContent_DirOverrides() + set(RunCMake_TEST_OUTPUT_MERGE 1) run_cmake(PreserveEmptyArgs) set(RunCMake_TEST_OUTPUT_MERGE 0) |