From c2fe87aaadcc82ea479884747d94167a062d4881 Mon Sep 17 00:00:00 2001 From: Chuck Walbourn Date: Mon, 12 Feb 2024 12:41:37 -0800 Subject: [PATCH] CMake refactor (#144) --- CMakeLists.txt | 162 ++------------------------------ UVAtlas/pch.h | 10 +- build/CompilerAndLinker.cmake | 169 ++++++++++++++++++++++++++++++++++ 3 files changed, 179 insertions(+), 162 deletions(-) create mode 100644 build/CompilerAndLinker.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index b0fd41a..24f51de 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -48,26 +48,6 @@ set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/lib") set(CMAKE_LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/lib") set(CMAKE_RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/bin") -if(DEFINED VCPKG_TARGET_ARCHITECTURE) - set(DIRECTX_ARCH ${VCPKG_TARGET_ARCHITECTURE}) -elseif(CMAKE_GENERATOR_PLATFORM MATCHES "^[Ww][Ii][Nn]32$") - set(DIRECTX_ARCH x86) -elseif(CMAKE_GENERATOR_PLATFORM MATCHES "^[Xx]64$") - set(DIRECTX_ARCH x64) -elseif(CMAKE_GENERATOR_PLATFORM MATCHES "^[Aa][Rr][Mm]$") - set(DIRECTX_ARCH arm) -elseif(CMAKE_GENERATOR_PLATFORM MATCHES "^[Aa][Rr][Mm]64$") - set(DIRECTX_ARCH arm64) -elseif(CMAKE_VS_PLATFORM_NAME_DEFAULT MATCHES "^[Ww][Ii][Nn]32$") - set(DIRECTX_ARCH x86) -elseif(CMAKE_VS_PLATFORM_NAME_DEFAULT MATCHES "^[Xx]64$") - set(DIRECTX_ARCH x64) -elseif(CMAKE_VS_PLATFORM_NAME_DEFAULT MATCHES "^[Aa][Rr][Mm]$") - set(DIRECTX_ARCH arm) -elseif(CMAKE_VS_PLATFORM_NAME_DEFAULT MATCHES "^[Aa][Rr][Mm]64$") - set(DIRECTX_ARCH arm64) -endif() - if(WINDOWS_STORE OR (DEFINED XBOX_CONSOLE_TARGET)) set(BUILD_TOOLS OFF) endif() @@ -183,39 +163,6 @@ if(ENABLE_USE_EIGEN) target_compile_definitions(${PROJECT_NAME} PRIVATE UVATLAS_USE_EIGEN) endif() -include(CheckIncludeFileCXX) - -if(DEFINED XBOX_CONSOLE_TARGET) - message(STATUS "Building for Xbox Console Target: ${XBOX_CONSOLE_TARGET}") - set(CMAKE_REQUIRED_QUIET ON) - if(XBOX_CONSOLE_TARGET STREQUAL "durango") - message(FATAL_ERROR "This library no longer supports legacy Xbox One XDK.") - else() - CHECK_INCLUDE_FILE_CXX(gxdk.h GXDK_HEADER) - if(NOT GXDK_HEADER) - message(FATAL_ERROR "Microsoft GDK with Xbox Extensions required to build for Xbox. See https://aka.ms/gdkx") - endif() - target_compile_definitions(${PROJECT_NAME} PUBLIC WINAPI_FAMILY=WINAPI_FAMILY_GAMES) - if(XBOX_CONSOLE_TARGET STREQUAL "scarlett") - CHECK_INCLUDE_FILE_CXX(d3d12_xs.h D3D12XS_HEADER) - if(NOT D3D12XS_HEADER) - message(FATAL_ERROR "Microsoft GDK with Xbox Extensions environment needs to be set for Xbox Series X|S.") - endif() - target_compile_definitions(${PROJECT_NAME} PUBLIC _GAMING_XBOX _GAMING_XBOX_SCARLETT) - elseif(XBOX_CONSOLE_TARGET STREQUAL "xboxone") - CHECK_INCLUDE_FILE_CXX(d3d12_x.h D3D12X_HEADER) - if(NOT D3D12X_HEADER) - message(FATAL_ERROR "Microsoft GDK with Xbox Extensions environment needs to be set for Xbox One.") - endif() - target_compile_definitions(${PROJECT_NAME} PUBLIC _GAMING_XBOX _GAMING_XBOX_XBOXONE) - else() - message(FATAL_ERROR "Unknown XBOX_CONSOLE_TARGET") - endif() - endif() -elseif(WINDOWS_STORE) - target_compile_definitions(${PROJECT_NAME} PUBLIC WINAPI_FAMILY=WINAPI_FAMILY_APP) -endif() - #--- Package include(CMakePackageConfigHelpers) @@ -313,59 +260,25 @@ endif() if(MSVC) foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE /Wall /EHsc /GR- "$<$>:/guard:cf>") - target_link_options(${t} PRIVATE /DYNAMICBASE /NXCOMPAT /INCREMENTAL:NO) - endforeach() - - if((CMAKE_SIZEOF_VOID_P EQUAL 4) AND (NOT (${DIRECTX_ARCH} MATCHES "^arm"))) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_link_options(${t} PRIVATE /SAFESEH) - endforeach() - endif() - - if((MSVC_VERSION GREATER_EQUAL 1928) - AND (CMAKE_SIZEOF_VOID_P EQUAL 8) - AND ((NOT (CMAKE_CXX_COMPILER_ID MATCHES "Clang|IntelLLVM")) OR (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 13.0))) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE "$<$>:/guard:ehcont>") - target_link_options(${t} PRIVATE "$<$>:/guard:ehcont>") - endforeach() - endif() -else() - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_definitions(${t} PRIVATE $,_DEBUG,NDEBUG>) + target_compile_options(${t} PRIVATE /Wall /EHsc /GR-) endforeach() endif() -if(XBOX_CONSOLE_TARGET STREQUAL "scarlett") - target_compile_options(${PROJECT_NAME} PRIVATE $,/favor:AMD64 /arch:AVX2,-march=znver2>) -elseif(XBOX_CONSOLE_TARGET STREQUAL "xboxone") - target_compile_options(${PROJECT_NAME} PRIVATE $,/favor:AMD64 /arch:AVX,-march=btver2>) -elseif(NOT (${DIRECTX_ARCH} MATCHES "^arm")) - if(CMAKE_SIZEOF_VOID_P EQUAL 4) - set(ARCH_SSE2 $<$:/arch:SSE2> $<$>:-msse2>) - else() - set(ARCH_SSE2 $<$>:-msse2>) - endif() +include(build/CompilerAndLinker.cmake) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE ${ARCH_SSE2}) - endforeach() -endif() +foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) + target_compile_definitions(${t} PRIVATE ${COMPILER_DEFINES}) + target_compile_options(${t} PRIVATE ${COMPILER_SWITCHES}) + target_link_options(${t} PRIVATE ${LINKER_SWITCHES}) +endforeach() if(MINGW) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) + foreach(t IN LISTS TOOL_EXES) target_link_options(${t} PRIVATE -municode) endforeach() endif() if(CMAKE_CXX_COMPILER_ID MATCHES "Clang|IntelLLVM") - if(MSVC AND (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 16.0)) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE /ZH:SHA_256) - endforeach() - endif() - set(WarningsLib -Wall -Wpedantic -Wextra) if(CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 16.0) list(APPEND WarningsLib "-Wno-unsafe-buffer-usage") @@ -381,28 +294,14 @@ elseif(CMAKE_CXX_COMPILER_ID MATCHES "GNU") target_compile_options(${t} PRIVATE "-Wno-ignored-attributes" "-Walloc-size-larger-than=4GB") endforeach() elseif(CMAKE_CXX_COMPILER_ID MATCHES "Intel") - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE /Zc:__cplusplus /Zc:inline /fp:fast /Qdiag-disable:161) - endforeach() set_target_properties(${PROJECT_NAME} PROPERTIES CXX_STANDARD 14) elseif(CMAKE_CXX_COMPILER_ID MATCHES "MSVC") - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE /sdl /permissive- /JMC- /Zc:__cplusplus /Zc:inline /fp:fast) - endforeach() - if(ENABLE_CODE_ANALYSIS) foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) target_compile_options(${t} PRIVATE /analyze) endforeach() endif() - if(CMAKE_INTERPROCEDURAL_OPTIMIZATION) - message(STATUS "Building using Whole Program Optimization") - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE /Gy /Gw) - endforeach() - endif() - if(ENABLE_SPECTRE_MITIGATION AND (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.13) AND (NOT WINDOWS_STORE)) @@ -412,49 +311,6 @@ elseif(CMAKE_CXX_COMPILER_ID MATCHES "MSVC") endforeach() endif() - if(CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.24) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE /ZH:SHA_256) - endforeach() - endif() - - if(CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.26) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE /Zc:preprocessor /wd5105) - endforeach() - endif() - - if((CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.27) AND (NOT (${DIRECTX_ARCH} MATCHES "^arm"))) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_link_options(${t} PRIVATE /CETCOMPAT) - endforeach() - endif() - - if(CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.28) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE /Zc:lambda) - endforeach() - endif() - - if(CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.35) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE /Zc:checkGwOdr) - endforeach() - - if(NOT (DEFINED XBOX_CONSOLE_TARGET)) - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE $<$:/Zc:templateScope>) - endforeach() - endif() - endif() - - if(OpenMP_CXX_FOUND) - # OpenMP in MSVC is not compatible with /permissive- unless you disable two-phase lookup - foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_options(${t} PRIVATE /Zc:twoPhase-) - endforeach() - endif() - set(WarningsEXE "/wd4365" "/wd4514" "/wd4625" "/wd4626" "/wd4627" "/wd4668" "/wd4710" "/wd4711" "/wd4751" "/wd4820" "/wd5026" "/wd5027" "/wd5039" "/wd5045" "/wd4061" "/wd4062" "/wd5219") if(CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.34) list(APPEND WarningsEXE "/wd5262" "/wd5264") @@ -475,7 +331,7 @@ if(WIN32) endif() foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) - target_compile_definitions(${t} PRIVATE _UNICODE UNICODE _WIN32_WINNT=${WINVER}) + target_compile_definitions(${t} PRIVATE _WIN32_WINNT=${WINVER}) endforeach() if(DISABLE_MSVC_ITERATOR_DEBUGGING) diff --git a/UVAtlas/pch.h b/UVAtlas/pch.h index ae9a4bf..64bf682 100644 --- a/UVAtlas/pch.h +++ b/UVAtlas/pch.h @@ -34,15 +34,7 @@ // C5264 'const' variable is not used // 26451: Arithmetic overflow: Using operator '*' on a 4 byte value and then casting the result to a 8 byte value. // 26812: The enum type 'x' is unscoped. Prefer 'enum class' over 'enum' (Enum.3). - -// Windows 8.1 SDK related Off by default warnings -#pragma warning(disable : 5029) -// C5029 nonstandard extension used - -// Xbox One XDK related Off by default warnings -#pragma warning(disable : 4643) -// C4643 Forward declaring in namespace std is not permitted by the C++ Standard -#endif +#endif // _MSC_VER #ifdef __clang__ #pragma clang diagnostic ignored "-Wc++98-compat" diff --git a/build/CompilerAndLinker.cmake b/build/CompilerAndLinker.cmake new file mode 100644 index 0000000..44fa1b0 --- /dev/null +++ b/build/CompilerAndLinker.cmake @@ -0,0 +1,169 @@ +# This modules provides variables with recommended Compiler and Linker switches +# +# Copyright (c) Microsoft Corporation. +# Licensed under the MIT License. + +set(COMPILER_DEFINES "") +set(COMPILER_SWITCHES "") +set(LINKER_SWITCHES "") + +#--- Determines target architecture if not explicitly set +if(DEFINED VCPKG_TARGET_ARCHITECTURE) + set(DIRECTX_ARCH ${VCPKG_TARGET_ARCHITECTURE}) +elseif(CMAKE_GENERATOR_PLATFORM MATCHES "^[Ww][Ii][Nn]32$") + set(DIRECTX_ARCH x86) +elseif(CMAKE_GENERATOR_PLATFORM MATCHES "^[Xx]64$") + set(DIRECTX_ARCH x64) +elseif(CMAKE_GENERATOR_PLATFORM MATCHES "^[Aa][Rr][Mm]$") + set(DIRECTX_ARCH arm) +elseif(CMAKE_GENERATOR_PLATFORM MATCHES "^[Aa][Rr][Mm]64$") + set(DIRECTX_ARCH arm64) +elseif(CMAKE_VS_PLATFORM_NAME_DEFAULT MATCHES "^[Ww][Ii][Nn]32$") + set(DIRECTX_ARCH x86) +elseif(CMAKE_VS_PLATFORM_NAME_DEFAULT MATCHES "^[Xx]64$") + set(DIRECTX_ARCH x64) +elseif(CMAKE_VS_PLATFORM_NAME_DEFAULT MATCHES "^[Aa][Rr][Mm]$") + set(DIRECTX_ARCH arm) +elseif(CMAKE_VS_PLATFORM_NAME_DEFAULT MATCHES "^[Aa][Rr][Mm]64$") + set(DIRECTX_ARCH arm64) +endif() + +#--- Build with Unicode Win32 APIs per "UTF-8 Everywhere" +if(WIN32) + list(APPEND COMPILER_DEFINES _UNICODE UNICODE) +endif() + +#--- General MSVC-like SDL options +if(MSVC) + list(APPEND COMPILER_SWITCHES "$<$>:/guard:cf>") + list(APPEND LINKER_SWITCHES /DYNAMICBASE /NXCOMPAT /INCREMENTAL:NO) + + if((${DIRECTX_ARCH} MATCHES "x86") + OR ((CMAKE_SIZEOF_VOID_P EQUAL 4) AND (NOT (${DIRECTX_ARCH} MATCHES "^arm")))) + list(APPEND LINKER_SWITCHES /SAFESEH) + endif() + + if((MSVC_VERSION GREATER_EQUAL 1928) + AND (CMAKE_SIZEOF_VOID_P EQUAL 8) + AND ((NOT (CMAKE_CXX_COMPILER_ID MATCHES "Clang|IntelLLVM")) OR (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 13.0))) + list(APPEND COMPILER_SWITCHES "$<$>:/guard:ehcont>") + list(APPEND LINKER_SWITCHES "$<$>:/guard:ehcont>") + endif() +else() + list(APPEND COMPILER_DEFINES $,_DEBUG,NDEBUG>) +endif() + +#--- Target architecture switches +if(XBOX_CONSOLE_TARGET STREQUAL "scarlett") + list(APPEND COMPILER_SWITCHES $,/favor:AMD64 /arch:AVX2,-march=znver2>) +elseif(XBOX_CONSOLE_TARGET STREQUAL "xboxone|durago") + list(APPEND COMPILER_SWITCHES $,/favor:AMD64 /arch:AVX,-march=btver2>) +elseif(NOT (${DIRECTX_ARCH} MATCHES "^arm")) + if((${DIRECTX_ARCH} MATCHES "x86") OR (CMAKE_SIZEOF_VOID_P EQUAL 4)) + set(ARCH_SSE2 $<$:/arch:SSE2> $<$>:-msse2>) + else() + set(ARCH_SSE2 $<$>:-msse2>) + endif() + + list(APPEND COMPILER_SWITCHES ${ARCH_SSE2}) +endif() + +#--- Compiler-specific switches +if(CMAKE_CXX_COMPILER_ID MATCHES "Clang|IntelLLVM") + if(MSVC AND (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 16.0)) + list(APPEND COMPILER_SWITCHES /ZH:SHA_256) + endif() +elseif(CMAKE_CXX_COMPILER_ID MATCHES "Intel") + list(APPEND COMPILER_SWITCHES /Zc:__cplusplus /Zc:inline /fp:fast /Qdiag-disable:161) +elseif(CMAKE_CXX_COMPILER_ID MATCHES "MSVC") + list(APPEND COMPILER_SWITCHES /sdl /permissive- /JMC- /Zc:__cplusplus /Zc:inline /fp:fast) + + if(CMAKE_INTERPROCEDURAL_OPTIMIZATION) + message(STATUS "Building using Whole Program Optimization") + list(APPEND /Gy /Gw) + endif() + + if(OpenMP_CXX_FOUND) + # OpenMP in MSVC is not compatible with /permissive- unless you disable two-phase lookup + list(APPEND /Zc:twoPhase-) + endif() + + if(CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.24) + list(APPEND COMPILER_SWITCHES /ZH:SHA_256) + endif() + + if((CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.26) + AND (NOT (XBOX_CONSOLE_TARGET STREQUAL "durango"))) + foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) + target_compile_options(${t} PRIVATE /Zc:preprocessor /wd5104 /wd5105) + endforeach() + endif() + + if((CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.27) AND (NOT (${DIRECTX_ARCH} MATCHES "^arm"))) + list(APPEND LINKER_SWITCHES /CETCOMPAT) + endif() + + if(CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.28) + list(APPEND COMPILER_SWITCHES /Zc:lambda) + endif() + + if((CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.31) + AND (XBOX_CONSOLE_TARGET STREQUAL "durango")) + + foreach(t IN LISTS TOOL_EXES ITEMS ${PROJECT_NAME}) + target_compile_options(${t} PRIVATE /Zc:static_assert-) + endforeach() + endif() + + if(CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.35) + list(APPEND COMPILER_SWITCHES /Zc:checkGwOdr) + + if(NOT (DEFINED XBOX_CONSOLE_TARGET)) + list(APPEND COMPILER_SWITCHES $<$:/Zc:templateScope>) + endif() + endif() +endif() + +#--- Windows API Family +include(CheckIncludeFileCXX) + +if(DEFINED XBOX_CONSOLE_TARGET) + message(STATUS "Building for Xbox Console Target: ${XBOX_CONSOLE_TARGET}") + set(CMAKE_REQUIRED_QUIET ON) + if(XBOX_CONSOLE_TARGET STREQUAL "durango") + CHECK_INCLUDE_FILE_CXX(xdk.h XDKLegacy_HEADER) + if(NOT XDKLegacy_HEADER) + message(FATAL_ERROR "Legacy Xbox One XDK required to build for Durango.") + endif() + list(APPEND COMPILER_DEFINES WINAPI_FAMILY=WINAPI_FAMILY_TV_TITLE _XBOX_ONE _TITLE MONOLITHIC=1) + else() + CHECK_INCLUDE_FILE_CXX(gxdk.h GXDK_HEADER) + if(NOT GXDK_HEADER) + message(FATAL_ERROR "Microsoft GDK with Xbox Extensions required to build for Xbox. See https://aka.ms/gdkx") + endif() + list(APPEND COMPILER_DEFINES WINAPI_FAMILY=WINAPI_FAMILY_GAMES) + if(XBOX_CONSOLE_TARGET STREQUAL "scarlett") + CHECK_INCLUDE_FILE_CXX(d3d12_xs.h D3D12XS_HEADER) + if(NOT D3D12XS_HEADER) + message(FATAL_ERROR "Microsoft GDK with Xbox Extensions environment needs to be set for Xbox Series X|S.") + endif() + list(APPEND COMPILER_DEFINES _GAMING_XBOX _GAMING_XBOX_SCARLETT) + elseif(XBOX_CONSOLE_TARGET STREQUAL "xboxone") + CHECK_INCLUDE_FILE_CXX(d3d12_x.h D3D12X_HEADER) + if(NOT D3D12X_HEADER) + message(FATAL_ERROR "Microsoft GDK with Xbox Extensions environment needs to be set for Xbox One.") + endif() + list(APPEND COMPILER_DEFINES _GAMING_XBOX _GAMING_XBOX_XBOXONE) + else() + message(FATAL_ERROR "Unknown XBOX_CONSOLE_TARGET") + endif() + endif() +elseif(WINDOWS_STORE) + list(APPEND COMPILER_DEFINES WINAPI_FAMILY=WINAPI_FAMILY_APP) +endif() + +#--- Address Sanitizer switches +if(CMAKE_CXX_COMPILER_ID MATCHES "MSVC") + set(ASAN_SWITCHES /fsanitize=address /fsanitize-coverage=inline-8bit-counters /fsanitize-coverage=edge /fsanitize-coverage=trace-cmp /fsanitize-coverage=trace-div) + set(ASAN_LIBS sancov.lib) +endif()