mirror of
https://github.com/Kitware/CMake.git
synced 2026-02-21 14:40:26 -06:00
CUDAToolkit: Use correct target paths from nvcc when cross-compiling
This fixes issues where FindCUDAToolkit would find host host platform libraries when nvcc -ccbin pointed to compiler of a different CPU architecture.
This commit is contained in:
@@ -685,7 +685,43 @@ else()
|
||||
# If NVCC exists then invoke it to find the toolkit location.
|
||||
# This allows us to support wrapper scripts (e.g. ccache or colornvcc), CUDA Toolkit,
|
||||
# NVIDIA HPC SDK, and distro's splayed layouts
|
||||
execute_process(COMMAND ${CUDAToolkit_NVCC_EXECUTABLE} "-v" "__cmake_determine_cuda"
|
||||
|
||||
|
||||
#Allow the user to specify a host compiler except for Visual Studio
|
||||
if(NOT $ENV{CUDAHOSTCXX} STREQUAL "")
|
||||
get_filename_component(CUDAToolkit_CUDA_HOST_COMPILER $ENV{CUDAHOSTCXX} PROGRAM)
|
||||
if(NOT EXISTS ${CUDAToolkit_CUDA_HOST_COMPILER})
|
||||
message(FATAL_ERROR "Could not find compiler set in environment variable CUDAHOSTCXX:\n$ENV{CUDAHOSTCXX}.\n${CUDAToolkit_CUDA_HOST_COMPILER}")
|
||||
endif()
|
||||
elseif(CUDAToolkit_CUDA_HOST_COMPILER)
|
||||
# We get here if CUDAToolkit_CUDA_HOST_COMPILER was specified by the user or toolchain file.
|
||||
if(IS_ABSOLUTE "${CUDAToolkit_CUDA_HOST_COMPILER}")
|
||||
# Convert to forward slashes.
|
||||
cmake_path(CONVERT "${CUDAToolkit_CUDA_HOST_COMPILER}" TO_CMAKE_PATH_LIST CUDAToolkit_CUDA_HOST_COMPILER NORMALIZE)
|
||||
else()
|
||||
# Convert to absolute path so changes in `PATH` do not impact CUDA compilation.
|
||||
find_program(_CUDAToolkit_CUDA_HOST_COMPILER_PATH NO_CACHE NAMES "${CUDAToolkit_CUDA_HOST_COMPILER}")
|
||||
if(_CUDAToolkit_CUDA_HOST_COMPILER_PATH)
|
||||
set(CUDAToolkit_CUDA_HOST_COMPILER "${_CUDAToolkit_CUDA_HOST_COMPILER_PATH}")
|
||||
endif()
|
||||
unset(_CUDAToolkit_CUDA_HOST_COMPILER_PATH)
|
||||
endif()
|
||||
if(NOT EXISTS "${CUDAToolkit_CUDA_HOST_COMPILER}")
|
||||
message(FATAL_ERROR "Could not find compiler set in variable CUDAToolkit_CUDA_HOST_COMPILER:\n ${CUDAToolkit_CUDA_HOST_COMPILER}")
|
||||
endif()
|
||||
# If the value was cached, update the cache entry with our modifications.
|
||||
get_property(_CUDAToolkit_CUDA_HOST_COMPILER_CACHED CACHE CUDAToolkit_CUDA_HOST_COMPILER PROPERTY TYPE)
|
||||
if(_CUDAToolkit_CUDA_HOST_COMPILER_CACHED)
|
||||
set_property(CACHE CUDAToolkit_CUDA_HOST_COMPILER PROPERTY VALUE "${CUDAToolkit_CUDA_HOST_COMPILER}")
|
||||
mark_as_advanced(CUDAToolkit_CUDA_HOST_COMPILER)
|
||||
endif()
|
||||
unset(_CUDAToolkit_CUDA_HOST_COMPILER_CACHED)
|
||||
endif()
|
||||
|
||||
if(CUDAToolkit_CUDA_HOST_COMPILER)
|
||||
set(nvcc_ccbin_flag "-ccbin=${CUDAToolkit_CUDA_HOST_COMPILER}")
|
||||
endif()
|
||||
execute_process(COMMAND ${CUDAToolkit_NVCC_EXECUTABLE} "${nvcc_ccbin_flag}" "-v" "__cmake_determine_cuda"
|
||||
OUTPUT_VARIABLE _CUDA_NVCC_OUT ERROR_VARIABLE _CUDA_NVCC_OUT)
|
||||
message(CONFIGURE_LOG
|
||||
"Executed nvcc to extract CUDAToolkit information:\n${_CUDA_NVCC_OUT}\n\n")
|
||||
@@ -968,8 +1004,9 @@ else()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# Find target directory when crosscompiling.
|
||||
if(CMAKE_CROSSCOMPILING)
|
||||
# Figure out the target directory when either crosscompiling
|
||||
# or if we don't have `nvcc` and need to deduce the target arch
|
||||
if(CMAKE_CROSSCOMPILING OR NOT CUDAToolkit_NVCC_EXECUTABLE)
|
||||
# When a language is enabled we can use its compiler's target architecture.
|
||||
if(CMAKE_CUDA_COMPILER_LOADED AND CMAKE_CUDA_COMPILER_ARCHITECTURE_ID)
|
||||
set(_CUDA_TARGET_PROCESSOR "${CMAKE_CUDA_COMPILER_ARCHITECTURE_ID}")
|
||||
@@ -979,7 +1016,7 @@ if(CMAKE_CROSSCOMPILING)
|
||||
set(_CUDA_TARGET_PROCESSOR "${CMAKE_C_COMPILER_ARCHITECTURE_ID}")
|
||||
elseif(CMAKE_SYSTEM_PROCESSOR)
|
||||
set(_CUDA_TARGET_PROCESSOR "${CMAKE_SYSTEM_PROCESSOR}")
|
||||
else()
|
||||
elseif(CMAKE_CROSSCOMPILING)
|
||||
message(FATAL_ERROR "Cross-compiling with the CUDA toolkit requires CMAKE_SYSTEM_PROCESSOR to be set.")
|
||||
endif()
|
||||
# Keep in sync with equivalent table in CMakeDetermineCUDACompiler and FindCUDA!
|
||||
@@ -1010,13 +1047,18 @@ if(CMAKE_CROSSCOMPILING)
|
||||
# Mark that we need to pop the root search path changes after we have
|
||||
# found all cuda libraries so that searches for our cross-compilation
|
||||
# libraries work when another cuda sdk is in CMAKE_PREFIX_PATH or
|
||||
# PATh
|
||||
# PATH
|
||||
set(_CUDAToolkit_Pop_ROOT_PATH True)
|
||||
break()
|
||||
endif()
|
||||
endforeach()
|
||||
endif()
|
||||
|
||||
#If not already set we simply use the toolkit root
|
||||
if(NOT CUDAToolkit_TARGET_DIR)
|
||||
set(CUDAToolkit_TARGET_DIR "${CUDAToolkit_ROOT_DIR}")
|
||||
endif()
|
||||
|
||||
# Determine windows search path suffix for libraries
|
||||
if(CMAKE_HOST_SYSTEM_NAME STREQUAL "Windows")
|
||||
if(CMAKE_HOST_SYSTEM_PROCESSOR STREQUAL "AMD64")
|
||||
@@ -1025,19 +1067,6 @@ if(CMAKE_HOST_SYSTEM_NAME STREQUAL "Windows")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
# If not already set we can simply use the toolkit root or it's a scattered installation.
|
||||
if(NOT CUDAToolkit_TARGET_DIR)
|
||||
# Not cross compiling
|
||||
set(CUDAToolkit_TARGET_DIR "${CUDAToolkit_ROOT_DIR}")
|
||||
# Now that we have the real ROOT_DIR, find components inside it.
|
||||
list(APPEND CMAKE_PREFIX_PATH ${CUDAToolkit_ROOT_DIR})
|
||||
|
||||
# Mark that we need to pop the prefix path changes after we have
|
||||
# found the cudart library.
|
||||
set(_CUDAToolkit_Pop_Prefix True)
|
||||
endif()
|
||||
|
||||
|
||||
# We don't need to verify the cuda_runtime header when we are using `nvcc` include paths
|
||||
# as the compiler being enabled means the header was found
|
||||
if(NOT CUDAToolkit_INCLUDE_DIRECTORIES)
|
||||
@@ -1067,7 +1096,8 @@ if(NOT CUDAToolkit_CUBLAS_INCLUDE_DIR)
|
||||
cmake_path(NORMAL_PATH CUDAToolkit_MATH_INCLUDE_DIR)
|
||||
|
||||
find_path(CUDAToolkit_CUBLAS_INCLUDE_DIR cublas_v2.h PATHS
|
||||
${CUDAToolkit_INCLUDE_DIRECTORIES}
|
||||
${CUDAToolkit_MATH_INCLUDE_DIR}
|
||||
NO_DEFAULT_PATH
|
||||
)
|
||||
if(CUDAToolkit_CUBLAS_INCLUDE_DIR)
|
||||
list(APPEND CUDAToolkit_INCLUDE_DIRECTORIES "${CUDAToolkit_CUBLAS_INCLUDE_DIR}")
|
||||
@@ -1079,12 +1109,12 @@ unset(CUDAToolkit_CUBLAS_INCLUDE_DIR)
|
||||
# Find the CUDA Runtime Library libcudart
|
||||
find_library(CUDA_CUDART
|
||||
NAMES cudart
|
||||
PATHS ${CUDAToolkit_IMPLICIT_LIBRARY_DIRECTORIES}
|
||||
PATHS ${CUDAToolkit_IMPLICIT_LIBRARY_DIRECTORIES} ${CUDAToolkit_TARGET_DIR}
|
||||
PATH_SUFFIXES lib64 ${_CUDAToolkit_win_search_dirs}
|
||||
)
|
||||
find_library(CUDA_CUDART
|
||||
NAMES cudart
|
||||
PATHS ${CUDAToolkit_IMPLICIT_LIBRARY_DIRECTORIES}
|
||||
PATHS ${CUDAToolkit_IMPLICIT_LIBRARY_DIRECTORIES} ${CUDAToolkit_TARGET_DIR}
|
||||
PATH_SUFFIXES lib64/stubs ${_CUDAToolkit_win_stub_search_dirs} lib/stubs stubs
|
||||
)
|
||||
|
||||
@@ -1092,11 +1122,6 @@ if(NOT CUDA_CUDART AND NOT CUDAToolkit_FIND_QUIETLY)
|
||||
message(STATUS "Unable to find cudart library.")
|
||||
endif()
|
||||
|
||||
if(_CUDAToolkit_Pop_Prefix)
|
||||
list(REMOVE_AT CMAKE_PREFIX_PATH -1)
|
||||
unset(_CUDAToolkit_Pop_Prefix)
|
||||
endif()
|
||||
|
||||
#-----------------------------------------------------------------------------
|
||||
# Perform version comparison and validate all required variables are set.
|
||||
include(FindPackageHandleStandardArgs)
|
||||
@@ -1127,7 +1152,10 @@ if(CUDAToolkit_FOUND)
|
||||
|
||||
# Detect we are in a splayed nvhpc toolkit layout and add extra
|
||||
# search paths without symlinks
|
||||
if(CUDAToolkit_LIBRARY_DIR MATCHES ".*/cuda/${CUDAToolkit_VERSION_MAJOR}.${CUDAToolkit_VERSION_MINOR}/lib64$")
|
||||
#
|
||||
# When the `nvcc` compiler output is parsed we have already resolved
|
||||
# symlinks so we have `cuda/12.X/targets/....` and not `cuda/12.X/lib64`.
|
||||
if(CUDAToolkit_LIBRARY_DIR MATCHES ".*/cuda/${CUDAToolkit_VERSION_MAJOR}.${CUDAToolkit_VERSION_MINOR}/(lib64$|targets/)")
|
||||
# Search location for math_libs/
|
||||
block(SCOPE_FOR POLICIES)
|
||||
cmake_policy(SET CMP0152 NEW)
|
||||
|
||||
Reference in New Issue
Block a user