1
0
mirror of https://github.com/Kitware/CMake.git synced 2025-10-14 02:08:27 +08:00

cmake: Restore acceptance of -DCMAKE_TOOLCHAIN_FILE=//... on non-Windows

POSIX specifies that two leading slashes have implementation-defined
interpretation, so CMake 3.31 and below did not normalize away leading
double slashes.  However, most implementations simply treat a leading
`//` as just `/`, so CMake 4.0 now normalizes them away when they do not
correspond to a network path on Windows.

This change exposed that we were not normalizing `CMAKE_TOOLCHAIN_FILE`
before passing its value to `include()` the first time if it was not
passed with the `FILEPATH` or `PATH` cache entry type.  Fix that.

Fixes: #27010
This commit is contained in:
Brad King
2025-06-23 10:29:47 -04:00
parent cf0f46ed85
commit c393300e2b
4 changed files with 23 additions and 10 deletions

View File

@@ -139,17 +139,24 @@ endif()
# variables around so they can be used in CMakeLists.txt.
# In all other cases, the host and target platform are the same.
if(CMAKE_TOOLCHAIN_FILE)
# at first try to load it as path relative to the directory from which cmake has been run
include("${CMAKE_BINARY_DIR}/${CMAKE_TOOLCHAIN_FILE}" OPTIONAL RESULT_VARIABLE _INCLUDED_TOOLCHAIN_FILE)
if(NOT _INCLUDED_TOOLCHAIN_FILE)
# if the file isn't found there, check the default locations
include("${CMAKE_TOOLCHAIN_FILE}" OPTIONAL RESULT_VARIABLE _INCLUDED_TOOLCHAIN_FILE)
endif()
if(_INCLUDED_TOOLCHAIN_FILE)
set(CMAKE_TOOLCHAIN_FILE "${_INCLUDED_TOOLCHAIN_FILE}" CACHE FILEPATH "The CMake toolchain file" FORCE)
if(IS_ABSOLUTE "${CMAKE_TOOLCHAIN_FILE}" AND EXISTS "${CMAKE_TOOLCHAIN_FILE}")
# Normalize the absolute path.
set(CMAKE_TOOLCHAIN_FILE "${CMAKE_TOOLCHAIN_FILE}" CACHE FILEPATH "The CMake toolchain file" FORCE)
set(CMAKE_TOOLCHAIN_FILE "$CACHE{CMAKE_TOOLCHAIN_FILE}")
include("${CMAKE_TOOLCHAIN_FILE}" OPTIONAL RESULT_VARIABLE _INCLUDED_TOOLCHAIN_FILE)
else()
message(FATAL_ERROR "Could not find toolchain file: ${CMAKE_TOOLCHAIN_FILE}")
# at first try to load it as path relative to the directory from which cmake has been run
include("${CMAKE_BINARY_DIR}/${CMAKE_TOOLCHAIN_FILE}" OPTIONAL RESULT_VARIABLE _INCLUDED_TOOLCHAIN_FILE)
if(NOT _INCLUDED_TOOLCHAIN_FILE)
# if the file isn't found there, check the default locations
include("${CMAKE_TOOLCHAIN_FILE}" OPTIONAL RESULT_VARIABLE _INCLUDED_TOOLCHAIN_FILE)
endif()
if(_INCLUDED_TOOLCHAIN_FILE)
set(CMAKE_TOOLCHAIN_FILE "${_INCLUDED_TOOLCHAIN_FILE}" CACHE FILEPATH "The CMake toolchain file" FORCE)
endif()
endif()
if(NOT _INCLUDED_TOOLCHAIN_FILE)
message(FATAL_ERROR "Could not find toolchain file:\n \"${CMAKE_TOOLCHAIN_FILE}\"")
endif()
endif()

View File

@@ -264,6 +264,10 @@ function(run_Toolchain)
run_cmake_with_options(toolchain-no-arg -S ${source_dir} --toolchain=)
run_cmake_with_options(toolchain-valid-abs-path -S ${source_dir} --toolchain "${source_dir}/toolchain.cmake")
run_cmake_with_options(toolchain-valid-rel-src-path -S ${source_dir} --toolchain=toolchain.cmake)
run_cmake_with_options(toolchain-D-abs-path -S ${source_dir} -DCMAKE_TOOLCHAIN_FILE=${source_dir}/toolchain.cmake)
if(CMAKE_HOST_UNIX AND NOT CMAKE_SYSTEM_NAME STREQUAL "CYGWIN" AND NOT CMAKE_SYSTEM_NAME STREQUAL "MSYS")
run_cmake_with_options(toolchain-D-slash-abs-path -S ${source_dir} -DCMAKE_TOOLCHAIN_FILE=/${source_dir}/toolchain.cmake)
endif()
set(RunCMake_TEST_NO_CLEAN 1)
set(binary_dir ${RunCMake_BINARY_DIR}/Toolchain-build)

View File

@@ -0,0 +1 @@
CMAKE_TOOLCHAIN_FILE='[^']*/Tests/RunCMake/CommandLine/Toolchain/toolchain\.cmake'

View File

@@ -0,0 +1 @@
CMAKE_TOOLCHAIN_FILE='/[^/][^']*/Tests/RunCMake/CommandLine/Toolchain/toolchain\.cmake'