cmake_minimum_required (VERSION 3.4) # CMake utils list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/cmake") # Forbids in-source builds include(CheckNotInSources) #------------------------------------------------------ #----------------- Main configuration ----------------- #------------------------------------------------------ # custom variable allowing to define version suffixes such as -rc*, -beta*, ... set(PUGS_VERSION "0.3.0") # deduce PUGS_SHORT_VERSION using regex string(REGEX MATCH "^[0-9]+\.[0-9]+\.[0-9]+" PUGS_SHORT_VERSION ${PUGS_VERSION}) if("${PUGS_SHORT_VERSION}" STREQUAL "") message(FATAL_ERROR "Unable to compute short version from PUGS_VERSION=${PUGS_VERSION}") endif() # set project version as PUGS_SHORT_VERSION project (Pugs VERSION ${PUGS_SHORT_VERSION}) #------------------------------------------------------ set(CMAKE_EXPORT_COMPILE_COMMANDS ON) #------------------------------------------------------ set(PUGS_SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}") set(PUGS_BINARY_DIR "${CMAKE_CURRENT_BINARY_DIR}") # Change RelWithDebInfo to compile assertions SET("CMAKE_CXX_FLAGS_RELWITHDEBINFO" "-g -O2" CACHE STRING "Flags used by the compiler during release builds with debug info and assertions" FORCE ) SET("CMAKE_C_FLAGS_RELWITHDEBINFO" "-g -O2" CACHE STRING "Flags used by the compiler during release builds with debug info and assertions" FORCE ) # Add new build types set(CMAKE_CXX_FLAGS_COVERAGE "-g -O0 --coverage" CACHE STRING "Flags used by the C++ compiler during coverage builds." FORCE ) set(CMAKE_C_FLAGS_COVERAGE "-g -O0 --coverage" CACHE STRING "Flags used by the C compiler during coverage builds." FORCE ) set(CMAKE_EXE_LINKER_FLAGS_COVERAGE "--coverage" CACHE STRING "Flags used for linking binaries during coverage builds." FORCE ) set(CMAKE_SHARED_LINKER_FLAGS_COVERAGE "--coverage" CACHE STRING "Flags used by the shared libraries linker during coverage builds." FORCE ) mark_as_advanced( CMAKE_CXX_FLAGS_COVERAGE CMAKE_C_FLAGS_COVERAGE CMAKE_EXE_LINKER_FLAGS_COVERAGE CMAKE_SHARED_LINKER_FLAGS_COVERAGE ) if(CMAKE_BUILD_TYPE) string(REGEX MATCH "(Debug|Release|RelWithDebInfo|MinSizeRel|Coverage)" VALID_BUILD_TYPE "${CMAKE_BUILD_TYPE}") if(NOT VALID_BUILD_TYPE) message(FATAL_ERROR "Invalid CMAKE_BUILD_TYPE: '${CMAKE_BUILD_TYPE}'") endif() endif() # Default build type is RelWIthDebInfo if(NOT CMAKE_BUILD_TYPE) set(CMAKE_BUILD_TYPE "RelWithDebInfo" CACHE STRING "Choose the type of build: Debug Release RelWithDebInfo MinSizeRel Coverage." FORCE) endif() #------------------------------------------------------ # Checks if compiler version is compatible with Pugs sources set(GNU_CXX_MIN_VERSION "7.0.0") set(CLANG_CXX_MIN_VERSION "5.0.0") # Pugs default compiler flags set(PUGS_CXX_FLAGS "${PUGS_CXX_FLAGS} -Wall -Wextra") if (CMAKE_CXX_COMPILER_ID STREQUAL "GNU") if(CMAKE_CXX_COMPILER_VERSION VERSION_LESS "${GNU_CXX_MIN_VERSION}") message(FATAL_ERROR "Pugs build requires at least g++-${GNU_CXX_MIN_VERSION}") endif() elseif(CMAKE_CXX_COMPILER_ID STREQUAL "Clang") if(CMAKE_CXX_COMPILER_VERSION VERSION_LESS "${CLANG_CXX_MIN_VERSION}") message(FATAL_ERROR "Pugs build requires at least llvm/clang ++-${CLANG_CXX_MIN_VERSION}") endif() set(PUGS_CXX_FLAGS "${PUGS_CXX_FLAGS} -Wsign-compare -Wunused -Wunused-member-function -Wunused-private-field") endif() #------------------------------------------------------ # defaults use of MPI set(PUGS_ENABLE_MPI AUTO CACHE STRING "Choose one of: AUTO ON OFF") if (NOT PUGS_ENABLE_MPI MATCHES "^(AUTO|ON|OFF)$") message(FATAL_ERROR "PUGS_ENABLE_MPI='${PUGS_ENABLE_MPI}'. Must be set to one of AUTO, ON or OFF") endif() # checks for MPI if (PUGS_ENABLE_MPI MATCHES "^(AUTO|ON)$") find_package(MPI) endif() if (${MPI_FOUND}) set(PUGS_CXX_FLAGS "${PUGS_CXX_FLAGS} ${MPI_CXX_COMPILER_FLAGS}") include_directories(SYSTEM ${MPI_CXX_INCLUDE_DIRS}) elseif(PUGS_ENABLE_MPI STREQUAL "ON") message(FATAL_ERROR "Could not find MPI library while requested") endif() set(PUGS_HAS_MPI ${MPI_FOUND}) #------------------------------------------------------ # search for clang-format find_program(CLANG_FORMAT clang-format) if (CLANG_FORMAT) add_custom_target(clang-format COMMAND echo "running ${CLANG_FORMAT} ..." COMMAND ${CMAKE_COMMAND} -DPUGS_SOURCE_DIR="${PUGS_SOURCE_DIR}" -DCLANG_FORMAT="${CLANG_FORMAT}" -P ${PUGS_SOURCE_DIR}/cmake/ClangFormatProcess.cmake) else () message(WARNING "clang-format no found!") endif() #------------------------------------------------------ # setting Kokkos defaults to OpenMP when available include(FindOpenMP) if(${OPENMP_FOUND}) set(KOKKOS_ENABLE_OPENMP ON CACHE BOOL "") endif() # do not build ETI by default set(KOKKOS_ENABLE_EXPLICIT_INSTANTIATION OFF CACHE BOOL "") # do not use Kokkos deprecated code set(KOKKOS_ENABLE_DEPRECATED_CODE OFF CACHE BOOL "") # Kokkos compiler flags add_subdirectory(${PUGS_SOURCE_DIR}/packages/kokkos) include_directories(SYSTEM ${Kokkos_INCLUDE_DIRS_RET}) include(GetKokkosCompilerFlags) # do not pollute compilation with Kokkos internal warnings set_target_properties(kokkos PROPERTIES COMPILE_FLAGS "-w") # sets Kokkos debug flags when non release build if (CMAKE_BUILD_TYPE MATCHES "^Release$") set (KOKKOS_ENABLE_DEBUG OFF) else() set (KOKKOS_ENABLE_DEBUG ON) endif() # C++ 17 flags if(${CMAKE_VERSION} VERSION_LESS "3.8.0") message(WARNING "Please consider to switch to CMake >= 3.8") set(PUGS_CXX_FLAGS "${PUGS_CXX_FLAGS} -std=gnu++1z") if (CMAKE_CXX_COMPILER_ID STREQUAL "Clang") set(PUGS_CXX_FLAGS "${PUGS_CXX_FLAGS} -Wno-c++17-extensions") endif() else() set(CMAKE_CXX_STANDARD "17") endif() # Compiler flags set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${PUGS_CXX_FLAGS}") # Add debug mode for Standard C++ library set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -D_GLIBCXX_DEBUG -D_LIBCPP_DEBUG=1 ${PUGS_CXX_FLAGS}") set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "${CMAKE_CXX_FLAGS_RELWITHDEBINFO} -D_GLIBCXX_DEBUG -D_LIBCPP_DEBUG=1 ${PUGS_CXX_FLAGS}") #------------------------------------------------------ # Rang (colors? Useless thus necessary!) include_directories(${PUGS_SOURCE_DIR}/packages/rang/include) # CLI11 include_directories(${PUGS_SOURCE_DIR}/packages/CLI11/include) # PGETL include_directories(${PUGS_SOURCE_DIR}/packages/PEGTL/include/tao) # Pugs src add_subdirectory(src) include_directories(src) include_directories(src/algebra) include_directories(src/language) include_directories(src/mesh) include_directories(src/output) include_directories(src/scheme) include_directories(src/utils) # Pugs generated sources include_directories(${PUGS_BINARY_DIR}/src/utils) # Pugs tests set(CATCH_MODULE_PATH "${PUGS_SOURCE_DIR}/packages/Catch2") set(CATCH_INCLUDE_PATH "${CATCH_MODULE_PATH}/single_include/catch2") include("${CATCH_MODULE_PATH}/contrib/ParseAndAddCatchTests.cmake") add_subdirectory("${CATCH_MODULE_PATH}") add_subdirectory(tests) enable_testing() # unit tests coverage if("${CMAKE_BUILD_TYPE}" STREQUAL "Coverage") find_program(GCOVR gcovr) if(NOT GCOVR) message(FATAL_ERROR "gcovr not found, cannot perform coverage.") endif() if (CMAKE_CXX_COMPILER_ID STREQUAL "Clang") string(REPLACE "clang++" "llvm-cov" LLVM_COV "${CMAKE_CXX_COMPILER}") if(NOT EXISTS "${LLVM_COV}") message(FATAL_ERROR "could not find ${LLVM_COV}, cannot perform coverage (using g++ for coverage is recommended).") endif() set(GCOVR_EXTRA "--gcov-executable=${LLVM_COV} gcov") endif() set (GCOVR_EXCLUDE -e "${PUGS_SOURCE_DIR}/src/main.cpp" -e "${PUGS_SOURCE_DIR}/src/utils/BacktraceManager.cpp" -e "${PUGS_SOURCE_DIR}/src/utils/BacktraceManager.hpp" ) set(GCOVR_OPTIONS --object-directory="${PUGS_BINARY_DIR}" -r "${PUGS_SOURCE_DIR}/src" ${GCOVR_EXCLUDE} ${GCOVR_EXTRA}) add_custom_target(run_unit_tests ALL COMMAND ${CMAKE_CTEST_COMMAND} -j ${PROCESSOR_COUNT} DEPENDS unit_tests mpi_unit_tests pugs COMMENT "Executing unit tests." ) add_custom_target(coverage ALL COMMAND ${GCOVR} ${GCOVR_OPTIONS} --exclude-unreachable-branches --sort-percentage DEPENDS run_unit_tests COMMENT "Running gcovr to build coverage report." ) add_custom_target(coverage-report ALL COMMAND ${CMAKE_COMMAND} -E remove_directory "${PUGS_BINARY_DIR}/coverage" COMMAND ${CMAKE_COMMAND} -E make_directory "${PUGS_BINARY_DIR}/coverage" COMMAND ${GCOVR} ${GCOVR_OPTIONS} --delete --html --html-details -o "${PUGS_BINARY_DIR}/coverage/index.html" DEPENDS coverage COMMENT "Building coverage html report." WORKING_DIRECTORY "${PUGS_BINARY_DIR}" ) endif() #------------------------------------------------------ # Search for ParMETIS if(${MPI_FOUND}) find_package(ParMETIS REQUIRED) endif() # ----------------------------------------------------- link_libraries("-rdynamic") # ------------------- Source files -------------------- # Pugs binary add_executable( pugs src/main.cpp) # Libraries target_link_libraries( pugs PugsMesh PugsUtils PugsLanguage kokkos ${PARMETIS_LIBRARIES} ${MPI_CXX_LINK_FLAGS} ${MPI_CXX_LIBRARIES} )