1 2#============================================================================= 3# CMake build system files for detecting Clang and LLVM 4# 5# Copyright (c) 2014-2020 pocl developers 6# 7# Permission is hereby granted, free of charge, to any person obtaining a copy 8# of this software and associated documentation files (the "Software"), to deal 9# in the Software without restriction, including without limitation the rights 10# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 11# copies of the Software, and to permit persons to whom the Software is 12# furnished to do so, subject to the following conditions: 13# 14# The above copyright notice and this permission notice shall be included in 15# all copies or substantial portions of the Software. 16# 17# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 18# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 19# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 20# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 21# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 22# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 23# THE SOFTWARE. 24# 25#============================================================================= 26 27if(DEFINED WITH_LLVM_CONFIG AND WITH_LLVM_CONFIG) 28 # search for preferred version 29 if(IS_ABSOLUTE "${WITH_LLVM_CONFIG}") 30 if(EXISTS "${WITH_LLVM_CONFIG}") 31 set(LLVM_CONFIG "${WITH_LLVM_CONFIG}") 32 endif() 33 else() 34 find_program(LLVM_CONFIG NAMES "${WITH_LLVM_CONFIG}") 35 endif() 36else() 37 # search for any version 38 find_program(LLVM_CONFIG 39 NAMES 40 "llvmtce-config" 41 "llvm-config" 42 "llvm-config-mp-13.0" "llvm-config-13" "llvm-config130" 43 "llvm-config-mp-12.0" "llvm-config-12" "llvm-config120" 44 "llvm-config-mp-11.0" "llvm-config-11" "llvm-config110" 45 "llvm-config-mp-10.0" "llvm-config-10" "llvm-config100" 46 "llvm-config-mp-9.0" "llvm-config-9" "llvm-config90" 47 "llvm-config-mp-8.0" "llvm-config-8" "llvm-config80" 48 "llvm-config-mp-7.0" "llvm-config-7" "llvm-config70" 49 "llvm-config-mp-6.0" "llvm-config-6.0" "llvm-config60" 50 DOC "llvm-config executable") 51endif() 52 53set(WITH_LLVM_CONFIG "${WITH_LLVM_CONFIG}" CACHE PATH "Path to preferred llvm-config") 54 55if(NOT LLVM_CONFIG) 56 message(FATAL_ERROR "llvm-config not found !") 57else() 58 file(TO_CMAKE_PATH "${LLVM_CONFIG}" LLVM_CONFIG) 59 message(STATUS "Using llvm-config: ${LLVM_CONFIG}") 60 if(LLVM_CONFIG MATCHES "llvmtce-config${CMAKE_EXECUTABLE_SUFFIX}$") 61 set(LLVM_BINARY_SUFFIX "") 62 elseif(LLVM_CONFIG MATCHES "llvm-config${CMAKE_EXECUTABLE_SUFFIX}$") 63 set(LLVM_BINARY_SUFFIX "") 64 elseif(LLVM_CONFIG MATCHES "llvm-config(.*)${CMAKE_EXECUTABLE_SUFFIX}$") 65 set(LLVM_BINARY_SUFFIX "${CMAKE_MATCH_1}") 66 else() 67 message(WARNING "Cannot determine llvm binary suffix from ${LLVM_CONFIG}") 68 endif() 69 message(STATUS "LLVM binaries suffix : ${LLVM_BINARY_SUFFIX}") 70endif() 71 72get_filename_component(LLVM_CONFIG_LOCATION "${LLVM_CONFIG}" DIRECTORY) 73 74########################################################################## 75 76# A macro to run llvm config 77macro(run_llvm_config VARIABLE_NAME) 78 execute_process( 79 COMMAND "${LLVM_CONFIG}" ${ARGN} 80 OUTPUT_VARIABLE LLVM_CONFIG_VALUE 81 RESULT_VARIABLE LLVM_CONFIG_RETVAL 82 OUTPUT_STRIP_TRAILING_WHITESPACE 83 ) 84 if(LLVM_CONFIG_RETVAL) 85 message(SEND_ERROR "Error running llvm-config with arguments: ${ARGN}") 86 else() 87 set(${VARIABLE_NAME} ${LLVM_CONFIG_VALUE} CACHE STRING "llvm-config's ${VARIABLE_NAME} value") 88 message(STATUS "llvm-config's ${VARIABLE_NAME} is: ${${VARIABLE_NAME}}") 89 endif() 90endmacro(run_llvm_config) 91 92run_llvm_config(LLVM_PREFIX --prefix) 93# on windows, llvm-config returs "C:\llvm_prefix/bin" mixed style paths, 94# and cmake doesn't like the "\" - thinks its an escape char.. 95file(TO_CMAKE_PATH "${LLVM_PREFIX}" LLVM_PREFIX_CMAKE) 96 97set(LLVM_PREFIX_BIN "${LLVM_PREFIX_CMAKE}/bin") 98run_llvm_config(LLVM_VERSION_FULL --version) 99# sigh, sanitize version... `llvm --version` on debian might return 3.4.1 but llvm command names are still <command>-3.4 100string(REGEX REPLACE "([0-9]+)\\.([0-9]+).*" "\\1.\\2" LLVM_VERSION "${LLVM_VERSION_FULL}") 101message(STATUS "LLVM_VERSION: ${LLVM_VERSION}") 102 103string(REPLACE "." ";" LLVM_VERSION_PARSED "${LLVM_VERSION}") 104list(GET LLVM_VERSION_PARSED 0 LLVM_VERSION_MAJOR) 105list(GET LLVM_VERSION_PARSED 1 LLVM_VERSION_MINOR) 106 107run_llvm_config(LLVM_CFLAGS --cflags) 108string(REPLACE "${LLVM_PREFIX}" "${LLVM_PREFIX_CMAKE}" LLVM_CFLAGS "${LLVM_CFLAGS}") 109run_llvm_config(LLVM_CXXFLAGS --cxxflags) 110string(REPLACE "${LLVM_PREFIX}" "${LLVM_PREFIX_CMAKE}" LLVM_CXXFLAGS "${LLVM_CXXFLAGS}") 111run_llvm_config(LLVM_CPPFLAGS --cppflags) 112string(REPLACE "${LLVM_PREFIX}" "${LLVM_PREFIX_CMAKE}" LLVM_CPPFLAGS "${LLVM_CPPFLAGS}") 113run_llvm_config(LLVM_LDFLAGS --ldflags) 114string(REPLACE "${LLVM_PREFIX}" "${LLVM_PREFIX_CMAKE}" LLVM_LDFLAGS "${LLVM_LDFLAGS}") 115run_llvm_config(LLVM_BINDIR --bindir) 116string(REPLACE "${LLVM_PREFIX}" "${LLVM_PREFIX_CMAKE}" LLVM_BINDIR "${LLVM_BINDIR}") 117run_llvm_config(LLVM_LIBDIR --libdir) 118string(REPLACE "${LLVM_PREFIX}" "${LLVM_PREFIX_CMAKE}" LLVM_LIBDIR "${LLVM_LIBDIR}") 119run_llvm_config(LLVM_INCLUDEDIR --includedir) 120string(REPLACE "${LLVM_PREFIX}" "${LLVM_PREFIX_CMAKE}" LLVM_INCLUDEDIR "${LLVM_INCLUDEDIR}") 121 122run_llvm_config(LLVM_SRC_ROOT --src-root) 123run_llvm_config(LLVM_OBJ_ROOT --obj-root) 124string(REPLACE "${LLVM_PREFIX}" "${LLVM_PREFIX_CMAKE}" LLVM_OBJ_ROOT "${LLVM_OBJ_ROOT}") 125run_llvm_config(LLVM_ALL_TARGETS --targets-built) 126run_llvm_config(LLVM_HOST_TARGET --host-target) 127run_llvm_config(LLVM_BUILD_MODE --build-mode) 128run_llvm_config(LLVM_ASSERTS_BUILD --assertion-mode) 129run_llvm_config(LLVM_SYSLIBS --system-libs) 130string(STRIP "${LLVM_SYSLIBS}" LLVM_SYSLIBS) 131 132if(MSVC) 133 string(REPLACE "-L${LLVM_LIBDIR}" "" LLVM_LDFLAGS "${LLVM_LDFLAGS}") 134 string(STRIP "${LLVM_LDFLAGS}" LLVM_LDFLAGS) 135endif() 136 137if(LLVM_BUILD_MODE MATCHES "Debug") 138 set(LLVM_BUILD_MODE_DEBUG 1) 139else() 140 set(LLVM_BUILD_MODE_DEBUG 0) 141endif() 142 143# A few work-arounds for llvm-config issues 144 145# - pocl doesn't compile with '-pedantic' 146#LLVM_CXX_FLAGS=$($LLVM_CONFIG --cxxflags | sed -e 's/ -pedantic / /g') 147string(REPLACE " -pedantic" "" LLVM_CXXFLAGS "${LLVM_CXXFLAGS}") 148 149#llvm-config clutters CXXFLAGS with a lot of -W<whatever> flags. 150#(They are not needed - we want to use -Wall anyways) 151#This is a problem if LLVM was built with a different compiler than we use here, 152#and our compiler chokes on unrecognized command-line options. 153string(REGEX REPLACE "-W[^ ]*" "" LLVM_CXXFLAGS "${LLVM_CXXFLAGS}") 154 155# Ubuntu's llvm reports "arm-unknown-linux-gnueabihf" triple, then if one tries 156# `clang --target=arm-unknown-linux-gnueabihf ...` it will produce armv6 code, 157# even if one's running armv7; 158# Here we replace the "arm" string with whatever's in CMAKE_HOST_SYSTEM_PROCESSOR 159# which should be "armv6l" on rasp pi, or "armv7l" on my cubieboard, hopefully its 160# more reasonable and reliable than llvm's own host flags 161if(NOT CMAKE_CROSSCOMPILING) 162 string(REPLACE "arm-" "${CMAKE_HOST_SYSTEM_PROCESSOR}-" LLVM_HOST_TARGET "${LLVM_HOST_TARGET}") 163endif() 164 165# In windows llvm-config reports --target=x86_64-pc-windows-msvc 166# however this causes clang to use MicrosoftCXXMangler, which does not 167# yet support mangling for extended vector types (with llvm 3.5) 168# so for now hardcode LLVM_HOST_TARGET to be x86_64-pc with windows 169if(WIN32) 170 set(LLVM_HOST_TARGET "x86_64-pc") 171endif(WIN32) 172 173# required for sources.. 174if(LLVM_VERSION MATCHES "^6[.]0") 175 set(LLVM_MAJOR 6) 176 set(LLVM_6_0 1) 177 set(LLVM_OLDER_THAN_7_0 1) 178 set(LLVM_OLDER_THAN_8_0 1) 179 set(LLVM_OLDER_THAN_9_0 1) 180 set(LLVM_OLDER_THAN_10_0 1) 181elseif(LLVM_VERSION MATCHES "^7[.]") 182 set(LLVM_MAJOR 7) 183 set(LLVM_7_0 1) 184 set(LLVM_OLDER_THAN_8_0 1) 185 set(LLVM_OLDER_THAN_9_0 1) 186 set(LLVM_OLDER_THAN_10_0 1) 187elseif(LLVM_VERSION MATCHES "^8[.]") 188 set(LLVM_MAJOR 8) 189 set(LLVM_8_0 1) 190 set(LLVM_OLDER_THAN_9_0 1) 191 set(LLVM_OLDER_THAN_10_0 1) 192elseif(LLVM_VERSION MATCHES "^9[.]") 193 set(LLVM_MAJOR 9) 194 set(LLVM_9_0 1) 195 set(LLVM_OLDER_THAN_10_0 1) 196elseif(LLVM_VERSION MATCHES "^10[.]") 197 set(LLVM_MAJOR 10) 198 set(LLVM_10_0 1) 199elseif(LLVM_VERSION MATCHES "^11[.]") 200 set(LLVM_MAJOR 11) 201 set(LLVM_11_0 1) 202elseif(LLVM_VERSION MATCHES "^12[.]") 203 set(LLVM_MAJOR 12) 204 set(LLVM_12_0 1) 205elseif(LLVM_VERSION MATCHES "^13[.]") 206 set(LLVM_MAJOR 13) 207 set(LLVM_13_0 1) 208else() 209 message(FATAL_ERROR "LLVM version between 6.0 and 13.0 required, found: ${LLVM_VERSION}") 210endif() 211 212############################################################# 213 214run_llvm_config(LLVM_HAS_RTTI --has-rtti) 215 216if(DEFINED SINGLE_LLVM_LIB) 217 message(AUTHOR_WARNING "SINGLE_LLVM_LIB option was removed; pocl now uses only llvm-config to get the libraries. Use STATIC_LLVM=ON/OFF to affect which libraries pocl requests from llvm-config") 218endif() 219 220if(STATIC_LLVM) 221 set(LLVM_LIB_MODE --link-static) 222else() 223 set(LLVM_LIB_MODE --link-shared) 224endif() 225 226unset(LLVM_LIBS) 227run_llvm_config(LLVM_LIBS --libs ${LLVM_LIB_MODE}) 228# Convert LLVM_LIBS from string -> list format to make handling them easier 229separate_arguments(LLVM_LIBS) 230 231# With Visual Studio llvm-config gives invalid list of static libs (libXXXX.a instead of XXXX.lib) 232# we extract the pure names (LLVMLTO, LLVMMipsDesc etc) and let find_library do its job 233foreach(LIBFLAG ${LLVM_LIBS}) 234 STRING(REGEX REPLACE "^-l(.*)$" "\\1" LIB_NAME ${LIBFLAG}) 235 list(APPEND LLVM_LIBNAMES "${LIB_NAME}") 236endforeach() 237 238foreach(LIBNAME ${LLVM_LIBNAMES}) 239 find_library(L_LIBFILE_${LIBNAME} NAMES "${LIBNAME}" HINTS "${LLVM_LIBDIR}") 240 list(APPEND LLVM_LIBFILES "${L_LIBFILE_${LIBNAME}}") 241endforeach() 242 243set(POCL_LLVM_LIBS ${LLVM_LIBFILES}) 244 245#################################################################### 246 247run_llvm_config(LLVM_SYSLIBS --system-libs ${LLVM_LIB_MODE}) 248string(STRIP "${LLVM_SYSLIBS}" LLVM_SYSLIBS) 249 250#################################################################### 251 252# llvm-config does not include clang libs 253if((9 LESS LLVM_MAJOR) AND (NOT STATIC_LLVM)) 254 # For Clang 10+, link against a single shared library instead of multiple component shared 255 # libraries. 256 if("${LLVM_LIBNAMES}" MATCHES "LLVMTCE") 257 set(CLANG_LIBNAMES clangTCE-cpp) 258 else() 259 set(CLANG_LIBNAMES clang-cpp) 260 endif() 261else() 262 set(CLANG_LIBNAMES clangCodeGen clangFrontendTool clangFrontend clangDriver clangSerialization 263 clangParse clangSema clangRewrite clangRewriteFrontend 264 clangStaticAnalyzerFrontend clangStaticAnalyzerCheckers 265 clangStaticAnalyzerCore clangAnalysis clangEdit clangAST clangASTMatchers clangLex clangBasic) 266endif() 267 268foreach(LIBNAME ${CLANG_LIBNAMES}) 269 find_library(C_LIBFILE_${LIBNAME} NAMES "${LIBNAME}" HINTS "${LLVM_LIBDIR}") 270 list(APPEND CLANG_LIBFILES "${C_LIBFILE_${LIBNAME}}") 271 if(UNIX AND (NOT APPLE)) 272 set(LLVM_LDFLAGS "${LLVM_LDFLAGS} -Wl,--exclude-libs,lib${LIBNAME}") 273 endif() 274endforeach() 275 276#################################################################### 277 278macro(find_program_or_die OUTPUT_VAR PROG_NAME DOCSTRING) 279 find_program(${OUTPUT_VAR} 280 NAMES "${PROG_NAME}${LLVM_BINARY_SUFFIX}${CMAKE_EXECUTABLE_SUFFIX}" "${PROG_NAME}${CMAKE_EXECUTABLE_SUFFIX}" 281 HINTS "${LLVM_BINDIR}" "${LLVM_CONFIG_LOCATION}" "${LLVM_PREFIX}" "${LLVM_PREFIX_BIN}" 282 DOC "${DOCSTRING}" 283 NO_CMAKE_PATH 284 NO_CMAKE_ENVIRONMENT_PATH 285 ) 286 if(${OUTPUT_VAR}) 287 message(STATUS "Found ${PROG_NAME}: ${${OUTPUT_VAR}}") 288 else() 289 message(FATAL_ERROR "${PROG_NAME} executable not found!") 290 endif() 291endmacro() 292 293find_program_or_die( CLANG "clang" "clang binary") 294execute_process(COMMAND "${CLANG}" "--version" OUTPUT_VARIABLE LLVM_CLANG_VERSION RESULT_VARIABLE CLANG_RES) 295# TODO this should be optional 296find_program_or_die( CLANGXX "clang++" "clang++ binary") 297execute_process(COMMAND "${CLANGXX}" "--version" OUTPUT_VARIABLE LLVM_CLANGXX_VERSION RESULT_VARIABLE CLANGXX_RES) 298if(CLANGXX_RES OR CLANG_RES) 299 message(FATAL_ERROR "Failed running clang/clang++ --version") 300endif() 301 302find_program_or_die(LLVM_OPT "opt" "LLVM optimizer") 303find_program_or_die(LLVM_LLC "llc" "LLVM static compiler") 304find_program_or_die(LLVM_AS "llvm-as" "LLVM assembler") 305find_program_or_die(LLVM_LINK "llvm-link" "LLVM IR linker") 306find_program_or_die(LLVM_LLI "lli" "LLVM interpreter") 307 308if(NOT DEFINED LLVM_SPIRV) 309 find_program(LLVM_SPIRV NAMES "llvm-spirv${LLVM_BINARY_SUFFIX}${CMAKE_EXECUTABLE_SUFFIX}" "llvm-spirv${CMAKE_EXECUTABLE_SUFFIX}" HINTS "${LLVM_BINDIR}" "${LLVM_CONFIG_LOCATION}" "${LLVM_PREFIX}" "${LLVM_PREFIX_BIN}") 310 if(LLVM_SPIRV) 311 message(STATUS "Found llvm-spirv: ${LLVM_SPIRV}") 312 endif() 313endif() 314 315#################################################################### 316 317# try compile with any compiler (supplied as argument) 318macro(custom_try_compile_any SILENT COMPILER SUFFIX SOURCE RES_VAR) 319 string(RANDOM RNDNAME) 320 set(RANDOM_FILENAME "${CMAKE_BINARY_DIR}/compile_test_${RNDNAME}.${SUFFIX}") 321 file(WRITE "${RANDOM_FILENAME}" "${SOURCE}") 322 323 math(EXPR LSIZE "${ARGC} - 4") 324 325 execute_process(COMMAND "${COMPILER}" ${ARGN} "${RANDOM_FILENAME}" RESULT_VARIABLE ${RES_VAR} OUTPUT_VARIABLE OV ERROR_VARIABLE EV) 326 if(${${RES_VAR}} AND (NOT ${SILENT})) 327 message(STATUS " ########## The command: ") 328 string(REPLACE ";" " " ARGN_STR "${ARGN}") 329 message(STATUS "${COMPILER} ${ARGN_STR} ${RANDOM_FILENAME}") 330 message(STATUS " ########## Exited with nonzero status: ${${RES_VAR}}") 331 if(OV) 332 message(STATUS "STDOUT: ${OV}") 333 endif() 334 if(EV) 335 message(STATUS "STDERR: ${EV}") 336 endif() 337 endif() 338 file(REMOVE "${RANDOM_FILENAME}") 339 340endmacro() 341 342# convenience c/c++ source wrapper 343macro(custom_try_compile_c_cxx COMPILER SUFFIX SOURCE1 SOURCE2 RES_VAR) 344 set(SOURCE_PROG " 345 ${SOURCE1} 346 347 int main(int argc, char** argv) { 348 349 ${SOURCE2} 350 351 }") 352 custom_try_compile_any(FALSE "${COMPILER}" ${SUFFIX} "${SOURCE_PROG}" ${RES_VAR} ${ARGN}) 353endmacro() 354 355# convenience c/c++ source wrapper 356macro(custom_try_compile_c_cxx_silent COMPILER SUFFIX SOURCE1 SOURCE2 RES_VAR) 357 set(SOURCE_PROG " 358 ${SOURCE1} 359 360 int main(int argc, char** argv) { 361 362 ${SOURCE2} 363 364 }") 365 custom_try_compile_any(TRUE "${COMPILER}" ${SUFFIX} "${SOURCE_PROG}" ${RES_VAR} ${ARGN}) 366endmacro() 367 368# clang++ try-compile macro 369macro(custom_try_compile_clangxx SOURCE1 SOURCE2 RES_VAR) 370 custom_try_compile_c_cxx("${CLANGXX}" "cc" "${SOURCE1}" "${SOURCE2}" ${RES_VAR} "-c" ${ARGN}) 371endmacro() 372 373# clang++ try-compile macro 374macro(custom_try_compile_clang SOURCE1 SOURCE2 RES_VAR) 375 custom_try_compile_c_cxx("${CLANG}" "c" "${SOURCE1}" "${SOURCE2}" ${RES_VAR} "-c" ${ARGN}) 376endmacro() 377 378# clang++ try-compile macro 379macro(custom_try_compile_clang_silent SOURCE1 SOURCE2 RES_VAR) 380 custom_try_compile_c_cxx_silent("${CLANG}" "c" "${SOURCE1}" "${SOURCE2}" ${RES_VAR} "-c" ${ARGN}) 381endmacro() 382 383# clang++ try-link macro 384macro(custom_try_link_clang SOURCE1 SOURCE2 RES_VAR) 385 set(RANDOM_FILENAME "${CMAKE_BINARY_DIR}/compile_test_${RNDNAME}.${SUFFIX}") 386 custom_try_compile_c_cxx_silent("${CLANG}" "c" "${SOURCE1}" "${SOURCE2}" ${RES_VAR} "-o" "${RANDOM_FILENAME}" ${ARGN}) 387 file(REMOVE "${RANDOM_FILENAME}") 388endmacro() 389 390# clang try-compile-run macro, running via native executable 391macro(custom_try_run_exe SOURCE1 SOURCE2 OUTPUT_VAR RES_VAR) 392 set(OUTF "${CMAKE_BINARY_DIR}/try_run${CMAKE_EXECUTABLE_SUFFIX}") 393 if(EXISTS "${OUTF}") 394 file(REMOVE "${OUTF}") 395 endif() 396 custom_try_compile_c_cxx("${CLANG}" "c" "${SOURCE1}" "${SOURCE2}" RESV "-o" "${OUTF}" "-x" "c") 397 set(${OUTPUT_VAR} "") 398 set(${RES_VAR} "") 399 if(RESV OR (NOT EXISTS "${OUTF}")) 400 message(STATUS " ########## Compilation failed") 401 else() 402 execute_process(COMMAND "${OUTF}" RESULT_VARIABLE RESV OUTPUT_VARIABLE ${OUTPUT_VAR} ERROR_VARIABLE EV) 403 set(${RES_VAR} ${RESV}) 404 file(REMOVE "${OUTF}") 405 if(${RESV}) 406 message(STATUS " ########## Running ${OUTF}") 407 message(STATUS " ########## Exited with nonzero status: ${RESV}") 408 if(${${OUTPUT_VAR}}) 409 message(STATUS " ########## STDOUT: ${${OUTPUT_VAR}}") 410 endif() 411 if(EV) 412 message(STATUS " ########## STDERR: ${EV}") 413 endif() 414 endif() 415 endif() 416endmacro() 417 418# clang try-compile-run macro, run via lli, the llvm interpreter 419macro(custom_try_run_lli SILENT SOURCE1 SOURCE2 OUTPUT_VAR RES_VAR) 420# this uses "lli" - the interpreter, so we can run any -target 421# TODO variable for target !! 422 set(OUTF "${CMAKE_BINARY_DIR}/try_run.bc") 423 if(EXISTS "${OUTF}") 424 file(REMOVE "${OUTF}") 425 endif() 426 custom_try_compile_c_cxx("${CLANG}" "c" "${SOURCE1}" "${SOURCE2}" RESV "-o" "${OUTF}" "-x" "c" "-emit-llvm" "-c" ${ARGN}) 427 set(${OUTPUT_VAR} "") 428 set(${RES_VAR} "") 429 if(RESV OR (NOT EXISTS "${OUTF}")) 430 message(STATUS " ########## Compilation failed") 431 else() 432 execute_process(COMMAND "${LLVM_LLI}" "-force-interpreter" "${OUTF}" RESULT_VARIABLE RESV OUTPUT_VARIABLE ${OUTPUT_VAR} ERROR_VARIABLE EV) 433 set(${RES_VAR} ${RESV}) 434 file(REMOVE "${OUTF}") 435 if(${RESV} AND (NOT ${SILENT})) 436 message(STATUS " ########## The command ${LLVM_LLI} -force-interpreter ${OUTF}") 437 message(STATUS " ########## Exited with nonzero status: ${RESV}") 438 if(${${OUTPUT_VAR}}) 439 message(STATUS " ########## STDOUT: ${${OUTPUT_VAR}}") 440 endif() 441 if(EV) 442 message(STATUS " ########## STDERR: ${EV}") 443 endif() 444 endif() 445 endif() 446endmacro() 447 448#################################################################### 449#################################################################### 450 451# The option for specifying the target changed; try the modern syntax 452# first, and fall back to the old-style syntax if this failed 453 454if(NOT DEFINED CLANG_TARGET_OPTION AND ENABLE_HOST_CPU_DEVICES) 455 456 custom_try_compile_clangxx("" "return 0;" RES "--target=${LLVM_HOST_TARGET}") 457 if(NOT RES) 458 set(CLANG_TGT "--target=") 459 else() 460 #EXECUTE_PROCESS(COMMAND "${CLANG}" "-target ${LLVM_HOST_TARGET}" "-x" "c" "/dev/null" "-S" RESULT_VARIABLE RES) 461 custom_try_compile_clangxx("" "return 0;" RES "-target ${LLVM_HOST_TARGET}") 462 if(NOT RES) 463 set(CLANG_TGT "-target ") 464 else() 465 message(FATAL_ERROR "Cannot determine Clang option to specify the target") 466 endif() 467 endif() 468 469 set(CLANG_TARGET_OPTION ${CLANG_TGT} CACHE INTERNAL "Clang option used to specify the target" ) 470 471endif() 472 473#################################################################### 474#################################################################### 475 476if(NOT DEFINED CLANG_NEEDS_RTLIB) 477 478 set(RT128 OFF) 479 set(RT64 OFF) 480 set(NEEDS_RTLIB_FLAG OFF) 481 482 # on 32bit systems, we need 64bit emulation 483 if(CMAKE_SIZEOF_VOID_P EQUAL 4) 484 set(INC "#include <stdint.h>\n#include <stddef.h>") 485 set(SRC "int64_t a = argc; int64_t b = argc-1; int64_t c = a / b; return (int)c; ") 486 custom_try_link_clang("${INC}" "${SRC}" RES) 487 if(NOT RES) 488 message(STATUS "64bit division compiles without extra flags") 489 set(RT64 ON) 490 else() 491 custom_try_link_clang("${INC}" "${SRC}" RES "--rtlib=compiler-rt") 492 if(NOT RES) 493 message(STATUS "64bit division compiles WITH --rtlib=compiler-rt") 494 set(NEEDS_RTLIB_FLAG ON) 495 set(RT64 ON) 496 else() 497 message(WARNING "64bit division doesn't compile at all!") 498 endif() 499 endif() 500 501 else() 502 503 set(RT64 ON) 504 # on 64bit systems, we need 128bit integers for Errol 505 set(INC "extern __uint128_t __udivmodti4(__uint128_t a, __uint128_t b, __uint128_t* rem);") 506 set(SRC "__uint128_t low, mid, tmp1, pow19 = (__uint128_t)1000000000; mid = __udivmodti4(low, pow19, &tmp1); return 0;") 507 custom_try_link_clang("${INC}" "${SRC}" RES) 508 509 if(NOT RES) 510 message(STATUS "udivmodti4 compiles without extra flags") 511 set(RT128 ON) 512 else() 513 custom_try_link_clang("${INC}" "${SRC}" RES "--rtlib=compiler-rt") 514 if(NOT RES) 515 message(STATUS "udivmodti4 compiles WITH --rtlib=compiler-rt") 516 set(NEEDS_RTLIB_FLAG ON) 517 set(RT128 ON) 518 else() 519 message(WARNING "udivmodti4 doesn't compile at all!") 520 endif() 521 endif() 522 523 endif() 524 525 set(CLANG_HAS_64B_MATH ${RT64} CACHE INTERNAL "Clang's available with 64bit math") 526 set(CLANG_HAS_128B_MATH ${RT128} CACHE INTERNAL "Clang's available with 128bit math") 527 set(CLANG_NEEDS_RTLIB ${NEEDS_RTLIB_FLAG} CACHE INTERNAL "Clang needs extra --rtlib flag for compiler-rt math") 528 529endif() 530 531#################################################################### 532 533macro(CHECK_ALIGNOF TYPE TYPEDEF OUT_VAR) 534 535 if(NOT DEFINED "${OUT_VAR}") 536 537 custom_try_run_lli(TRUE " 538#ifndef offsetof 539#define offsetof(type, member) ((char *) &((type *) 0)->member - (char *) 0) 540#endif 541 542${TYPEDEF}" "typedef struct { char x; ${TYPE} y; } ac__type_alignof_; 543 int r = offsetof(ac__type_alignof_, y); 544 return r;" SIZEOF_STDOUT RESULT "${CLANG_TARGET_OPTION}${LLC_TRIPLE}") 545 546 #message(FATAL_ERROR "SIZEOF: ${SIZEOF_STDOUT} RES: ${RESULT}") 547 if(NOT ${RESULT}) 548 message(SEND_ERROR "Could not determine align of(${TYPE})") 549 endif() 550 551 set(${OUT_VAR} "${RESULT}" CACHE INTERNAL "Align of ${TYPE}") 552 553 endif() 554 555endmacro() 556 557#################################################################### 558# 559# clangxx works check 560# 561 562# TODO clang + vecmathlib doesn't work on Windows yet... 563if(CLANGXX AND (NOT WIN32) AND ENABLE_HOST_CPU_DEVICES) 564 565 message(STATUS "Checking if clang++ works (required by vecmathlib)") 566 567 set(CXX_WORKS 0) 568 set(CXX_STDLIB "") 569 570 if(NOT DEFINED CLANGXX_WORKS) 571 572 custom_try_compile_clangxx("namespace std { class type_info; } \n #include <iostream> \n #include <type_traits>" "std::cout << \"Hello clang++ world!\" << std::endl;" _STATUS_FAIL "-std=c++11") 573 574 if(NOT _STATUS_FAIL) 575 set(CXX_WORKS 1) 576 else() 577 custom_try_compile_clangxx("namespace std { class type_info; } \n #include <iostream> \n #include <type_traits>" "std::cout << \"Hello clang++ world!\" << std::endl;" _STATUS_FAIL "-stdlib=libstdc++" "-std=c++11") 578 if (NOT _STATUS_FAIL) 579 set(CXX_STDLIB "-stdlib=libstdc++") 580 set(CXX_WORKS 1) 581 else() 582 custom_try_compile_clangxx("namespace std { class type_info; } \n #include <iostream> \n #include <type_traits>" "std::cout << \"Hello clang++ world!\" << std::endl;" _STATUS_FAIL "-stdlib=libc++" "-std=c++11") 583 if(NOT _STATUS_FAIL) 584 set(CXX_STDLIB "-stdlib=libc++") 585 set(CXX_WORKS 1) 586 endif() 587 endif() 588 endif() 589 590 set(CLANGXX_WORKS ${CXX_WORKS} CACHE INTERNAL "Clang++ ") 591 set(CLANGXX_STDLIB ${CXX_STDLIB} CACHE INTERNAL "Clang++ stdlib") 592 endif() 593 594 595endif() 596 597if(CLANGXX_STDLIB AND (CMAKE_CXX_COMPILER_ID MATCHES "Clang")) 598 set(LLVM_CXXFLAGS "${CLANGXX_STDLIB} ${LLVM_CXXFLAGS}") 599 set(LLVM_LDFLAGS "${CLANGXX_STDLIB} ${LLVM_LDFLAGS}") 600endif() 601 602#################################################################### 603# 604# - '-DNDEBUG' is a work-around for llvm bug 18253 605# 606# llvm-config does not always report the "-DNDEBUG" flag correctly 607# (see LLVM bug 18253). If LLVM and the pocl passes are built with 608# different NDEBUG settings, problems arise 609 610if(NOT DEFINED LLVM_NDEBUG_BUILD) 611 612 message(STATUS "Checking if LLVM is a DEBUG build") 613 separate_arguments(_FLAGS UNIX_COMMAND "${LLVM_CXXFLAGS}") 614 615 set(_TEST_SOURCE "${CMAKE_BINARY_DIR}${CMAKE_FILES_DIRECTORY}/llvmNDEBUG.cc") 616 file(WRITE "${_TEST_SOURCE}" 617 " 618 #include <llvm/Support/Debug.h> 619 int main(int argc, char** argv) { 620 llvm::DebugFlag=true; 621 } 622 ") 623 624 set(TRY_COMPILE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${LLVM_CXXFLAGS} -UNDEBUG") 625 626 try_compile(_TRY_SUCCESS ${CMAKE_BINARY_DIR} "${_TEST_SOURCE}" 627 CMAKE_FLAGS "-DINCLUDE_DIRECTORIES:STRING=${LLVM_INCLUDE_DIRS}" 628 CMAKE_FLAGS "-DLINK_DIRECTORIES:STRING=${LLVM_LIBDIR}" 629 LINK_LIBRARIES "${LLVM_LIBS} ${LLVM_SYSLIBS} ${LLVM_LDFLAGS}" 630 COMPILE_DEFINITIONS ${TRY_COMPILE_CXX_FLAGS} 631 OUTPUT_VARIABLE _TRY_COMPILE_OUTPUT 632 ) 633 634 file(APPEND "${CMAKE_BINARY_DIR}/CMakeFiles/CMakeOutput.log" 635 "Test -NDEBUG flag: ${_TRY_COMPILE_OUTPUT}\n") 636 637 if(_TRY_SUCCESS) 638 message(STATUS "DEBUG build") 639 set(LLVM_NDEBUG_BUILD 0 CACHE INTERNAL "DNDEBUG") 640 else() 641 message(STATUS "Not a DEBUG build") 642 set(LLVM_NDEBUG_BUILD 1 CACHE INTERNAL "DNDEBUG") 643 endif() 644 645endif() 646 647if((NOT LLVM_CXXFLAGS MATCHES "-DNDEBUG") AND LLVM_NDEBUG_BUILD) 648 message(STATUS "adding -DNDEBUG explicitly") 649 set(LLVM_CXXFLAGS "${LLVM_CXXFLAGS} -DNDEBUG") 650endif() 651 652 653#################################################################### 654 655# TODO: We need to set both target-triple and cpu-type when 656# building, since the ABI depends on both. We can either add flags 657# to all the scripts, or set the respective flags here in 658# *_CLANG_FLAGS and *_LLC_FLAGS. Note that clang and llc use 659# different option names to set these. Note that clang calls the 660# triple "target" and the cpu "architecture", which is different 661# from llc. 662 663# Normalise the triple. Otherwise, clang normalises it when 664# passing it to llc, which is then different from the triple we 665# pass to llc. This would lead to inconsistent bytecode files, 666# depending on whether they are generated via clang or directly 667# via llc. 668 669 670if(ENABLE_HOST_CPU_DEVICES AND NOT DEFINED LLC_TRIPLE) 671 message(STATUS "Find out LLC target triple (for host ${LLVM_HOST_TARGET})") 672 set(_EMPTY_C_FILE "${CMAKE_BINARY_DIR}${CMAKE_FILES_DIRECTORY}/tripletfind.c") 673 file(WRITE "${_EMPTY_C_FILE}" "") 674 675 execute_process(COMMAND ${CLANG} "${CLANG_TARGET_OPTION}${LLVM_HOST_TARGET}" -x c ${_EMPTY_C_FILE} -S -emit-llvm -o - RESULT_VARIABLE RES_VAR OUTPUT_VARIABLE OUTPUT_VAR) 676 if(RES_VAR) 677 message(FATAL_ERROR "Error ${RES_VAR} while determining target triple") 678 endif() 679 if(OUTPUT_VAR MATCHES "target triple = \"([^\"]+)") 680 string(STRIP "${CMAKE_MATCH_1}" LLC_TRIPLE) 681 else() 682 message(FATAL_ERROR "Could not find target triple in llvm output") 683 endif() 684 685 # TODO the armv7hl normalize 686 string(REPLACE "armv7l-" "armv7-" LLC_TRIPLE "${LLC_TRIPLE}") 687 688 set(LLC_TRIPLE "${LLC_TRIPLE}" CACHE INTERNAL "LLC_TRIPLE") 689 690endif() 691 692 693# FIXME: The cpu name printed by llc --version is the same cpu that will be 694# targeted if you pass -mcpu=native to llc, so we could replace this auto-detection 695# with just: set(LLC_HOST_CPU "native"), however, we can't do this at the moment 696# because of the work-around for arm1176jz-s. 697if(ENABLE_HOST_CPU_DEVICES AND NOT DEFINED LLC_HOST_CPU_AUTO) 698 message(STATUS "Find out LLC host CPU with ${LLVM_LLC}") 699 execute_process(COMMAND ${LLVM_LLC} "--version" RESULT_VARIABLE RES_VAR OUTPUT_VARIABLE OUTPUT_VAR) 700 # WTF, ^^ has return value 1 701 #if(RES_VAR) 702 # message(FATAL_ERROR "Error ${RES_VAR} while determining LLC host CPU") 703 #endif() 704 705 if(OUTPUT_VAR MATCHES "Host CPU: ([^ ]*)") 706 # sigh... STRING(STRIP is to workaround regexp bug in cmake 707 string(STRIP "${CMAKE_MATCH_1}" LLC_HOST_CPU_AUTO) 708 else() 709 message(FATAL_ERROR "Couldnt determine host CPU from llc output") 710 endif() 711 712 #TODO better 713 if(CMAKE_LIBRARY_ARCHITECTURE MATCHES "gnueabihf" AND LLC_HOST_CPU_AUTO MATCHES "arm1176jz-s") 714 set(LLC_HOST_CPU_AUTO "arm1176jzf-s") 715 endif() 716endif() 717 718 719 720if((LLC_HOST_CPU_AUTO MATCHES "unknown") AND (NOT LLC_HOST_CPU)) 721 message(FATAL_ERROR "LLVM could not recognize your CPU model automatically. Please run CMake with -DLLC_HOST_CPU=<cpu> (you can find valid names with: llc -mcpu=help)") 722else() 723 set(LLC_HOST_CPU_AUTO "${LLC_HOST_CPU_AUTO}" CACHE INTERNAL "Autodetected CPU") 724endif() 725 726if((DEFINED LLC_HOST_CPU) AND (NOT LLC_HOST_CPU STREQUAL LLC_HOST_CPU_AUTO)) 727 message(STATUS "Autodetected CPU ${LLC_HOST_CPU_AUTO} overriden by user to ${LLC_HOST_CPU}") 728 set(HOST_CPU_FORCED 1 CACHE INTERNAL "CPU is forced by user") 729else() 730 set(LLC_HOST_CPU "${LLC_HOST_CPU_AUTO}" CACHE STRING "The Host CPU to use with llc") 731 set(HOST_CPU_FORCED 0 CACHE INTERNAL "CPU is forced by user") 732endif() 733 734 735#################################################################### 736# Some architectures have -march and -mcpu reversed 737 738if(NOT DEFINED CLANG_MARCH_FLAG) 739 message(STATUS "Checking clang -march vs. -mcpu flag") 740 custom_try_compile_clang_silent("" "return 0;" RES ${CLANG_TARGET_OPTION}${LLC_TRIPLE} -march=${LLC_HOST_CPU}) 741 if(NOT RES) 742 set(CLANG_MARCH_FLAG "-march=") 743 else() 744 custom_try_compile_clang_silent("" "return 0;" RES ${CLANG_TARGET_OPTION}${LLC_TRIPLE} -mcpu=${LLC_HOST_CPU}) 745 if(NOT RES) 746 set(CLANG_MARCH_FLAG "-mcpu=") 747 else() 748 message(FATAL_ERROR "Could not determine whether to use -march or -mcpu with clang") 749 endif() 750 endif() 751 message(STATUS " Using ${CLANG_MARCH_FLAG}") 752 753 set(CLANG_MARCH_FLAG ${CLANG_MARCH_FLAG} CACHE INTERNAL "Clang option used to specify the target cpu") 754endif() 755 756#################################################################### 757 758# This tests that we can actually link to the llvm libraries. 759# Mostly to catch issues like #295 - cannot find -ledit 760 761if(NOT DEFINED LLVM_LINK_TEST) 762 763 set(LLVM_LINK_TEST_SOURCE " 764 #include <stdio.h> 765 #include \"llvm/IR/LLVMContext.h\" 766 #include \"llvm/Support/SourceMgr.h\" 767 #include \"llvm/IR/Module.h\" 768 #include \"llvm/IRReader/IRReader.h\" 769 770 int main( int argc, char* argv[] ) 771 { 772 if( argc < 2 ) 773 exit(2); 774 775 llvm::LLVMContext context; 776 llvm::SMDiagnostic err; 777 std::unique_ptr<llvm::Module> module = llvm::parseIRFile( argv[1], err, context ); 778 779 if( !module ) 780 exit(1); 781 else 782 printf(\"DataLayout = %s\\n\", module->getDataLayoutStr().c_str()); 783 784 return 0; 785 }") 786 787 string(RANDOM RNDNAME) 788 set(LLVM_LINK_TEST_FILENAME "${CMAKE_BINARY_DIR}/llvm_link_test_${RNDNAME}.cc") 789 file(WRITE "${LLVM_LINK_TEST_FILENAME}" "${LLVM_LINK_TEST_SOURCE}") 790 791 try_compile(LLVM_LINK_TEST ${CMAKE_BINARY_DIR} "${LLVM_LINK_TEST_FILENAME}" 792 CMAKE_FLAGS "-DINCLUDE_DIRECTORIES:STRING=${LLVM_INCLUDE_DIRS}" 793 CMAKE_FLAGS "-DLINK_DIRECTORIES:STRING=${LLVM_LIBDIR}" 794 LINK_LIBRARIES "${LLVM_LDFLAGS} ${LLVM_LIBS} ${LLVM_SYSLIBS}" 795 COMPILE_DEFINITIONS "${CMAKE_CXX_FLAGS} ${LLVM_CXXFLAGS}" 796 OUTPUT_VARIABLE _TRY_COMPILE_OUTPUT) 797 798 if (LLVM_LINK_TEST) 799 message(STATUS "LLVM link test OK") 800 set(LLVM_LINK_TEST 1 CACHE INTERNAL "LLVM link test result") 801 else() 802 message(STATUS "LLVM link test output: ${_TRY_COMPILE_OUTPUT}") 803 message(FATAL_ERROR "LLVM link test FAILED. This mostly happens when your LLVM installation does not have all dependencies installed.") 804 endif() 805 806endif() 807 808 809#################################################################### 810 811if(ENABLE_HOST_CPU_DEVICES AND NOT DEFINED ${CL_DISABLE_HALF}) 812 set(CL_DISABLE_HALF 0) 813 message(STATUS "Checking fp16 support") 814 custom_try_compile_clang_silent("__fp16 callfp16(__fp16 a) { return a * (__fp16)1.8; };" "__fp16 x=callfp16((__fp16)argc);" RESV ${CLANG_TARGET_OPTION}${LLC_TRIPLE} ${CLANG_MARCH_FLAG}${LLC_HOST_CPU}) 815 if(RESV) 816 set(CL_DISABLE_HALF 1) 817 endif() 818endif() 819 820set(CL_DISABLE_HALF "${CL_DISABLE_HALF}" CACHE INTERNAL "Disable cl_khr_fp16 because fp16 is not supported") 821message(STATUS "FP16 is disabled: ${CL_DISABLE_HALF}") 822 823##################################################################### 824 825execute_process(COMMAND "${CLANG}" "--print-resource-dir" OUTPUT_VARIABLE RESOURCE_DIR) 826string(STRIP "${RESOURCE_DIR}" RESOURCE_DIR) 827set(CLANG_RESOURCE_DIR "${RESOURCE_DIR}" CACHE INTERNAL "Clang resource dir") 828 829set(CLANG_OPENCL_HEADERS "${CLANG_RESOURCE_DIR}/include/opencl-c.h") 830if(NOT LLVM_OLDER_THAN_9_0) 831 list(APPEND CLANG_OPENCL_HEADERS "${CLANG_RESOURCE_DIR}/include/opencl-c-base.h") 832endif() 833