diff --git a/libc/cmake/modules/prepare_libc_gpu_build.cmake b/libc/cmake/modules/prepare_libc_gpu_build.cmake --- a/libc/cmake/modules/prepare_libc_gpu_build.cmake +++ b/libc/cmake/modules/prepare_libc_gpu_build.cmake @@ -12,13 +12,8 @@ "sm_70;sm_72;sm_75;sm_80;sm_86") set(all_gpu_architectures "${all_amdgpu_architectures};${all_nvptx_architectures}") -set(LIBC_GPU_ARCHITECTURES ${all_gpu_architectures} CACHE STRING +set(LIBC_GPU_ARCHITECTURES "all" CACHE STRING "List of GPU architectures to build the libc for.") -if(LIBC_GPU_ARCHITECTURES STREQUAL "all") - set(LIBC_GPU_ARCHITECTURES ${all_gpu_architectures} FORCE) -endif() -message(STATUS "Building libc for the following GPU architectures: " - "${LIBC_GPU_ARCHITECTURES}") # Ensure the compiler is a valid clang when building the GPU target. set(req_ver "${LLVM_VERSION_MAJOR}.${LLVM_VERSION_MINOR}.${LLVM_VERSION_PATCH}") @@ -29,10 +24,42 @@ " is not `Clang ${req_ver}.") endif() if(NOT LLVM_LIBC_FULL_BUILD) - message(STATUS "LLVM_LIBC_FULL_BUILD must be enabled to build libc for GPU. " - "Overriding LLVM_LIBC_FULL_BUILD to ON.") - set(LLVM_LIBC_FULL_BUILD ON FORCE) + message(FATAL_ERROR "LLVM_LIBC_FULL_BUILD must be enabled to build libc for " + "GPU.") +endif() + +# Identify any locally installed AMD GPUs on the system using 'amdgpu-arch'. +find_program(LIBC_AMDGPU_ARCH + NAMES amdgpu-arch + PATHS ${LLVM_BINARY_DIR}/bin /opt/rocm/llvm/bin/) + +# Identify any locally installed NVIDIA GPUs on the system using 'nvptx-arch'. +find_program(LIBC_NVPTX_ARCH + NAMES nvptx-arch + PATHS ${LLVM_BINARY_DIR}/bin) + +# Get the list of all natively supported GPU architectures. +set(detected_gpu_architectures "") +foreach(arch_tool ${LIBC_NVPTX_ARCH} ${LIBC_AMDGPU_ARCH}) + if(arch_tool) + execute_process(COMMAND ${arch_tool} + OUTPUT_VARIABLE arch_tool_output + OUTPUT_STRIP_TRAILING_WHITESPACE) + string(REPLACE "\n" ";" arch_list "${arch_tool_output}") + list(APPEND detected_gpu_architectures "${arch_list}") + endif() +endforeach() + +if(LIBC_GPU_ARCHITECTURES STREQUAL "all") + set(LIBC_GPU_ARCHITECTURES ${all_gpu_architectures}) +elseif(LIBC_GPU_ARCHITECTURES STREQUAL "native") + if(NOT detected_gpu_architectures) + message(FATAL_ERROR "No GPUs found on the system when using 'native'") + endif() + set(LIBC_GPU_ARCHITECTURES ${detected_gpu_architectures}) endif() +message(STATUS "Building libc for the following GPU architecture(s): " + "${LIBC_GPU_ARCHITECTURES}") # Identify the program used to package multiple images into a single binary. find_program(LIBC_CLANG_OFFLOAD_PACKAGER @@ -44,68 +71,30 @@ endif() set(LIBC_GPU_TEST_ARCHITECTURE "" CACHE STRING "Architecture for the GPU tests") -if(LIBC_GPU_TEST_ARCHITECTURE) - message(STATUS "Using user-specified GPU architecture for testing " - "'${LIBC_GPU_TEST_ARCHITECTURE}'") - if("${LIBC_GPU_TEST_ARCHITECTURE}" IN_LIST all_amdgpu_architectures) - set(LIBC_GPU_TARGET_ARCHITECTURE_IS_AMDGPU TRUE) - set(LIBC_GPU_TARGET_TRIPLE "amdgcn-amd-amdhsa") - set(LIBC_GPU_TARGET_ARCHITECTURE "${LIBC_GPU_TEST_ARCHITECTURE}") - elseif("${LIBC_GPU_TEST_ARCHITECTURE}" IN_LIST all_nvptx_architectures) - set(LIBC_GPU_TARGET_ARCHITECTURE_IS_NVPTX TRUE) - set(LIBC_GPU_TARGET_TRIPLE "nvptx64-nvidia-cuda") - set(LIBC_GPU_TARGET_ARCHITECTURE "${LIBC_GPU_TEST_ARCHITECTURE}") - else() - message(FATAL_ERROR - "Unknown GPU architecture '${LIBC_GPU_TARGET_ARCHITECTURE}'") - endif() - return() -endif() - -# Identify any locally installed AMD GPUs on the system to use for testing. -find_program(LIBC_AMDGPU_ARCH - NAMES amdgpu-arch - PATHS ${LLVM_BINARY_DIR}/bin /opt/rocm/llvm/bin/) -if(LIBC_AMDGPU_ARCH) - execute_process(COMMAND ${LIBC_AMDGPU_ARCH} - OUTPUT_VARIABLE LIBC_AMDGPU_ARCH_OUTPUT - OUTPUT_STRIP_TRAILING_WHITESPACE) - string(FIND "${LIBC_AMDGPU_ARCH_OUTPUT}" "\n" first_arch_string) - string(SUBSTRING "${LIBC_AMDGPU_ARCH_OUTPUT}" 0 ${first_arch_string} - arch_string) - if(arch_string) - set(LIBC_GPU_TARGET_ARCHITECTURE_IS_AMDGPU TRUE) - set(LIBC_GPU_TARGET_TRIPLE "amdgcn-amd-amdhsa") - set(LIBC_GPU_TARGET_ARCHITECTURE "${arch_string}") - endif() -endif() -if(LIBC_GPU_TARGET_ARCHITECTURE_IS_AMDGPU) - message(STATUS "Found an installed AMD GPU on the system with target " - "architecture ${LIBC_GPU_TARGET_ARCHITECTURE} ") +set(gpu_test_architecture "") +if(LIBC_GPU_TEST_ARCHITECTURE) + set(gpu_test_architecture ${LIBC_GPU_TEST_ARCHITECTURE}) + message(STATUS "Using user-specified GPU architecture for testing: " + "'${gpu_test_architecture}'") +elseif(detected_gpu_architectures) + list(GET detected_gpu_architectures 0 gpu_test_architecture) + message(STATUS "Using GPU architecture detected on the system for testing: " + "'${gpu_test_architecture}'") +else() + message(STATUS "No GPU architecture set for testing. GPU tests will not be " + "availibe.") return() endif() -# Identify any locally installed NVIDIA GPUs on the system to use for testing. -find_program(LIBC_NVPTX_ARCH - NAMES nvptx-arch - PATHS ${LLVM_BINARY_DIR}/bin) -if(LIBC_NVPTX_ARCH) - execute_process(COMMAND ${LIBC_NVPTX_ARCH} - OUTPUT_VARIABLE LIBC_NVPTX_ARCH_OUTPUT - OUTPUT_STRIP_TRAILING_WHITESPACE) - string(FIND "${LIBC_NVPTX_ARCH_OUTPUT}" "\n" first_arch_string) - string(SUBSTRING "${LIBC_NVPTX_ARCH_OUTPUT}" 0 ${first_arch_string} - arch_string) - if(arch_string) - set(LIBC_GPU_TARGET_ARCHITECTURE_IS_NVPTX TRUE) - set(LIBC_GPU_TARGET_TRIPLE "nvptx64-nvidia-cuda") - set(LIBC_GPU_TARGET_ARCHITECTURE "${arch_string}") - endif() -endif() - -if(LIBC_GPU_TARGET_ARCHITECTURE_IS_NVPTX) - message(STATUS "Found an installed NVIDIA GPU on the system with target " - "architecture ${LIBC_GPU_TARGET_ARCHITECTURE} ") - return() +if("${gpu_test_architecture}" IN_LIST all_amdgpu_architectures) + set(LIBC_GPU_TARGET_ARCHITECTURE_IS_AMDGPU TRUE) + set(LIBC_GPU_TARGET_TRIPLE "amdgcn-amd-amdhsa") + set(LIBC_GPU_TARGET_ARCHITECTURE "${gpu_test_architecture}") +elseif("${gpu_test_architecture}" IN_LIST all_nvptx_architectures) + set(LIBC_GPU_TARGET_ARCHITECTURE_IS_NVPTX TRUE) + set(LIBC_GPU_TARGET_TRIPLE "nvptx64-nvidia-cuda") + set(LIBC_GPU_TARGET_ARCHITECTURE "${gpu_test_architecture}") +else() + message(FATAL_ERROR "Unknown GPU architecture '${gpu_test_architecture}'") endif()