1# Distributed under the OSI-approved BSD 3-Clause License. See accompanying 2# file Copyright.txt or https://cmake.org/licensing for details. 3 4 5# This module is shared by multiple languages; use include blocker. 6if(__WINDOWS_CLANG) 7 return() 8endif() 9set(__WINDOWS_CLANG 1) 10 11set(__pch_header_C "c-header") 12set(__pch_header_CXX "c++-header") 13set(__pch_header_OBJC "objective-c-header") 14set(__pch_header_OBJCXX "objective-c++-header") 15 16macro(__windows_compiler_clang_gnu lang) 17 set(CMAKE_LIBRARY_PATH_FLAG "-L") 18 set(CMAKE_LINK_LIBRARY_FLAG "-l") 19 20 set(CMAKE_IMPORT_LIBRARY_PREFIX "") 21 set(CMAKE_SHARED_LIBRARY_PREFIX "") 22 set(CMAKE_SHARED_MODULE_PREFIX "") 23 set(CMAKE_STATIC_LIBRARY_PREFIX "") 24 set(CMAKE_EXECUTABLE_SUFFIX ".exe") 25 set(CMAKE_IMPORT_LIBRARY_SUFFIX ".lib") 26 set(CMAKE_SHARED_LIBRARY_SUFFIX ".dll") 27 set(CMAKE_SHARED_MODULE_SUFFIX ".dll") 28 set(CMAKE_STATIC_LIBRARY_SUFFIX ".lib") 29 if(NOT "${lang}" STREQUAL "ASM") 30 set(CMAKE_DEPFILE_FLAGS_${lang} "-MD -MT <DEP_TARGET> -MF <DEP_FILE>") 31 endif() 32 33 set(CMAKE_FIND_LIBRARY_PREFIXES "lib" "") 34 set(CMAKE_FIND_LIBRARY_SUFFIXES ".dll.a" ".a" ".lib") 35 set(CMAKE_SUPPORT_WINDOWS_EXPORT_ALL_SYMBOLS 1) 36 set (CMAKE_LINK_DEF_FILE_FLAG "-Xlinker /DEF:") 37 38 set(CMAKE_${lang}_LINKER_WRAPPER_FLAG "-Xlinker" " ") 39 set(CMAKE_${lang}_LINKER_WRAPPER_FLAG_SEP) 40 41 set(CMAKE_${lang}_LINKER_MANIFEST_FLAG " -Xlinker /MANIFESTINPUT:") 42 43 if("${CMAKE_${lang}_SIMULATE_VERSION}" MATCHES "^([0-9]+)\\.([0-9]+)") 44 math(EXPR MSVC_VERSION "${CMAKE_MATCH_1}*100 + ${CMAKE_MATCH_2}") 45 endif() 46 47 # No -fPIC on Windows 48 set(CMAKE_${lang}_COMPILE_OPTIONS_PIC "") 49 set(CMAKE_${lang}_COMPILE_OPTIONS_PIE "") 50 set(_CMAKE_${lang}_PIE_MAY_BE_SUPPORTED_BY_LINKER NO) 51 set(CMAKE_${lang}_LINK_OPTIONS_PIE "") 52 set(CMAKE_${lang}_LINK_OPTIONS_NO_PIE "") 53 set(CMAKE_SHARED_LIBRARY_${lang}_FLAGS "") 54 55 set(CMAKE_${lang}_USE_RESPONSE_FILE_FOR_OBJECTS 1) 56 set(CMAKE_${lang}_USE_RESPONSE_FILE_FOR_LIBRARIES 1) 57 set(CMAKE_${lang}_USE_RESPONSE_FILE_FOR_INCLUDES 1) 58 59 set(CMAKE_${lang}_COMPILE_OPTIONS_IPO "-flto") 60 set(_CMAKE_${lang}_IPO_SUPPORTED_BY_CMAKE YES) 61 set(_CMAKE_${lang}_IPO_MAY_BE_SUPPORTED_BY_COMPILER YES) 62 set(CMAKE_${lang}_ARCHIVE_CREATE_IPO "<CMAKE_AR> qc <TARGET> <LINK_FLAGS> <OBJECTS>") 63 set(CMAKE_${lang}_ARCHIVE_APPEND_IPO "<CMAKE_AR> q <TARGET> <LINK_FLAGS> <OBJECTS>") 64 set(CMAKE_${lang}_ARCHIVE_FINISH_IPO "<CMAKE_RANLIB> <TARGET>") 65 66 # Create archiving rules to support large object file lists for static libraries. 67 set(CMAKE_${lang}_ARCHIVE_CREATE "<CMAKE_AR> qc <TARGET> <LINK_FLAGS> <OBJECTS>") 68 set(CMAKE_${lang}_ARCHIVE_APPEND "<CMAKE_AR> q <TARGET> <LINK_FLAGS> <OBJECTS>") 69 set(CMAKE_${lang}_ARCHIVE_FINISH "<CMAKE_RANLIB> <TARGET>") 70 set(CMAKE_${lang}_CREATE_SHARED_LIBRARY 71 "<CMAKE_${lang}_COMPILER> -fuse-ld=lld-link -nostartfiles -nostdlib <CMAKE_SHARED_LIBRARY_${lang}_FLAGS> <LANGUAGE_COMPILE_FLAGS> <LINK_FLAGS> <CMAKE_SHARED_LIBRARY_CREATE_${lang}_FLAGS> -o <TARGET> ${CMAKE_GNULD_IMAGE_VERSION} -Xlinker /MANIFEST:EMBED -Xlinker /implib:<TARGET_IMPLIB> -Xlinker /pdb:<TARGET_PDB> -Xlinker /version:<TARGET_VERSION_MAJOR>.<TARGET_VERSION_MINOR> <OBJECTS> <LINK_LIBRARIES> <MANIFESTS>") 72 set(CMAKE_${lang}_CREATE_SHARED_MODULE ${CMAKE_${lang}_CREATE_SHARED_LIBRARY}) 73 set(CMAKE_${lang}_LINK_EXECUTABLE 74 "<CMAKE_${lang}_COMPILER> -fuse-ld=lld-link -nostartfiles -nostdlib <FLAGS> <CMAKE_${lang}_LINK_FLAGS> <LINK_FLAGS> <OBJECTS> -o <TARGET> -Xlinker /MANIFEST:EMBED -Xlinker /implib:<TARGET_IMPLIB> -Xlinker /pdb:<TARGET_PDB> -Xlinker /version:<TARGET_VERSION_MAJOR>.<TARGET_VERSION_MINOR> ${CMAKE_GNULD_IMAGE_VERSION} <LINK_LIBRARIES> <MANIFESTS>") 75 76 set(CMAKE_${lang}_CREATE_WIN32_EXE "-Xlinker /subsystem:windows") 77 set(CMAKE_${lang}_CREATE_CONSOLE_EXE "-Xlinker /subsystem:console") 78 79 if(NOT "${lang}" STREQUAL "ASM") 80 set(CMAKE_${lang}_COMPILE_OPTIONS_MSVC_RUNTIME_LIBRARY_MultiThreaded -Xclang -flto-visibility-public-std -D_MT -Xclang --dependent-lib=libcmt) 81 set(CMAKE_${lang}_COMPILE_OPTIONS_MSVC_RUNTIME_LIBRARY_MultiThreadedDLL -D_DLL -D_MT -Xclang --dependent-lib=msvcrt) 82 set(CMAKE_${lang}_COMPILE_OPTIONS_MSVC_RUNTIME_LIBRARY_MultiThreadedDebug -D_DEBUG -Xclang -flto-visibility-public-std -D_MT -Xclang --dependent-lib=libcmtd) 83 set(CMAKE_${lang}_COMPILE_OPTIONS_MSVC_RUNTIME_LIBRARY_MultiThreadedDebugDLL -D_DEBUG -D_DLL -D_MT -Xclang --dependent-lib=msvcrtd) 84 85 if(CMAKE_MSVC_RUNTIME_LIBRARY_DEFAULT) 86 set(__ADDED_FLAGS "") 87 set(__ADDED_FLAGS_DEBUG "") 88 else() 89 set(__ADDED_FLAGS_DEBUG "-D_DEBUG -D_DLL -D_MT -Xclang --dependent-lib=msvcrtd") 90 set(__ADDED_FLAGS "-D_DLL -D_MT -Xclang --dependent-lib=msvcrt") 91 endif() 92 93 string(APPEND CMAKE_${lang}_FLAGS_DEBUG_INIT " -g -Xclang -gcodeview -O0 ${__ADDED_FLAGS_DEBUG}") 94 string(APPEND CMAKE_${lang}_FLAGS_MINSIZEREL_INIT " -Os -DNDEBUG ${__ADDED_FLAGS}") 95 string(APPEND CMAKE_${lang}_FLAGS_RELEASE_INIT " -O3 -DNDEBUG ${__ADDED_FLAGS}") 96 string(APPEND CMAKE_${lang}_FLAGS_RELWITHDEBINFO_INIT " -O2 -g -DNDEBUG -Xclang -gcodeview ${__ADDED_FLAGS}") 97 endif() 98 set(CMAKE_INCLUDE_SYSTEM_FLAG_${lang} "-isystem ") 99 100 set(CMAKE_PCH_EXTENSION .pch) 101 set(CMAKE_PCH_PROLOGUE "#pragma clang system_header") 102 set(CMAKE_${lang}_COMPILE_OPTIONS_USE_PCH -Xclang -include-pch -Xclang <PCH_FILE> -Xclang -include -Xclang <PCH_HEADER>) 103 set(CMAKE_${lang}_COMPILE_OPTIONS_CREATE_PCH -Xclang -emit-pch -Xclang -include -Xclang <PCH_HEADER> -x ${__pch_header_${lang}}) 104 105 unset(__ADDED_FLAGS) 106 unset(__ADDED_FLAGS_DEBUG) 107 string(TOLOWER "${CMAKE_BUILD_TYPE}" BUILD_TYPE_LOWER) 108 set(CMAKE_${lang}_STANDARD_LIBRARIES_INIT "-lkernel32 -luser32 -lgdi32 -lwinspool -lshell32 -lole32 -loleaut32 -luuid -lcomdlg32 -ladvapi32 -loldnames") 109 110 enable_language(RC) 111endmacro() 112 113macro(__enable_llvm_rc_preprocessing clang_option_prefix extra_pp_flags) 114 # Feed the preprocessed rc file to llvm-rc 115 if(CMAKE_RC_COMPILER_INIT MATCHES "llvm-rc" OR CMAKE_RC_COMPILER MATCHES "llvm-rc") 116 if(DEFINED CMAKE_C_COMPILER_ID) 117 set(CMAKE_RC_PREPROCESSOR CMAKE_C_COMPILER) 118 elseif(DEFINED CMAKE_CXX_COMPILER_ID) 119 set(CMAKE_RC_PREPROCESSOR CMAKE_CXX_COMPILER) 120 endif() 121 if(DEFINED CMAKE_RC_PREPROCESSOR) 122 set(CMAKE_DEPFILE_FLAGS_RC "${clang_option_prefix}-MD ${clang_option_prefix}-MF ${clang_option_prefix}<DEP_FILE>") 123 # The <FLAGS> are passed to the preprocess and the resource compiler to pick 124 # up the eventual -D / -C options passed through the CMAKE_RC_FLAGS. 125 set(CMAKE_RC_COMPILE_OBJECT "<CMAKE_COMMAND> -E cmake_llvm_rc <SOURCE> <OBJECT>.pp <${CMAKE_RC_PREPROCESSOR}> <DEFINES> -DRC_INVOKED <INCLUDES> <FLAGS> ${extra_pp_flags} -E -- <SOURCE> ++ <CMAKE_RC_COMPILER> <DEFINES> -I <SOURCE_DIR> <INCLUDES> <FLAGS> /fo <OBJECT> <OBJECT>.pp") 126 if(CMAKE_GENERATOR MATCHES "Ninja") 127 set(CMAKE_NINJA_CMCLDEPS_RC 0) 128 set(CMAKE_NINJA_DEP_TYPE_RC gcc) 129 endif() 130 unset(CMAKE_RC_PREPROCESSOR) 131 endif() 132 endif() 133endmacro() 134 135 136if("x${CMAKE_C_SIMULATE_ID}" STREQUAL "xMSVC" 137 OR "x${CMAKE_CXX_SIMULATE_ID}" STREQUAL "xMSVC") 138 139 if ( DEFINED CMAKE_C_COMPILER_ID AND DEFINED CMAKE_CXX_COMPILER_ID 140 AND NOT "x${CMAKE_C_COMPILER_ID}" STREQUAL "x${CMAKE_CXX_COMPILER_ID}") 141 message(FATAL_ERROR "The current configuration mixes Clang and MSVC or " 142 "some other CL compatible compiler tool. This is not supported. " 143 "Use either clang or MSVC as both C and C++ compilers.") 144 endif() 145 146 if ( DEFINED CMAKE_C_COMPILER_FRONTEND_VARIANT AND DEFINED CMAKE_CXX_COMPILER_FRONTEND_VARIANT 147 AND NOT "x${CMAKE_C_COMPILER_FRONTEND_VARIANT}" STREQUAL "x${CMAKE_CXX_COMPILER_FRONTEND_VARIANT}") 148 message(FATAL_ERROR "The current configuration uses the Clang compiler " 149 "tool with mixed frontend variants, both the GNU and in MSVC CL " 150 "like variants. This is not supported. Use either clang/clang++ " 151 "or clang-cl as both C and C++ compilers.") 152 endif() 153 154 if(NOT CMAKE_RC_COMPILER_INIT) 155 # Check if rc is already in the path 156 # This may happen in cases where the user is already in a visual studio environment when CMake is invoked 157 find_program(__RC_COMPILER_PATH NAMES rc) 158 159 # Default to rc if it's available, otherwise fall back to llvm-rc 160 if(__RC_COMPILER_PATH) 161 set(CMAKE_RC_COMPILER_INIT rc) 162 else() 163 find_program(__RC_COMPILER_PATH NAMES llvm-rc) 164 if(__RC_COMPILER_PATH) 165 set(CMAKE_RC_COMPILER_INIT llvm-rc) 166 endif() 167 endif() 168 169 unset(__RC_COMPILER_PATH CACHE) 170 endif() 171 172 if ( "x${CMAKE_CXX_COMPILER_FRONTEND_VARIANT}" STREQUAL "xMSVC" OR "x${CMAKE_C_COMPILER_FRONTEND_VARIANT}" STREQUAL "xMSVC" ) 173 include(Platform/Windows-MSVC) 174 # Set the clang option forwarding prefix for clang-cl usage in the llvm-rc processing stage 175 __enable_llvm_rc_preprocessing("-clang:" "") 176 macro(__windows_compiler_clang_base lang) 177 set(_COMPILE_${lang} "${_COMPILE_${lang}_MSVC}") 178 __windows_compiler_msvc(${lang}) 179 set(CMAKE_INCLUDE_SYSTEM_FLAG_${lang} "-imsvc ") 180 endmacro() 181 else() 182 cmake_policy(GET CMP0091 __WINDOWS_CLANG_CMP0091) 183 if(__WINDOWS_CLANG_CMP0091 STREQUAL "NEW") 184 set(CMAKE_MSVC_RUNTIME_LIBRARY_DEFAULT "MultiThreaded$<$<CONFIG:Debug>:Debug>DLL") 185 else() 186 set(CMAKE_MSVC_RUNTIME_LIBRARY_DEFAULT "") 187 endif() 188 unset(__WINDOWS_CLANG_CMP0091) 189 190 set(CMAKE_BUILD_TYPE_INIT Debug) 191 192 __enable_llvm_rc_preprocessing("" "-x c") 193 macro(__windows_compiler_clang_base lang) 194 __windows_compiler_clang_gnu(${lang}) 195 endmacro() 196 endif() 197 198else() 199 include(Platform/Windows-GNU) 200 __enable_llvm_rc_preprocessing("" "-x c") 201 macro(__windows_compiler_clang_base lang) 202 __windows_compiler_gnu(${lang}) 203 endmacro() 204endif() 205 206macro(__windows_compiler_clang lang) 207 if(CMAKE_${lang}_COMPILER_VERSION VERSION_LESS 3.4.0) 208 set(CMAKE_${lang}_COMPILE_OPTIONS_TARGET "-target ") 209 else() 210 set(CMAKE_${lang}_COMPILE_OPTIONS_TARGET "--target=") 211 endif() 212 __windows_compiler_clang_base(${lang}) 213endmacro() 214