1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 535 536 537 538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561 562 563 564 565 566 567 568
|
# ~~~
# Copyright (c) 2014-2023 The Khronos Group Inc.
# Copyright (c) 2014-2023 Valve Corporation
# Copyright (c) 2014-2023 LunarG, Inc.
# Copyright (c) 2021 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
# Copyright (c) 2023-2023 RasterGrid Kft.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
# ~~~
include(CheckIncludeFile)
add_library(loader_specific_options INTERFACE)
target_link_libraries(loader_specific_options INTERFACE loader_common_options Vulkan::Headers)
target_include_directories(loader_specific_options INTERFACE ${CMAKE_CURRENT_SOURCE_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/generated ${CMAKE_CURRENT_BINARY_DIR})
if(WIN32)
if(ENABLE_WIN10_ONECORE)
# Note: When linking your app or driver to OneCore.lib, be sure to remove any links to non-umbrella libs (such as
# kernel32.lib).
set(CMAKE_C_STANDARD_LIBRARIES " ") # space is intentional
endif()
# ~~~
# Only generate the loader.rc file with CMake if BUILD_DLL_VERSIONINFO was set.
# This feature is for the Vulkan Runtime build
# Otherwise rely on the checked in loader.rc from the python script
# ~~~
if (NOT "$CACHE{BUILD_DLL_VERSIONINFO}" STREQUAL "")
string(TIMESTAMP CURRENT_YEAR "%Y")
set(LOADER_CUR_COPYRIGHT_YEAR "${CURRENT_YEAR}")
set(LOADER_RC_VERSION "$CACHE{BUILD_DLL_VERSIONINFO}")
set(LOADER_VER_FILE_VERSION_STR "\"${LOADER_RC_VERSION}\"")
set(LOADER_VER_FILE_DESCRIPTION_STR "\"Vulkan Loader\"")
# RC file wants the value of FILEVERSION to separated by commas
string(REPLACE "." ", " LOADER_VER_FILE_VERSION "${LOADER_RC_VERSION}")
# Configure the file to include the versioning info
# Place it in the build directory - the GN build will use the checked in file
configure_file(loader.rc.in ${CMAKE_CURRENT_BINARY_DIR}/loader.rc)
endif()
else()
# Used to make alloca() and secure_getenv() available
target_compile_definitions(loader_specific_options INTERFACE _GNU_SOURCE)
if(CMAKE_SYSTEM_NAME MATCHES "FreeBSD")
target_compile_definitions(loader_specific_options INTERFACE __BSD_VISIBLE=1)
endif()
check_include_file("alloca.h" HAVE_ALLOCA_H)
if(HAVE_ALLOCA_H)
target_compile_definitions(loader_specific_options INTERFACE HAVE_ALLOCA_H)
endif()
set(THREADS_PREFER_PTHREAD_FLAG ON)
find_package(Threads REQUIRED)
endif()
set(NORMAL_LOADER_SRCS
allocation.c
allocation.h
cJSON.c
cJSON.h
debug_utils.c
debug_utils.h
extension_manual.c
extension_manual.h
loader_environment.c
loader_environment.h
gpa_helper.c
gpa_helper.h
loader.c
loader.h
log.c
log.h
loader_json.c
loader_json.h
settings.c
settings.h
terminator.c
trampoline.c
unknown_function_handling.c
unknown_function_handling.h
wsi.c
wsi.h
)
if(WIN32)
list(APPEND NORMAL_LOADER_SRCS loader_windows.c dirent_on_windows.c)
elseif(CMAKE_SYSTEM_NAME MATCHES "Linux|BSD|DragonFly|GNU")
list(APPEND NORMAL_LOADER_SRCS loader_linux.c)
target_compile_definitions(loader_specific_options INTERFACE LOADER_ENABLE_LINUX_SORT)
endif()
if ("${CMAKE_OSX_ARCHITECTURES}" MATCHES ";")
set(APPLE_UNIVERSAL_BINARY ON)
# When building a universal binary we cannot enable USE_GAS
# Since USE_GAS assumes only 1 architecture (arm64, x64, etc).
set(USE_GAS OFF)
endif()
set(OPT_LOADER_SRCS dev_ext_trampoline.c phys_dev_ext.c)
set(ASM_FAILURE_MSG "Support for unknown physical device and device functions is disabled due to missing the required assembly support code. \
To support unknown functions, assembly must be added for the platform.\n")
set(ARMASM_CMAKE_FAILURE_MSG "Support for unknown physical device and device functions is disabled due to the CMake version ${CMAKE_VERSION} \
being older than 3.26. Please update CMake to version 3.26 or newer.\n")
# Check for assembler support
if(WIN32 AND NOT USE_GAS)
option(USE_MASM "Use MASM" ON)
if(USE_MASM AND MINGW)
find_program(JWASM_FOUND NAMES jwasm uasm)
if (JWASM_FOUND)
set(CMAKE_ASM_MASM_COMPILER ${JWASM_FOUND})
execute_process(COMMAND ${CMAKE_C_COMPILER} -dumpmachine OUTPUT_VARIABLE COMPILER_VERSION_OUTPUT)
if (COMPILER_VERSION_OUTPUT)
if (COMPILER_VERSION_OUTPUT MATCHES "x86_64")
set(JWASM_FLAGS -win64)
else()
# jwasm requires setting the cpu to at least 386 for setting a flat model
set(JWASM_FLAGS -3 -coff)
endif()
endif()
endif()
endif()
if (USE_MASM)
if(SYSTEM_PROCESSOR MATCHES "arm")
if(CMAKE_VERSION VERSION_LESS "3.26.0")
set(ASM_FAILURE_MSG ${ARMASM_CMAKE_FAILURE_MSG})
else()
enable_language(ASM_MARMASM)
set(LOADER_ASM_DIALECT "MARMASM")
endif()
else()
enable_language(ASM_MASM)
set(LOADER_ASM_DIALECT "MASM")
endif()
endif()
# Test if the detected compiler actually works.
# Unfortunately, CMake's detection of ASM_MASM is not reliable, so we need to do this ourselves.
if(SYSTEM_PROCESSOR MATCHES "arm")
if (CMAKE_SIZEOF_VOID_P EQUAL 4)
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/masm_check.asm [=[
test_func FUNCTION
mov r0, #0
bx lr
ENDFUNC
END
]=])
else()
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/masm_check.asm [=[
test_func FUNCTION
mov x1, 26
ldr x0, [x0, x1]
ENDFUNC
END
]=])
endif()
else()
if (CMAKE_SIZEOF_VOID_P EQUAL 4)
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/masm_check.asm [=[
.model flat
.code
extrn _start:near
xor eax, eax
ret
end
]=])
else()
file(WRITE ${CMAKE_CURRENT_BINARY_DIR}/masm_check.asm [=[
.code
extrn start:near
xor rax, rax
ret
end
]=])
endif()
endif ()
if(MINGW)
set(CMAKE_ASM_MASM_FLAGS ${CMAKE_ASM_MASM_FLAGS} ${JWASM_FLAGS})
set(CMAKE_ASM_MARMASM_FLAGS ${CMAKE_ASM_MARMASM_FLAGS} ${JWASM_FLAGS})
elseif(NOT CMAKE_CL_64 AND NOT JWASM_FOUND AND CMAKE_SIZEOF_VOID_P EQUAL 4)
set(CMAKE_ASM_MASM_FLAGS ${CMAKE_ASM_MASM_FLAGS} /safeseh) # /safeseh is only needed in x86
endif()
# try_compile does not work here due to the same reasons as static above.
if(SYSTEM_PROCESSOR MATCHES "arm")
execute_process(COMMAND ${CMAKE_ASM_MARMASM_COMPILER} ${CMAKE_ASM_MARMASM_FLAGS} ${CMAKE_CURRENT_BINARY_DIR}/masm_check.asm
RESULT_VARIABLE ASM_COMPILER_WORKS
OUTPUT_QUIET ERROR_QUIET)
else()
execute_process(COMMAND ${CMAKE_ASM_MASM_COMPILER} ${CMAKE_ASM_MASM_FLAGS} -c -Fo ${CMAKE_CURRENT_BINARY_DIR}/masm_check.obj ${CMAKE_CURRENT_BINARY_DIR}/masm_check.asm
RESULT_VARIABLE ASM_COMPILER_WORKS
OUTPUT_QUIET ERROR_QUIET)
endif()
# Convert the return code to a boolean
if(ASM_COMPILER_WORKS EQUAL 0)
set(ASM_COMPILER_WORKS true)
else()
set(ASM_COMPILER_WORKS false)
endif()
if(ASM_COMPILER_WORKS)
add_executable(asm_offset asm_offset.c)
target_link_libraries(asm_offset PRIVATE loader_specific_options)
# If am emulator is provided (Like Wine), or running on native, run asm_offset to generate gen_defines.asm
if (CMAKE_CROSSCOMPILING_EMULATOR OR NOT CMAKE_CROSSCOMPILING)
add_custom_command(OUTPUT gen_defines.asm DEPENDS asm_offset COMMAND asm_offset ${LOADER_ASM_DIALECT})
else()
# Forces compiler to write the intermediate asm file, needed so that we can get sizeof/offset of info out of it.
target_compile_options(asm_offset PRIVATE "/Fa$<TARGET_FILE_DIR:asm_offset>/asm_offset.asm" /FA)
# Force off optimization so that the output assembly includes all the necessary info - optimizer would get rid of it otherwise.
target_compile_options(asm_offset PRIVATE /Od)
find_package(Python3 REQUIRED QUIET)
# Run parse_asm_values.py on asm_offset's assembly file to generate the gen_defines.asm, which the asm code depends on
add_custom_command(TARGET asm_offset POST_BUILD
COMMAND Python3::Interpreter ${PROJECT_SOURCE_DIR}/scripts/parse_asm_values.py "${CMAKE_CURRENT_BINARY_DIR}/gen_defines.asm"
"$<TARGET_FILE_DIR:asm_offset>/asm_offset.asm" "${LOADER_ASM_DIALECT}" "${CMAKE_C_COMPILER_ID}" "${SYSTEM_PROCESSOR}"
BYPRODUCTS gen_defines.asm
)
endif()
add_custom_target(loader_asm_gen_files DEPENDS gen_defines.asm)
set_target_properties(loader_asm_gen_files PROPERTIES FOLDER ${LOADER_HELPER_FOLDER})
if(SYSTEM_PROCESSOR MATCHES "arm")
list(APPEND OPT_LOADER_SRCS unknown_ext_chain_marmasm.asm)
else()
list(APPEND OPT_LOADER_SRCS unknown_ext_chain_masm.asm)
endif()
set(UNKNOWN_FUNCTIONS_SUPPORTED ON)
else()
message(WARNING "Could not find working ${} assembler\n${ASM_FAILURE_MSG}")
endif()
elseif(UNIX OR MINGW OR (WIN32 AND USE_GAS)) # i.e.: Linux & Apple & MinGW & Windows using Clang-CL
option(USE_GAS "Use GAS" ON)
if(USE_GAS)
if (APPLE_UNIVERSAL_BINARY)
message(FATAL_ERROR "USE_GAS cannot be used when compiling a universal binary!")
endif()
enable_language(ASM)
set(CMAKE_ASM_FLAGS "${CMAKE_C_FLAGS}")
set(CMAKE_TRY_COMPILE_TARGET_TYPE STATIC_LIBRARY)
if(WIN32 AND ${SYSTEM_PROCESSOR} MATCHES "arm64")
# In this particular case, we are using the same approach as for NASM
# This specifically avoids CMake issue #18889
execute_process(COMMAND ${CMAKE_ASM_COMPILER} ${CMAKE_ASM_FLAGS} -c -o ${CMAKE_CURRENT_BINARY_DIR}/asm_test_aarch64.obj ${CMAKE_CURRENT_SOURCE_DIR}/asm_test_aarch64.S
RESULT_VARIABLE WIN_ARM64_ASSEMBLER_WORKS
OUTPUT_QUIET ERROR_QUIET)
if(WIN_ARM64_ASSEMBLER_WORKS EQUAL 0)
set(ASSEMBLER_WORKS true)
endif()
if(ASSEMBLER_WORKS)
list(APPEND OPT_LOADER_SRCS unknown_ext_chain_gas_aarch.S)
endif()
elseif (${SYSTEM_PROCESSOR} MATCHES "aarch64|arm64")
try_compile(ASSEMBLER_WORKS ${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/asm_test_aarch64.S OUTPUT_VARIABLE TRY_COMPILE_OUTPUT)
if(ASSEMBLER_WORKS)
list(APPEND OPT_LOADER_SRCS unknown_ext_chain_gas_aarch.S)
endif()
elseif (${SYSTEM_PROCESSOR} MATCHES "aarch32|armhf|armv7l|armv8l")
try_compile(ASSEMBLER_WORKS ${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/asm_test_aarch32.S OUTPUT_VARIABLE TRY_COMPILE_OUTPUT)
if(ASSEMBLER_WORKS)
list(APPEND OPT_LOADER_SRCS unknown_ext_chain_gas_aarch.S)
endif()
# Covers x86_64, amd64, x86, i386, i686, I386, I686
elseif(${SYSTEM_PROCESSOR} MATCHES "amd64|86")
check_include_file("cet.h" HAVE_CET_H)
if(HAVE_CET_H)
target_compile_definitions(loader_specific_options INTERFACE HAVE_CET_H)
endif()
try_compile(ASSEMBLER_WORKS ${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/asm_test_x86.S)
if(ASSEMBLER_WORKS)
list(APPEND OPT_LOADER_SRCS unknown_ext_chain_gas_x86.S)
endif()
endif()
endif()
# When compiling for x86 on x64, we can't use CMAKE_SYSTEM_PROCESSOR to determine which architecture to use,
# Instead, check the size of void* and if its 4, set ASM_OFFSET_SYSTEM_PROCESSOR to x86 if we aren't on arm
if("${CMAKE_SIZEOF_VOID_P}" EQUAL "8")
set(ASM_OFFSET_SYSTEM_PROCESSOR ${SYSTEM_PROCESSOR}) # x86_64 or aarch64/arm64
string(REPLACE amd64 x86_64 ASM_OFFSET_SYSTEM_PROCESSOR "${ASM_OFFSET_SYSTEM_PROCESSOR}")
else()
if(${SYSTEM_PROCESSOR} MATCHES "86")
set(ASM_OFFSET_SYSTEM_PROCESSOR "x86")
else()
set(ASM_OFFSET_SYSTEM_PROCESSOR ${SYSTEM_PROCESSOR})
endif()
endif()
if(ASSEMBLER_WORKS)
add_executable(asm_offset asm_offset.c)
target_link_libraries(asm_offset loader_specific_options)
# If not cross compiling, run asm_offset to generage gen_defines.asm
if (NOT CMAKE_CROSSCOMPILING)
add_custom_command(OUTPUT gen_defines.asm DEPENDS asm_offset COMMAND asm_offset GAS)
else()
# Forces compiler to write the intermediate asm file, needed so that we can get sizeof/offset of info out of it.
# If with lto, compiler will output IR instead of asm, so we need to explicitly disable lto here.
if(CMAKE_C_COMPILER_ID STREQUAL "GNU")
target_compile_options(asm_offset PRIVATE -save-temps=obj -fno-lto)
elseif(CMAKE_C_COMPILER_ID STREQUAL "Clang" OR CMAKE_C_COMPILER_ID STREQUAL "AppleClang")
target_compile_options(asm_offset PRIVATE -save-temps=obj -fno-lto -fno-whole-program-vtables -fno-virtual-function-elimination)
else()
target_compile_options(asm_offset PRIVATE -save-temps=obj)
endif()
if(CMAKE_C_COMPILER_ID STREQUAL "GNU")
set(ASM_OFFSET_EXECUTABLE_LOCATION "$<TARGET_FILE_DIR:asm_offset>/gen_defines.asm")
set(ASM_OFFSET_INTERMEDIATE_LOCATION "$<TARGET_FILE_DIR:asm_offset>/CMakeFiles/asm_offset.dir/asm_offset.c.s")
elseif(CMAKE_C_COMPILER_ID STREQUAL "Clang")
set(ASM_OFFSET_EXECUTABLE_LOCATION "$<TARGET_FILE_DIR:asm_offset>/gen_defines.asm")
set(ASM_OFFSET_INTERMEDIATE_LOCATION "$<TARGET_FILE_DIR:asm_offset>/CMakeFiles/asm_offset.dir/asm_offset.s")
elseif(CMAKE_C_COMPILER_ID STREQUAL "AppleClang")
# Need to use the current binary dir since the asm_offset.s file is in that folder rather than the bundle
set(ASM_OFFSET_EXECUTABLE_LOCATION "${CMAKE_CURRENT_BINARY_DIR}/gen_defines.asm")
set(ASM_OFFSET_INTERMEDIATE_LOCATION "${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/asm_offset.dir/asm_offset.s")
else()
message(FATAL_ERROR "C_COMPILER_ID not supported!")
endif()
message(STATUS "CMAKE_CROSSCOMPILING FALSE")
find_package(Python3 REQUIRED QUIET)
# Run parse_asm_values.py on asm_offset's assembly file to generate the gen_defines.asm, which the asm code depends on
add_custom_command(TARGET asm_offset POST_BUILD
COMMAND Python3::Interpreter ${PROJECT_SOURCE_DIR}/scripts/parse_asm_values.py "${ASM_OFFSET_EXECUTABLE_LOCATION}"
"${ASM_OFFSET_INTERMEDIATE_LOCATION}" "GAS" "${CMAKE_C_COMPILER_ID}" "${ASM_OFFSET_SYSTEM_PROCESSOR}"
BYPRODUCTS gen_defines.asm
)
endif()
add_custom_target(loader_asm_gen_files DEPENDS gen_defines.asm)
if (APPLE)
set(MODIFY_UNKNOWN_FUNCTION_DECLS ON)
endif()
set(UNKNOWN_FUNCTIONS_SUPPORTED ON)
else()
if(USE_GAS)
message(WARNING "Could not find working ${ASM_OFFSET_SYSTEM_PROCESSOR} GAS assembler\n${ASM_FAILURE_MSG}")
else()
message(WARNING "Assembly sources have been disabled\n${ASM_FAILURE_MSG}")
endif()
endif()
endif()
if(UNKNOWN_FUNCTIONS_SUPPORTED)
list(APPEND NORMAL_LOADER_SRCS ${OPT_LOADER_SRCS})
endif()
if(WIN32)
# If BUILD_DLL_VERSIONINFO was set, use the loader.rc in the build dir, otherwise use the checked in file
set(RC_FILE_LOCATION ${CMAKE_CURRENT_SOURCE_DIR}/loader.rc)
if (NOT "$CACHE{BUILD_DLL_VERSIONINFO}" STREQUAL "")
set(RC_FILE_LOCATION ${CMAKE_CURRENT_BINARY_DIR}/loader.rc)
endif()
add_library(vulkan
SHARED
${NORMAL_LOADER_SRCS}
${CMAKE_CURRENT_SOURCE_DIR}/${API_TYPE}-1.def
${RC_FILE_LOCATION})
target_link_libraries(vulkan PRIVATE loader_specific_options)
# when adding the suffix the import and runtime library names must be consistent
# mingw: libvulkan-1.dll.a / vulkan-1.dll
# msvc: vulkan-1.lib / vulkan-1.dll
set_target_properties(vulkan
PROPERTIES
OUTPUT_NAME ${API_TYPE}-1)
if(MINGW)
# generate the same DLL with mingw
set_target_properties(vulkan
PROPERTIES
PREFIX "")
endif()
if(MSVC AND ENABLE_WIN10_ONECORE)
target_link_libraries(vulkan PRIVATE OneCoreUAP.lib LIBCMT.LIB LIBCMTD.LIB LIBVCRUNTIME.LIB LIBUCRT.LIB)
set_target_properties(vulkan PROPERTIES LINK_FLAGS "/NODEFAULTLIB")
else()
target_link_libraries(vulkan PRIVATE cfgmgr32)
endif()
else()
if(APPLE)
option(APPLE_STATIC_LOADER "Build a loader that can be statically linked. Intended for Chromium usage/testing.")
mark_as_advanced(APPLE_STATIC_LOADER)
endif()
if(APPLE_STATIC_LOADER)
add_library(vulkan STATIC)
target_compile_definitions(vulkan PRIVATE APPLE_STATIC_LOADER)
message(WARNING "The APPLE_STATIC_LOADER option has been set. Note that this will only work on MacOS and is not supported "
"or tested as part of the loader. Use it at your own risk.")
else()
add_library(vulkan SHARED)
endif()
target_sources(vulkan PRIVATE ${NORMAL_LOADER_SRCS})
set_target_properties(vulkan PROPERTIES
SOVERSION "1"
VERSION "${VULKAN_LOADER_VERSION}"
)
target_link_libraries(vulkan PRIVATE ${CMAKE_DL_LIBS} m Threads::Threads)
set_target_properties(vulkan PROPERTIES OUTPUT_NAME ${API_TYPE})
if (LOADER_ENABLE_ADDRESS_SANITIZER)
target_compile_options(vulkan PUBLIC -fsanitize=address,undefined)
target_link_options(vulkan PUBLIC -fsanitize=address,undefined)
endif()
if (LOADER_ENABLE_THREAD_SANITIZER)
target_compile_options(vulkan PUBLIC -fsanitize=thread)
target_link_options(vulkan PUBLIC -fsanitize=thread)
endif()
if(APPLE)
find_library(COREFOUNDATION_LIBRARY NAMES CoreFoundation)
target_link_libraries(vulkan PRIVATE "-framework CoreFoundation")
# Build vulkan.framework
# Use GLOB_RECURSE to find all the header files and populate the vulkan.framework headers with them
# Use CONFIGURE_DEPENDS to ensure that if the header files are updated, this list is also updated
get_target_property(VulkanHeaders_INCLUDE_DIRS Vulkan::Headers INTERFACE_INCLUDE_DIRECTORIES)
file(GLOB_RECURSE CONFIGURE_DEPENDS FRAMEWORK_HEADERS ${VulkanHeaders_INCLUDE_DIRS})
add_library(vulkan-framework SHARED)
target_sources(vulkan-framework PRIVATE ${NORMAL_LOADER_SRCS} ${FRAMEWORK_HEADERS})
if (UNKNOWN_FUNCTIONS_SUPPORTED)
add_dependencies(vulkan-framework loader_asm_gen_files)
endif()
target_link_libraries(vulkan-framework ${CMAKE_DL_LIBS} Threads::Threads -lm "-framework CoreFoundation")
target_link_libraries(vulkan-framework loader_specific_options)
if (MODIFY_UNKNOWN_FUNCTION_DECLS)
# Modifies the names of functions as they appearin the assembly code so that the
# unknown function handling will work
target_compile_definitions(vulkan PRIVATE MODIFY_UNKNOWN_FUNCTION_DECLS)
target_compile_definitions(vulkan-framework PRIVATE MODIFY_UNKNOWN_FUNCTION_DECLS)
endif()
# The FRAMEWORK_VERSION needs to be "A" here so that Xcode code-signing works when a user adds their framework to an Xcode
# project and does "Sign on Copy". It would have been nicer to use "1" to denote Vulkan 1. Although Apple docs say that a
# framework version does not have to be "A", this part of the Apple toolchain expects it.
# https://forums.developer.apple.com/thread/65963
set_target_properties(vulkan-framework PROPERTIES
OUTPUT_NAME vulkan
FRAMEWORK TRUE
FRAMEWORK_VERSION A
VERSION "${VULKAN_LOADER_VERSION}"
MACOSX_FRAMEWORK_BUNDLE_VERSION "${VULKAN_LOADER_VERSION}"
MACOSX_FRAMEWORK_SHORT_VERSION_STRING "${VULKAN_LOADER_VERSION}"
SOVERSION "1.0.0"
MACOSX_FRAMEWORK_IDENTIFIER com.lunarg.vulkanFramework
PUBLIC_HEADER "${FRAMEWORK_HEADERS}"
)
# Workaround linker warning: https://github.com/KhronosGroup/Vulkan-Loader/issues/1332
#
# MACHO_CURRENT_VERSION specifically applies to the -current_version linker option which is the
# linker warning we are trying to address.
set(APPLE_VULKAN_LOADER_VERSION "${VULKAN_LOADER_VERSION_MAJOR}.${VULKAN_LOADER_VERSION_MINOR}.0")
set_target_properties(vulkan PROPERTIES MACHO_CURRENT_VERSION "${APPLE_VULKAN_LOADER_VERSION}")
set_target_properties(vulkan-framework PROPERTIES MACHO_CURRENT_VERSION "${APPLE_VULKAN_LOADER_VERSION}")
install(TARGETS vulkan-framework
PUBLIC_HEADER DESTINATION vulkan
FRAMEWORK DESTINATION loader
)
endif()
endif()
option(LOADER_USE_UNSAFE_FILE_SEARCH "Allows the loader to search in unsafe locations")
if (LOADER_USE_UNSAFE_FILE_SEARCH)
target_compile_definitions(vulkan PRIVATE LOADER_USE_UNSAFE_FILE_SEARCH)
endif()
# common attributes of the vulkan library
target_link_libraries(vulkan PRIVATE loader_specific_options)
target_link_libraries(vulkan PRIVATE Vulkan::Headers)
add_library(Vulkan::Loader ALIAS vulkan)
if (UNKNOWN_FUNCTIONS_SUPPORTED)
target_compile_definitions(vulkan PRIVATE UNKNOWN_FUNCTIONS_SUPPORTED)
add_dependencies(vulkan loader_asm_gen_files)
endif()
if (BUILD_TESTS)
target_compile_definitions(vulkan PRIVATE SHOULD_EXPORT_TEST_FUNCTIONS)
endif()
if (APPLE_STATIC_LOADER)
# TLDR: This feature only exists at the request of Google for Chromium. No other project should use this!
message(NOTICE "Apple STATIC lib: it will be built but not installed, and vulkan.pc and VulkanLoaderConfig.cmake won't be generated!")
return()
endif()
# Generate CMake Configuration File (IE: VulkanLoaderConfig.cmake)
install(TARGETS vulkan EXPORT VulkanLoaderConfig)
set_target_properties(vulkan PROPERTIES EXPORT_NAME "Loader")
install(EXPORT VulkanLoaderConfig DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/VulkanLoader NAMESPACE Vulkan::)
# Generate CMake Version File (IE: VulkanLoaderConfigVersion.cmake)
include(CMakePackageConfigHelpers)
set(version_config "${CMAKE_CURRENT_BINARY_DIR}/generated/VulkanLoaderConfigVersion.cmake")
write_basic_package_version_file("${version_config}" COMPATIBILITY SameMajorVersion)
install(FILES "${version_config}" DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/VulkanLoader)
# Generate PkgConfig File (IE: vulkan.pc)
# NOTE: Hopefully in the future CMake can generate .pc files natively.
# https://gitlab.kitware.com/cmake/cmake/-/issues/22621
find_package(PkgConfig)
if (PKG_CONFIG_FOUND)
if(WIN32)
if(MINGW)
set(VULKAN_LIB_SUFFIX "-1.dll")
else()
set(VULKAN_LIB_SUFFIX "-1")
endif()
endif()
# BUG: The following code will NOT work well with `cmake --install ... --prefix <dir>`
# due to this code relying on CMAKE_INSTALL_PREFIX being defined at configure time.
#
# NOTE: vulkan.pc essentially cover both Vulkan-Loader and Vulkan-Headers for legacy reasons.
if ("${CMAKE_INSTALL_PREFIX}" STREQUAL "")
set(CMAKE_INSTALL_LIBDIR_PC ${CMAKE_INSTALL_FULL_LIBDIR})
set(CMAKE_INSTALL_INCLUDEDIR_PC ${CMAKE_INSTALL_FULL_INCLUDEDIR})
else()
file(RELATIVE_PATH CMAKE_INSTALL_LIBDIR_PC ${CMAKE_INSTALL_PREFIX} ${CMAKE_INSTALL_FULL_LIBDIR})
file(RELATIVE_PATH CMAKE_INSTALL_INCLUDEDIR_PC ${CMAKE_INSTALL_PREFIX} ${CMAKE_INSTALL_FULL_INCLUDEDIR})
endif()
configure_file("vulkan.pc.in" "vulkan.pc" @ONLY)
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/vulkan.pc" DESTINATION "${CMAKE_INSTALL_LIBDIR}/pkgconfig" RENAME "${API_TYPE}.pc")
endif()
if (CODE_COVERAGE)
target_code_coverage(vulkan AUTO ALL)
endif()
|