CUDA: Support clang-cl

Fixes: #28139
This commit is contained in:
Vito Gamberini committed 2026-10-04 22:11:50 -04:00
1 parent c579da7b31
commit 3fae9133cc
13 files changed
+84 -7

No files matched your search

+5 -1
View File
@@ -25,7 +25,11 @@ set(_CMAKE_CUDA_PTX_FLAG "--cuda-device-only -S")
if (CMAKE_CUDA_COMPILER_VERSION VERSION_GREATER_EQUAL 20.0)
# Starting in 20.0, clang supports device linking as part of the host link phase
set(CMAKE_CUDA_COMPILER_HAS_DEVICE_LINK_PHASE FALSE)
set(_CMAKE_CUDA_RDC_LINK_FLAG "--offload-link")
if(CMAKE_CUDA_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC")
set(_CMAKE_CUDA_RDC_LINK_FLAG "-clang:--offload-link")
else()
set(_CMAKE_CUDA_RDC_LINK_FLAG "--offload-link")
endif()
endif()
# Device linking is just regular linking so these are the same.
+24 -1
View File
@@ -1,15 +1,38 @@
include(Platform/Windows-Clang)
__windows_compiler_clang(CUDA)
# The MSVC platform initialization enables host IPO for Clang, but CUDA's
# compiler module does not support CUDA device IPO.
set(_CMAKE_CUDA_IPO_SUPPORTED_BY_CMAKE NO)
set(_CMAKE_CUDA_IPO_MAY_BE_SUPPORTED_BY_COMPILER NO)
if(CMAKE_CUDA_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC")
# The MSVC object rule has no CUDA_COMPILE_MODE placeholder, so it would
# omit -fgpu-rdc for separable compilation. Use -o for the final host object
# rather than applying /Fo to device intermediates as well.
set(CMAKE_CUDA_COMPILE_OBJECT
"<CMAKE_CUDA_COMPILER> ${CMAKE_START_TEMP_FILE} ${CMAKE_CL_NOLOGO} ${_CMAKE_CUDA_EXTRA_FLAGS} <DEFINES> <INCLUDES> <FLAGS> ${_CMAKE_COMPILE_AS_CUDA_FLAG} <CUDA_COMPILE_MODE> -o <OBJECT> /Fd<TARGET_COMPILE_PDB> -- <SOURCE>${CMAKE_END_TEMP_FILE}")
if(NOT CMAKE_CUDA_COMPILER_HAS_DEVICE_LINK_PHASE)
# link.exe's incremental padding breaks the contiguous offload-entry
# table traversed by clang-linker-wrapper's registration constructor.
__windows_compiler_clang_msvc_offload_link(CUDA "${_CMAKE_CUDA_RDC_LINK_FLAG}" "/INCREMENTAL:NO")
endif()
set(_CUDA_LIBRARY_PATH_FLAG "-libpath:")
set(CMAKE_CUDA_VERBOSE_FLAG "-clang:-v")
else()
set(_CUDA_LIBRARY_PATH_FLAG "-L")
endif()
# Tell Clang where to find the CUDA libraries.
set(__IMPLICIT_LINKS)
foreach(dir ${CMAKE_CUDA_HOST_IMPLICIT_LINK_DIRECTORIES})
string(APPEND __IMPLICIT_LINKS " -L\"${dir}\"")
string(APPEND __IMPLICIT_LINKS " ${_CUDA_LIBRARY_PATH_FLAG}\"${dir}\"")
endforeach()
string(APPEND CMAKE_CUDA_LINK_EXECUTABLE "${__IMPLICIT_LINKS}")
string(APPEND CMAKE_CUDA_CREATE_SHARED_LIBRARY "${__IMPLICIT_LINKS}")
string(APPEND CMAKE_CUDA_CREATE_SHARED_MODULE "${__IMPLICIT_LINKS}")
unset(__IMPLICIT_LINKS)
unset(_CUDA_LIBRARY_PATH_FLAG)
# Device linking is just regular linking so these are the same.
set(CMAKE_CUDA_DEVICE_LINKER_WRAPPER_FLAG ${CMAKE_CUDA_LINKER_WRAPPER_FLAG})
+21
View File
@@ -14,6 +14,7 @@ set(__pch_header_OBJC "objective-c-header")
set(__pch_header_OBJCXX "objective-c++-header")
macro(__windows_compiler_clang_gnu lang)
set(CMAKE_${lang}_LIBRARY_PATH_FLAG "-L")
set(CMAKE_LIBRARY_PATH_FLAG "-L")
set(CMAKE_LINK_LIBRARY_FLAG "-l")
@@ -295,3 +296,23 @@ macro(__windows_compiler_clang lang)
endif()
__windows_compiler_clang_base(${lang})
endmacro()
macro(__windows_compiler_clang_msvc_offload_link lang extra_flags extra_link_flags)
# Preserve compiler-driven offload linking while retaining the standard
# MSVC manifest, import-library, PDB, and response-file handling.
set(CMAKE_${lang}_LINK_MODE DRIVER)
# Native linker flags are passed after /link.
set(CMAKE_${lang}_LINKER_WRAPPER_FLAG "")
set(CMAKE_${lang}_LINKER_WRAPPER_FLAG_SEP "")
# clang-linker-wrapper recognizes the native option's lowercase spelling;
# uppercase -LIBPATH can otherwise be parsed as the GNU -L option.
set(CMAKE_${lang}_LIBRARY_PATH_FLAG "-libpath:")
set(CMAKE_${lang}_STANDARD_LIBRARIES_INIT "${CMAKE_C_STANDARD_LIBRARIES_INIT}")
# The driver needs the final output name before /link, including when
# naming its device-link intermediates.
set(CMAKE_${lang}_LINK_EXECUTABLE
"${_CMAKE_VS_LINK_EXE}<CMAKE_${lang}_COMPILER> ${extra_flags} <FLAGS> ${CMAKE_CL_NOLOGO} <OBJECTS> ${CMAKE_START_TEMP_FILE} /Fe<TARGET> /link /implib:<TARGET_IMPLIB> /pdb:<TARGET_PDB> /version:<TARGET_VERSION_MAJOR>.<TARGET_VERSION_MINOR>${_PLATFORM_LINK_FLAGS} <LINK_FLAGS> <LINK_LIBRARIES>${_CMAKE_FASTBUILD_MANIFESTS} ${extra_link_flags} ${CMAKE_END_TEMP_FILE}")
set(CMAKE_${lang}_CREATE_SHARED_LIBRARY
"${_CMAKE_VS_LINK_DLL}<CMAKE_${lang}_COMPILER> ${extra_flags} <LANGUAGE_COMPILE_FLAGS> ${CMAKE_CL_NOLOGO} /LD <OBJECTS> ${CMAKE_START_TEMP_FILE} /Fe<TARGET> /link /implib:<TARGET_IMPLIB> /pdb:<TARGET_PDB> /version:<TARGET_VERSION_MAJOR>.<TARGET_VERSION_MINOR>${_PLATFORM_LINK_FLAGS} <LINK_FLAGS> <LINK_LIBRARIES>${_CMAKE_FASTBUILD_MANIFESTS} ${extra_link_flags} ${CMAKE_END_TEMP_FILE}")
set(CMAKE_${lang}_CREATE_SHARED_MODULE "${CMAKE_${lang}_CREATE_SHARED_LIBRARY}")
endmacro()
+3 -1
View File
@@ -496,7 +496,9 @@ macro(__windows_compiler_msvc lang)
if("x${lang}" STREQUAL "xC" OR
"x${lang}" STREQUAL "xCXX" OR
"x${lang}" STREQUAL "xHIP")
"x${lang}" STREQUAL "xHIP" OR
("x${lang}" STREQUAL "xCUDA" AND
CMAKE_CUDA_COMPILER_ID STREQUAL "Clang"))
if(CMAKE_MSVC_RUNTIME_LIBRARY_DEFAULT)
set(_MDd "")
set(_MD "")
@@ -7,5 +7,8 @@ project (IncludePathNoToolkit CXX CUDA)
# the cuda runtime headers
add_executable(IncludePathNoToolkit main.cpp)
if(CMAKE_CUDA_COMPILER_TOOLKIT_VERSION VERSION_GREATER_EQUAL 13)
target_compile_features(IncludePathNoToolkit PRIVATE cxx_std_17)
endif()
target_include_directories(IncludePathNoToolkit PRIVATE
${CMAKE_CUDA_TOOLKIT_INCLUDE_DIRECTORIES})
+3
View File
@@ -90,6 +90,9 @@ foreach (cuda_lib IN LISTS nv_libs)
endforeach()
add_executable(Toolkit main.cpp)
if(CUDAToolkit_VERSION VERSION_GREATER_EQUAL 13)
target_compile_features(Toolkit PRIVATE cxx_std_17)
endif()
target_link_libraries(Toolkit PRIVATE CUDA::toolkit)
if(HAS_CUPTI)
+4 -1
View File
@@ -10,9 +10,12 @@ set_target_properties(CudaOnlyPDB PROPERTIES
)
set(pdbs
${CMAKE_CURRENT_BINARY_DIR}/CompPDBDir/${CMAKE_CFG_INTDIR}/CompPDBName.pdb
${CMAKE_CURRENT_BINARY_DIR}/LinkPDBDir/${CMAKE_CFG_INTDIR}/LinkPDBName.pdb
)
if(NOT CMAKE_CUDA_COMPILER_ID STREQUAL "Clang")
list(APPEND pdbs
${CMAKE_CURRENT_BINARY_DIR}/CompPDBDir/${CMAKE_CFG_INTDIR}/CompPDBName.pdb)
endif()
add_custom_command(TARGET CudaOnlyPDB POST_BUILD
COMMAND ${CMAKE_COMMAND} -Dconfig=$<CONFIG> "-Dpdbs=${pdbs}"
-P ${CMAKE_CURRENT_SOURCE_DIR}/check_pdbs.cmake
+3
View File
@@ -116,4 +116,7 @@ if(HAS_CUPTI)
endif()
add_executable(CudaOnlyToolkit main.cu)
if(CUDAToolkit_VERSION VERSION_GREATER_EQUAL 13)
target_compile_features(CudaOnlyToolkit PRIVATE cuda_std_17)
endif()
target_link_libraries(CudaOnlyToolkit PRIVATE CUDA::toolkit)
@@ -23,4 +23,7 @@ foreach (cuda_lib IN LISTS cuda_libs)
endforeach()
add_executable(CudaOnlyToolkitBeforeLang main.cu)
if(CUDAToolkit_VERSION VERSION_GREATER_EQUAL 13)
target_compile_features(CudaOnlyToolkitBeforeLang PRIVATE cuda_std_17)
endif()
target_link_libraries(CudaOnlyToolkitBeforeLang PRIVATE CUDA::toolkit)
@@ -19,4 +19,7 @@ message(STATUS "CUDAToolkit_LIBRARY_DIR: ${CUDAToolkit_LIBRARY_DIR}")
message(STATUS "CUDAToolkit_NVCC_EXECUTABLE ${CUDAToolkit_NVCC_EXECUTABLE}")
add_executable(CudaOnlyToolkitMultipleDirs main.cu)
if(CUDAToolkit_VERSION VERSION_GREATER_EQUAL 13)
target_compile_features(CudaOnlyToolkitMultipleDirs PRIVATE cuda_std_17)
endif()
target_link_libraries(CudaOnlyToolkitMultipleDirs PRIVATE CUDA::toolkit)
@@ -3,5 +3,5 @@
]*[/\]main\.cu['"
].*-E env LW_OUTER=1 [^
]*-E env LW_INNER=2 [^
]*[ /\:]main(\.exe)?['"
]*([ /\:]|/Fe)main(\.exe)?['"
]
@@ -1,7 +1,11 @@
if(CMake_TEST_CUDA STREQUAL "NVIDIA")
set(expected "-Xlinker=OPT1 -Xlinker=OPT2 -Xlinker=OPT3 -Xlinker=OPT4 -Xlinker=OPT5")
elseif(CMake_TEST_CUDA STREQUAL "Clang")
set(expected "-Wl,OPT1 -Xlinker OPT2 -Xlinker OPT3 -Xlinker OPT4")
if(CMAKE_CUDA_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC")
set(expected "OPT1 OPT2 OPT3 OPT4")
else()
set(expected "-Wl,OPT1 -Xlinker OPT2 -Xlinker OPT3 -Xlinker OPT4")
endif()
endif()
if(NOT actual_stdout MATCHES "${expected}")
@@ -49,7 +49,11 @@ if (CMake_TEST_CUDA)
if(CMake_TEST_CUDA STREQUAL "NVIDIA")
target_link_options(LinkOptions_host_link_options PRIVATE -Wl,OPT1 -Xlinker=OPT2 "SHELL:-Xlinker OPT3" "SHELL:LINKER:OPT4 LINKER:OPT5")
elseif(CMake_TEST_CUDA STREQUAL "Clang")
target_link_options(LinkOptions_host_link_options PRIVATE -Wl,OPT1 "SHELL:-Xlinker OPT2" "SHELL:LINKER:OPT3 LINKER:OPT4")
if(CMAKE_CUDA_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC")
target_link_options(LinkOptions_host_link_options PRIVATE OPT1 "SHELL:OPT2" "SHELL:LINKER:OPT3 LINKER:OPT4")
else()
target_link_options(LinkOptions_host_link_options PRIVATE -Wl,OPT1 "SHELL:-Xlinker OPT2" "SHELL:LINKER:OPT3 LINKER:OPT4")
endif()
endif()
add_executable(LinkOptions_no_device LinkOptionsDevice.cu)
@@ -58,5 +62,6 @@ if (CMake_TEST_CUDA)
file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/info.cmake"
"set(CMAKE_CUDA_COMPILER_HAS_DEVICE_LINK_PHASE \"${CMAKE_CUDA_COMPILER_HAS_DEVICE_LINK_PHASE}\")\n"
"set(CMAKE_CUDA_COMPILER_FRONTEND_VARIANT \"${CMAKE_CUDA_COMPILER_FRONTEND_VARIANT}\")\n"
)
endif()