Skip to content

Commit 5332b16

Browse files
committed
Workaround broken ARM64X / MSVC_BUILD_AS_X builds (#7827)
Currently, when internal pipelines build for ARM64X we use the older experimental `MSVC_BUILD_AS_X` feature. The latest VS release has regressed this functionality, resulting in the import libs for the ARM64 and ARM64X DLLs being written to the same location. Remember that ARM64X binaries are fat binaries containing both ARM64 and ARM64EC code. When building for ARM64 with MSVC_BUILD_AS_X, the Visual Studio cmake generator actually generates vcxproj files that build ARM64 and ARM64EC (with the ARM64EC version being the one that becomes the combined ARM64X binary. The generated project knows how to ensure that the ARM64 DLL is built to one location and the ARM64X one goes into the destination specified in the cmake scripts. However, the import libraries end up being configured to go into the same location, resulting in a race condition. Our cmake scripts have no knowledge of these two platforms, and so there's no direct way to address this. This workaround makes it so that when building in this mode the import libraries are written to a location containing `$(PLATFORM)`. This is a msbuild variable that's evaluated at build time. This is a short-term fix that allows us to unblock our internal pipelines. Longer-term we should move to using the [documented ARM64X approach](https://learn.microsoft.com/en-us/windows/arm/arm64x-build#building-an-arm64x-dll-with-cmake), at which point this change should be reverted. (cherry picked from commit ea7e910)
1 parent 0352ada commit 5332b16

File tree

1 file changed

+24
-0
lines changed

1 file changed

+24
-0
lines changed

cmake/modules/AddLLVM.cmake

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -222,11 +222,35 @@ function(set_output_directory target bindir libdir)
222222
set(moddir ${libdir})
223223
endif()
224224
if(NOT "${CMAKE_CFG_INTDIR}" STREQUAL ".")
225+
# HLSL change begin: work around broken MSVC_BUILD_AS_X
226+
get_target_property(target_type ${target} TYPE)
227+
if(target_type STREQUAL "SHARED_LIBRARY" AND MSVC_BUILD_AS_X EQUAL 1)
228+
set(arm64x_workaround 1)
229+
message(NOTICE "Working around ARM64X / MSVC_BUILD_AS_X bug for ${target}")
230+
else()
231+
set(arm64x_workaround 0)
232+
endif()
233+
# HLSL change end
234+
225235
foreach(build_mode ${CMAKE_CONFIGURATION_TYPES})
226236
string(TOUPPER "${build_mode}" CONFIG_SUFFIX)
227237
string(REPLACE ${CMAKE_CFG_INTDIR} ${build_mode} bi ${bindir})
228238
string(REPLACE ${CMAKE_CFG_INTDIR} ${build_mode} li ${libdir})
229239
string(REPLACE ${CMAKE_CFG_INTDIR} ${build_mode} mi ${moddir})
240+
241+
# HLSL change begin: work around broken MSVC_BUILD_AS_X
242+
#
243+
# MSVC_BUILD_AS_X generates a vcxproj that builds for both ARM64 and
244+
# ARM64EC, but these two platforms are only visible in msbuild. It also
245+
# currently configures the import libraries to all be output to the same
246+
# location, which means it's a race for if we get the ARM64 or ARM64X
247+
# version there. The appended $(PLATFORM) is evaluated by msbuild at
248+
# build time to separate the ARM64EC from ARM64 builds.
249+
if(arm64x_workaround EQUAL 1)
250+
string(APPEND li "/$(PLATFORM)")
251+
endif()
252+
# HLSL change end
253+
230254
set_target_properties(${target} PROPERTIES "RUNTIME_OUTPUT_DIRECTORY_${CONFIG_SUFFIX}" ${bi})
231255
set_target_properties(${target} PROPERTIES "ARCHIVE_OUTPUT_DIRECTORY_${CONFIG_SUFFIX}" ${li})
232256
set_target_properties(${target} PROPERTIES "LIBRARY_OUTPUT_DIRECTORY_${CONFIG_SUFFIX}" ${mi})

0 commit comments

Comments
 (0)