summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBrad King <brad.king@kitware.com>2022-04-28 13:36:25 (GMT)
committerKitware Robot <kwrobot@kitware.com>2022-04-28 13:36:31 (GMT)
commitd35f1c9beee14f1be1e39838b5d4be0906a48974 (patch)
treeb8c0f6a296f1cee0b259bb826c922d9c3b85ada8
parent2fb1398b7eba0e980b2e1295916a9d5fd0337bff (diff)
parentc267ed205a2ef2a2396b4d00b593d617b2befdcc (diff)
downloadCMake-d35f1c9beee14f1be1e39838b5d4be0906a48974.zip
CMake-d35f1c9beee14f1be1e39838b5d4be0906a48974.tar.gz
CMake-d35f1c9beee14f1be1e39838b5d4be0906a48974.tar.bz2
Merge topic 'cuda-arch-verify'
c267ed205a CUDA: Defer architecture testing to the compiler testing step Acked-by: Kitware Robot <kwrobot@kitware.com> Acked-by: Robert Maynard <robertjmaynard@gmail.com> Acked-by: Raul Tambre <raul@tambre.ee> Merge-request: !7202
-rw-r--r--Modules/CMakeDetermineCUDACompiler.cmake113
-rw-r--r--Modules/CMakeDetermineCompilerId.cmake8
-rw-r--r--Modules/CUDA/architectures.cmake60
-rw-r--r--Tests/RunCMake/CUDA_architectures/architectures-empty-stderr.txt2
-rw-r--r--Tests/RunCMake/CUDA_architectures/architectures-invalid-stderr.txt11
5 files changed, 32 insertions, 162 deletions
diff --git a/Modules/CMakeDetermineCUDACompiler.cmake b/Modules/CMakeDetermineCUDACompiler.cmake
index 66020e8..23da8ee 100644
--- a/Modules/CMakeDetermineCUDACompiler.cmake
+++ b/Modules/CMakeDetermineCUDACompiler.cmake
@@ -248,10 +248,6 @@ if(NOT CMAKE_CUDA_COMPILER_ID_RUN)
if(CMAKE_CUDA_COMPILER_ID_OUTPUT MATCHES [=[V([0-9]+\.[0-9]+\.[0-9]+)]=])
set(CMAKE_CUDA_COMPILER_TOOLKIT_VERSION "${CMAKE_MATCH_1}")
endif()
-
- # Make the all, all-major, and native architecture information available.
- # FIXME(#23161): Defer architecture detection until compiler testing.
- include(${CMAKE_ROOT}/Modules/CUDA/architectures.cmake)
endif()
set(CMAKE_CUDA_COMPILER_ID_FLAGS_ALWAYS "-v")
@@ -273,76 +269,34 @@ if(NOT CMAKE_CUDA_COMPILER_ID_RUN)
endif()
endif()
- # FIXME(#23161): Defer architecture testing until compiler testing.
- if(DEFINED CMAKE_CUDA_ARCHITECTURES)
- if(CMAKE_CUDA_ARCHITECTURES MATCHES "^(all|all-major)$")
- # For sufficiently new NVCC we can just use the all and all-major flags.
- # For VS we don't test since we can't figure out the version this early (see #23161).
- # For others select based on version.
- if(CMAKE_CUDA_COMPILER_ID STREQUAL "NVIDIA" AND CMAKE_CUDA_COMPILER_TOOLKIT_VERSION VERSION_GREATER_EQUAL 11.5)
- string(APPEND nvcc_test_flags " -arch=${CMAKE_CUDA_ARCHITECTURES}")
- set(architectures_tested "${CMAKE_CUDA_ARCHITECTURES}")
- elseif(CMAKE_GENERATOR MATCHES "Visual Studio")
- set(architectures_tested "${CMAKE_CUDA_ARCHITECTURES}")
- else()
- if(CMAKE_CUDA_ARCHITECTURES STREQUAL "all")
- set(architectures_test ${CMAKE_CUDA_ARCHITECTURES_ALL})
- elseif(CMAKE_CUDA_ARCHITECTURES STREQUAL "all-major")
- set(architectures_test ${CMAKE_CUDA_ARCHITECTURES_ALL_MAJOR})
- endif()
- endif()
- elseif(CMAKE_CUDA_ARCHITECTURES STREQUAL "native")
- # For sufficiently new NVCC we can just use the 'native' value directly.
- # For VS we don't test since we can't find nvcc this early (see #23161).
- if(CMAKE_CUDA_COMPILER_ID STREQUAL "NVIDIA" AND CMAKE_CUDA_COMPILER_TOOLKIT_VERSION VERSION_GREATER_EQUAL 11.6)
- string(APPEND nvcc_test_flags " -arch=${CMAKE_CUDA_ARCHITECTURES}")
- set(architectures_tested "${CMAKE_CUDA_ARCHITECTURES}")
- elseif(CMAKE_GENERATOR MATCHES "Visual Studio")
- set(architectures_tested "${CMAKE_CUDA_ARCHITECTURES}")
- else()
- set(architectures_test ${_CUDA_ARCHITECTURES_NATIVE})
- endif()
- elseif(CMAKE_CUDA_ARCHITECTURES OR "${CMAKE_CUDA_ARCHITECTURES}" STREQUAL "")
- # Explicit architectures. Test them during detection.
- set(architectures_explicit TRUE)
- set(architectures_test ${CMAKE_CUDA_ARCHITECTURES})
- endif()
- endif()
-
- foreach(arch ${architectures_test})
- # Strip specifiers as PTX vs binary doesn't matter.
- string(REGEX MATCH "[0-9]+" arch_name "${arch}")
- string(APPEND clang_test_flags " --cuda-gpu-arch=sm_${arch_name}")
- string(APPEND nvcc_test_flags " -gencode=arch=compute_${arch_name},code=sm_${arch_name}")
- list(APPEND architectures_tested "${arch_name}")
- endforeach()
-
# Rest of the code treats an empty value as equivalent to "use the defaults".
# Error out early to prevent confusing errors as a result of this.
# Note that this also catches invalid non-numerical values such as "a".
- if(DEFINED architectures_explicit AND "${architectures_tested}" STREQUAL "")
- message(FATAL_ERROR "CMAKE_CUDA_ARCHITECTURES must be valid if set.")
+ if(DEFINED CMAKE_CUDA_ARCHITECTURES)
+ if(CMAKE_CUDA_ARCHITECTURES STREQUAL "")
+ message(FATAL_ERROR "CMAKE_CUDA_ARCHITECTURES must be non-empty if set.")
+ elseif(CMAKE_CUDA_ARCHITECTURES AND NOT CMAKE_CUDA_ARCHITECTURES MATCHES "^([0-9]+[;0-9]*|all|all-major|native)$")
+ message(FATAL_ERROR
+ "CMAKE_CUDA_ARCHITECTURES:\n"
+ " ${CMAKE_CUDA_ARCHITECTURES}\n"
+ "is not one of the following:\n"
+ "* a semicolon-separated list of integers\n"
+ "* a special value: all, all-major, native\n"
+ )
+ endif()
endif()
if(CMAKE_CUDA_COMPILER_ID STREQUAL "Clang")
- if(NOT CMAKE_CUDA_ARCHITECTURES)
- # Clang doesn't automatically select an architecture supported by the SDK.
- # Try in reverse order of deprecation with the most recent at front (i.e. the most likely to work for new setups).
- foreach(arch "52" "30" "20")
- list(APPEND CMAKE_CUDA_COMPILER_ID_TEST_FLAGS_FIRST "${clang_test_flags} --cuda-gpu-arch=sm_${arch}")
- endforeach()
- endif()
-
- # If the user specified CMAKE_CUDA_ARCHITECTURES this will include all the architecture flags.
- # Otherwise this won't include any architecture flags and we'll fallback to Clang's defaults.
- list(APPEND CMAKE_CUDA_COMPILER_ID_TEST_FLAGS_FIRST "${clang_test_flags}")
+ # Clang doesn't automatically select an architecture supported by the SDK.
+ # Try in reverse order of deprecation with the most recent at front (i.e. the most likely to work for new setups).
+ foreach(arch "52" "30" "20")
+ list(APPEND CMAKE_CUDA_COMPILER_ID_TEST_FLAGS_FIRST "${clang_test_flags} --cuda-gpu-arch=sm_${arch}")
+ endforeach()
elseif(CMAKE_CUDA_COMPILER_ID STREQUAL "NVIDIA")
list(APPEND CMAKE_CUDA_COMPILER_ID_TEST_FLAGS_FIRST "${nvcc_test_flags}")
endif()
# We perform compiler identification for a second time to extract implicit linking info and host compiler for NVCC.
- # We also use it to verify that CMAKE_CUDA_ARCHITECTURES and additionally on Clang that CUDA toolkit path works.
- # The latter could be done during compiler testing in the future to avoid doing this for Clang.
# We need to unset the compiler ID otherwise CMAKE_DETERMINE_COMPILER_ID() doesn't work.
set(CMAKE_CUDA_COMPILER_ID)
set(CMAKE_CUDA_PLATFORM_ID)
@@ -357,12 +311,12 @@ if(NOT CMAKE_CUDA_COMPILER_ID_RUN)
get_filename_component(CMAKE_CUDA_COMPILER_TOOLKIT_ROOT "${CMAKE_CUDA_COMPILER_TOOLKIT_ROOT}" DIRECTORY)
set(CMAKE_CUDA_COMPILER_LIBRARY_ROOT "${CMAKE_CUDA_COMPILER_TOOLKIT_ROOT}")
- # We now know the version, so make the architecture variables available.
+ # The compiler comes with the toolkit, so the versions are the same.
set(CMAKE_CUDA_COMPILER_TOOLKIT_VERSION ${CMAKE_CUDA_COMPILER_VERSION})
- # FIXME(#23161): Defer architecture detection until compiler testing.
- include(${CMAKE_ROOT}/Modules/CUDA/architectures.cmake)
endif()
+ include(${CMAKE_ROOT}/Modules/CUDA/architectures.cmake)
+
_cmake_find_compiler_sysroot(CUDA)
endif()
@@ -647,31 +601,6 @@ if("${CMAKE_CUDA_ARCHITECTURES}" STREQUAL "")
message(FATAL_ERROR "Failed to detect a default CUDA architecture.\n\nCompiler output:\n${CMAKE_CUDA_COMPILER_PRODUCED_OUTPUT}")
endif()
endif()
-elseif(CMAKE_CUDA_ARCHITECTURES AND NOT "${architectures_tested}" MATCHES "^(all|all-major|native)$")
- # Sort since order mustn't matter.
- list(SORT architectures_detected)
- list(SORT architectures_tested)
-
- # We don't distinguish real/virtual architectures during testing.
- # For "70-real;70-virtual" we detect "70" as working and architectures_tested is "70;70".
- # Thus we need to remove duplicates before checking if they're equal.
- list(REMOVE_DUPLICATES architectures_tested)
-
- # Print the actual architectures for generic values (all and all-major).
- if(NOT DEFINED architectures_explicit)
- set(architectures_error "${CMAKE_CUDA_ARCHITECTURES} (${architectures_tested})")
- else()
- set(architectures_error "${architectures_tested}")
- endif()
-
- if(NOT "${architectures_detected}" STREQUAL "${architectures_tested}")
- message(FATAL_ERROR
- "The CMAKE_CUDA_ARCHITECTURES:\n"
- " ${architectures_error}\n"
- "do not all work with this compiler. Try:\n"
- " ${architectures_detected}\n"
- "instead.")
- endif()
endif()
# configure all variables set in this file
@@ -687,9 +616,7 @@ unset(_CUDA_LIBRARY_DIR)
unset(_CUDA_TARGET_DIR)
unset(_CUDA_TARGET_NAME)
-unset(architectures_explicit)
unset(architectures_detected)
-unset(architectures_tested)
set(CMAKE_CUDA_COMPILER_ENV_VAR "CUDACXX")
set(CMAKE_CUDA_HOST_COMPILER_ENV_VAR "CUDAHOSTCXX")
diff --git a/Modules/CMakeDetermineCompilerId.cmake b/Modules/CMakeDetermineCompilerId.cmake
index a90fa5d..0e8b2af 100644
--- a/Modules/CMakeDetermineCompilerId.cmake
+++ b/Modules/CMakeDetermineCompilerId.cmake
@@ -495,13 +495,7 @@ Id flags: ${testflags} ${CMAKE_${lang}_COMPILER_ID_FLAGS_ALWAYS}
if(CMAKE_VS_PLATFORM_NAME STREQUAL x64)
set(cuda_target "<TargetMachinePlatform>64</TargetMachinePlatform>")
endif()
- if(CMAKE_CUDA_ARCHITECTURES AND NOT CMAKE_CUDA_ARCHITECTURES MATCHES "^(all|all-major|native)$")
- foreach(arch ${CMAKE_CUDA_ARCHITECTURES})
- string(REGEX MATCH "[0-9]+" arch_name "${arch}")
- string(APPEND cuda_codegen "compute_${arch_name},sm_${arch_name};")
- endforeach()
- endif()
- set(id_ItemDefinitionGroup_entry "<CudaCompile>${cuda_target}<AdditionalOptions>%(AdditionalOptions)-v</AdditionalOptions><CodeGeneration>${cuda_codegen}</CodeGeneration></CudaCompile>")
+ set(id_ItemDefinitionGroup_entry "<CudaCompile>${cuda_target}<AdditionalOptions>%(AdditionalOptions)-v</AdditionalOptions></CudaCompile>")
set(id_PostBuildEvent_Command [[echo CMAKE_CUDA_COMPILER=$(CudaToolkitBinDir)\nvcc.exe]])
if(CMAKE_VS_PLATFORM_TOOLSET_CUDA_CUSTOM_DIR)
# check for legacy cuda custom toolkit folder structure
diff --git a/Modules/CUDA/architectures.cmake b/Modules/CUDA/architectures.cmake
index 9b1f2b5..fa3a5a1 100644
--- a/Modules/CUDA/architectures.cmake
+++ b/Modules/CUDA/architectures.cmake
@@ -44,63 +44,3 @@ if(CMAKE_CUDA_COMPILER_TOOLKIT_VERSION VERSION_GREATER_EQUAL 11.4
AND (NOT CMAKE_CUDA_COMPILER_ID STREQUAL "Clang"))
list(APPEND CMAKE_CUDA_ARCHITECTURES_ALL 87)
endif()
-
-# FIXME(#23161): Detect architectures early since we test them during
-# compiler detection. We already have code to detect them later during
-# compiler testing, so we should not need to do this here.
-if(NOT CMAKE_GENERATOR MATCHES "Visual Studio")
- set(_CUDA_ARCHS_EXE "${CMAKE_PLATFORM_INFO_DIR}/CMakeDetermineCUDACompilerArchs.bin")
- execute_process(
- COMMAND "${_CUDA_NVCC_EXECUTABLE}" -o "${_CUDA_ARCHS_EXE}" --cudart=static "${CMAKE_ROOT}/Modules/CMakeCUDACompilerABI.cu"
- RESULT_VARIABLE _CUDA_ARCHS_RESULT
- OUTPUT_VARIABLE _CUDA_ARCHS_OUTPUT
- ERROR_VARIABLE _CUDA_ARCHS_OUTPUT
- )
- if(_CUDA_ARCHS_RESULT EQUAL 0)
- execute_process(
- COMMAND "${_CUDA_ARCHS_EXE}"
- RESULT_VARIABLE _CUDA_ARCHS_RESULT
- OUTPUT_VARIABLE _CUDA_ARCHS_OUTPUT
- ERROR_VARIABLE _CUDA_ARCHS_OUTPUT
- OUTPUT_STRIP_TRAILING_WHITESPACE
- )
- endif()
- if(_CUDA_ARCHS_RESULT EQUAL 0)
- if("$ENV{CMAKE_CUDA_ARCHITECTURES_NATIVE_CLAMP}")
- # Undocumented hook used by CMake's CI.
- # Clamp native architecture to version range supported by this CUDA.
- list(GET CMAKE_CUDA_ARCHITECTURES_ALL 0 _CUDA_ARCH_MIN)
- list(GET CMAKE_CUDA_ARCHITECTURES_ALL -1 _CUDA_ARCH_MAX)
- set(_CUDA_ARCHITECTURES_NATIVE "")
- foreach(_CUDA_ARCH IN LISTS _CUDA_ARCHS_OUTPUT)
- if(_CUDA_ARCH LESS _CUDA_ARCH_MIN)
- set(_CUDA_ARCH "${_CUDA_ARCH_MIN}")
- endif()
- if(_CUDA_ARCH GREATER _CUDA_ARCH_MAX)
- set(_CUDA_ARCH "${_CUDA_ARCH_MAX}")
- endif()
- list(APPEND _CUDA_ARCHITECTURES_NATIVE ${_CUDA_ARCH})
- endforeach()
- unset(_CUDA_ARCH)
- unset(_CUDA_ARCH_MIN)
- unset(_CUDA_ARCH_MAX)
- else()
- set(_CUDA_ARCHITECTURES_NATIVE "${_CUDA_ARCHS_OUTPUT}")
- endif()
- list(REMOVE_DUPLICATES _CUDA_ARCHITECTURES_NATIVE)
- else()
- if (NOT _CUDA_ARCHS_RESULT MATCHES "[0-9]+")
- set(_CUDA_ARCHS_STATUS " (${_CUDA_ARCHS_RESULT})")
- else()
- set(_CUDA_ARCHS_STATUS "")
- endif()
- string(REPLACE "\n" "\n " _CUDA_ARCHS_OUTPUT " ${_CUDA_ARCHS_OUTPUT}")
- file(APPEND ${CMAKE_BINARY_DIR}${CMAKE_FILES_DIRECTORY}/CMakeError.log
- "Detecting the CUDA native architecture(s) failed with "
- "the following output:\n${_CUDA_ARCHS_OUTPUT}\n\n")
- set(_CUDA_ARCHS_OUTPUT "")
- endif()
- unset(_CUDA_ARCHS_EXE)
- unset(_CUDA_ARCHS_RESULT)
- unset(_CUDA_ARCHS_OUTPUT)
-endif()
diff --git a/Tests/RunCMake/CUDA_architectures/architectures-empty-stderr.txt b/Tests/RunCMake/CUDA_architectures/architectures-empty-stderr.txt
index 39640fa..6c42612 100644
--- a/Tests/RunCMake/CUDA_architectures/architectures-empty-stderr.txt
+++ b/Tests/RunCMake/CUDA_architectures/architectures-empty-stderr.txt
@@ -1,5 +1,5 @@
^CMake Error at .*/Modules/CMakeDetermineCUDACompiler\.cmake:[0-9]+ \(message\):
- CMAKE_CUDA_ARCHITECTURES must be valid if set\.
+ CMAKE_CUDA_ARCHITECTURES must be non-empty if set\.
Call Stack \(most recent call first\):
architectures-empty\.cmake:2 \(enable_language\)
CMakeLists\.txt:3 \(include\)
diff --git a/Tests/RunCMake/CUDA_architectures/architectures-invalid-stderr.txt b/Tests/RunCMake/CUDA_architectures/architectures-invalid-stderr.txt
index 7608730..48f379c 100644
--- a/Tests/RunCMake/CUDA_architectures/architectures-invalid-stderr.txt
+++ b/Tests/RunCMake/CUDA_architectures/architectures-invalid-stderr.txt
@@ -1,5 +1,14 @@
^CMake Error at .*/Modules/CMakeDetermineCUDACompiler\.cmake:[0-9]+ \(message\):
- CMAKE_CUDA_ARCHITECTURES must be valid if set\.
+ CMAKE_CUDA_ARCHITECTURES:
+
+ invalid
+
+ is not one of the following:
+
+ \* a semicolon-separated list of integers
+
+ \* a special value: all, all-major, native
+
Call Stack \(most recent call first\):
architectures-invalid\.cmake:2 \(enable_language\)
CMakeLists\.txt:3 \(include\)$