Browse Source

Add the first Conan-based dependecies

add_conan_lib cmake function is defined, that allows to add a dependency using Conan with two possible system fallbacks:

1. pkg_check_modules is invoked, if `PGK_CONFIG ...` is present
2. find_package is invoked if `FIND_PACKAGE_OPTIONS` is present and `pkg_check_modules` has failed

If `ALWAYS_ALLOW_CONAN_FALLBACK` is present - `obey_system_dependencies` will be ignored for the package

Currently, the following dependencies are retrieved using Conan:

* zlib
* expat
* wxwidgets
* libmp3lame
* libid3tag
* libmad

The last three libraries are included in this commit, as they depend on zlib.
Properly pass **arch** and **os.version** to Conan
pull/2/head
Dmitry Vedenko 1 year ago
parent
commit
8aca9d02de
  1. 26
      CMakeLists.txt
  2. 101
      cmake-proxies/CMakeLists.txt
  3. 269
      cmake-proxies/cmake-modules/AudacityDependencies.cmake
  4. 50
      cmake-proxies/cmake-modules/CopyLibs.cmake
  5. 902
      cmake-proxies/cmake-modules/conan.cmake
  6. 94
      cmake-proxies/cmake-modules/dependencies/wxwidgets.cmake
  7. 39
      cmake-proxies/cmake-modules/dependencies/zlib.cmake
  8. 3
      cmake-proxies/libid3tag/CMakeLists.txt
  9. 2
      linux/build-environment/Dockerfile
  10. 6
      linux/build-environment/build_audacity.sh
  11. 2
      src/AboutDialog.cpp
  12. 48
      src/CMakeLists.txt

26
CMakeLists.txt

@ -97,7 +97,18 @@ if( APPLE )
endif()
# Add our module path
set( CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}/cmake-proxies/cmake-modules)
# CMAKE_BINARY_DIR is required for Conan to work
set( AUDACITY_MODULE_PATH "${CMAKE_SOURCE_DIR}/cmake-proxies/cmake-modules")
set( CMAKE_MODULE_PATH
${AUDACITY_MODULE_PATH}
${CMAKE_BINARY_DIR}
${CMAKE_MODULE_PATH}
)
set( CMAKE_PREFIX_PATH
${CMAKE_BINARY_DIR}
${CMAKE_PREFIX_PATH}
)
# This "is a good thing" but greatly increases link time on Linux
#set( CMAKE_INTERPROCEDURAL_OPTIMIZATION ON )
@ -116,6 +127,9 @@ if( CCACHE_PROGRAM )
set_property( GLOBAL PROPERTY RULE_LAUNCH_COMPILE "${CCACHE_PROGRAM}" )
endif()
# Define option() prefix
set( _OPT "audacity_" )
# Our very own project
project( Audacity )
@ -125,7 +139,7 @@ include( AudacityFunctions )
# Allow user to globally set the library preference
cmd_option( ${_OPT}lib_preference
"Library preference [system (if available), local]"
"local"
"system"
STRINGS "system" "local"
)
@ -215,9 +229,6 @@ endif()
message( STATUS " Current Commit: ${GIT_COMMIT_SHORT}" )
message( STATUS )
# Define option() prefix
set( _OPT "audacity_" )
# Organize subdirectories/targets into folders for the IDEs
set_property( GLOBAL PROPERTY USE_FOLDERS ON )
@ -437,6 +448,7 @@ find_package( Python3 )
if( Python3_FOUND )
set( PYTHON "${Python3_EXECUTABLE}" )
elseif( CMAKE_SYSTEM_NAME MATCHES "Windows" )
# This is an odd case now, as Conan requires Python as well
nuget_package( pkgdir "python3" "3.7.7" )
file( TO_NATIVE_PATH "${pkgdir}/tools/python.exe" PYTHON )
endif()
@ -447,6 +459,10 @@ include( "src/Experimental.cmake" )
# Add our children
add_subdirectory( "cmake-proxies" )
# Conan uses find_package and does not set GLOBAL flag
resolve_conan_dependencies()
add_subdirectory( "help" )
add_subdirectory( "images" )
add_subdirectory( "libraries" )

101
cmake-proxies/CMakeLists.txt

@ -1,22 +1,96 @@
# Allow user to globally set the library preference
cmd_option( ${_OPT}lib_preference
"Library preference [system (if available), local]"
"system"
STRINGS "system" "local"
add_conan_lib(
ZLIB
zlib/1.2.11
REQUIRED
PGK_CONFIG "zlib >= 1.2.11"
INTERFACE_NAME ZLIB::ZLIB
OPTION_NAME zlib
CONAN_OPTIONS
zlib:shared=True
)
# Special mode, that will force dependencies to the packages provided by system unless they were set to local explicitly.
cmd_option( ${_OPT}obey_system_dependencies
"Use system packages to satisfy dependencies"
Off
add_conan_lib(
expat
expat/2.2.9
REQUIRED
PGK_CONFIG "expat >= 2.1.0"
CONAN_OPTIONS
expat:shared=True
)
set(wx_zlib "zlib")
set(wx_png "libpng")
if (${_OPT}use_zlib STREQUAL "system")
set(wx_zlib "sys")
# To prevent linking conflicts - we need to use system libpng as well.
# wxWdigets will attempt to resolve it using find_package
set(wx_png "sys")
endif()
set(wx_expat "expat")
if (${_OPT}use_expat STREQUAL "system")
set(wx_expat "sys")
endif()
add_conan_lib(
wxWidgets
wxwidgets/3.1.3-audacity
REQUIRED
ALWAYS_ALLOW_CONAN_FALLBACK
OPTION_NAME wxwidgets
FIND_PACKAGE_OPTIONS COMPONENTS adv base core html qa xml net
INTERFACE_NAME wxwidgets::wxwidgets
CONAN_OPTIONS
wxwidgets:shared=True
wxwidgets:zlib=${wx_zlib}
wxwidgets:expat=${wx_expat}
wxwidgets:compatibility=3.0
wxwidgets:png=${wx_png}
wxwidgets:tiff=off
wxwidgets:secretstore=False
wxwidgets:opengl=False
wxwidgets:propgrid=False
wxwidgets:ribbon=False
wxwidgets:richtext=False
wxwidgets:stc=False
wxwidgets:webview=False
wxwidgets:help=False
wxwidgets:html_help=False
wxwidgets:fs_inet=False
wxwidgets:protocol=False
)
add_conan_lib(
libmp3lame
libmp3lame/3.100
REQUIRED
INTERFACE_NAME libmp3lame::libmp3lame
PGK_CONFIG "lame >= 3.100"
)
add_conan_lib(
libid3tag
libid3tag/0.15.1b
OPTION_NAME id3tag
HAS_ONLY_DEBUG_RELEASE
PGK_CONFIG "id3tag >= 0.15.1b"
)
add_conan_lib(
libmad
libmad/0.15.1b
OPTION_NAME mad
HAS_ONLY_DEBUG_RELEASE
PGK_CONFIG "mad >= 0.15.1b"
)
set_conan_vars_to_parent()
# Required libraries
#
# directory option symbol req chk version
addlib( wxWidgets wxwidgets WX YES NO "" ) # must be first
addlib( expat expat EXPAT YES YES "expat >= 2.1.0" )
addlib( lame lame LAME YES YES "lame >= 3.100" )
addlib( libsndfile sndfile SNDFILE YES YES "sndfile >= 1.0.28" )
addlib( libsoxr soxr SOXR YES YES "soxr >= 0.1.1" )
addlib( portaudio-v19 portaudio PORTAUDIO YES YES "" )
@ -26,8 +100,6 @@ addlib( sqlite sqlite SQLITE YES YES "sqlite3 >= 3.32.
#
# directory option symbol req chk version
addlib( ffmpeg ffmpeg FFMPEG NO NO "libavcodec >= 51.53" "libavformat >= 52.12" "libavutil >= 52.66" )
addlib( libid3tag id3tag LIBID3TAG NO YES "id3tag >= 0.15.1b" )
addlib( libmad mad LIBMAD NO YES "mad >= 0.15.1b" )
addlib( libnyquist nyquist NYQUIST NO YES "" )
addlib( libvamp vamp VAMP NO YES "vamp >= 2.5" "vamp-hostsdk >= 2.5" )
addlib( libogg ogg LIBOGG NO YES "ogg >= 1.3.1" )
@ -53,4 +125,3 @@ addlib( portsmf portsmf PORTSMF NO YES "portSMF >= 0.1"
addlib( libsbsms sbsms SBSMS NO YES "sbsms >= 2.2.0" )
addlib( soundtouch soundtouch SOUNDTOUCH NO YES "soundtouch >= 1.7.1" )
addlib( twolame twolame LIBTWOLAME NO YES "twolame >= 0.3.13" )

269
cmake-proxies/cmake-modules/AudacityDependencies.cmake

@ -0,0 +1,269 @@
# Load Conan
include( conan )
conan_add_remote(NAME audacity
URL https://artifactory.audacityteam.org/artifactory/api/conan/conan-local
VERIFY_SSL True
)
set( CONAN_BUILD_REQUIRES )
set( CONAN_REQUIRES )
set( CONAN_PACKAGE_OPTIONS )
set( CONAN_ONLY_DEBUG_RELEASE )
set( CONAN_CONFIG_OPTIONS )
set( CONAN_RESOLVE_LIST )
# Add a Conan dependency
# Example usage:
# add_conan_lib(
# wxWdidget
# wxwidgets/3.1.3-audacity
# OPTION_NAME wxwidgets
# SYMBOL WXWIDGET
# REQUIRED
# ALWAYS_ALLOW_CONAN_FALLBACK
# PGK_CONFIG "wxwidgets >= 3.1.3"
# FIND_PACKAGE_OPTIONS COMPONENTS adv base core html qa xml
# INTERFACE_NAME wxwidgets::wxwidgets
# HAS_ONLY_DEBUG_RELEASE
# CONAN_OPTIONS
# wxwidgets:shared=True
# )
function (add_conan_lib package conan_package_name )
# Extract the list of packages from the function args
list( SUBLIST ARGV 2 -1 options )
set( list_mode on )
set( current_var "conan_package_options" )
set( option_name_base ${package} )
set( allow_find_package off )
set( find_package_options )
set( conan_package_options )
set( required off )
set( pkg_config_options )
set( system_only ${${_OPT}obey_system_dependencies})
set( interface_name "${package}::${package}")
# Parse function arguments
foreach( opt IN LISTS options )
if( opt STREQUAL "FIND_PACKAGE_OPTIONS" )
set( list_mode on )
set( allow_find_package on )
set( current_var "find_package_options" )
elseif ( opt STREQUAL "CONAN_OPTIONS" )
set( list_mode on )
set( current_var "conan_package_options" )
elseif ( opt STREQUAL "PGK_CONFIG" )
set( list_mode on )
set( current_var "pkg_config_options" )
elseif ( opt STREQUAL "OPTION_NAME" )
set( list_mode off )
set( current_var "option_name_base" )
elseif ( opt STREQUAL "SYMBOL" )
set( list_mode off )
set( current_var "symbol" )
elseif ( opt STREQUAL "INTERFACE_NAME" )
set( list_mode off )
set( current_var "interface_name" )
elseif ( opt STREQUAL "REQUIRED" )
set( required on )
elseif ( opt STREQUAL "ALWAYS_ALLOW_CONAN_FALLBACK" )
set( system_only off )
elseif ( opt STREQUAL "HAS_ONLY_DEBUG_RELEASE" )
set ( only_debug_release on )
else()
if( list_mode )
list( APPEND ${current_var} ${opt} )
else()
set (${current_var} ${opt})
endif()
endif()
endforeach()
if( NOT DEFINED symbol )
string( TOUPPER "${option_name_base}" symbol)
endif()
# Generate CMake option
set( option_name ${_OPT}use_${option_name_base} )
set( option_desc "local" )
if( pkg_config_options OR allow_find_package )
set( sysopt "system" )
string( PREPEND option_desc "system (if available), " )
set( default "${${_OPT}lib_preference}" )
else()
set( default "local" )
endif()
if( NOT required )
set( reqopt "off" )
string( APPEND option_desc ", off" )
endif()
cmd_option( ${option_name}
"Use ${option_name_base} library [${option_desc}]"
"${default}"
STRINGS ${sysopt} "local" ${reqopt}
)
# Early bail out
if( ${option_name} STREQUAL "off" )
message( STATUS "========== ${option_name_base} disabled ==========" )
set( USE_${symbol} OFF CACHE INTERNAL "" FORCE )
return()
endif()
# Let the Audacity target know that this library will be used
set( USE_${symbol} ON CACHE INTERNAL "" FORCE )
if ( TARGET "${package}" )
return()
endif()
if( ${option_name} STREQUAL "system" )
if( pkg_config_options )
pkg_check_modules( PKG_${package} ${pkg_config_options} )
if( PKG_${package}_FOUND )
message( STATUS "Using '${package}' system library" )
# Create the target interface library
add_library( ${interface_name} INTERFACE IMPORTED GLOBAL)
# Retrieve the package information
get_package_interface( PKG_${package} )
# And add it to our target
target_include_directories( ${interface_name} INTERFACE ${INCLUDES} )
target_link_libraries( ${interface_name} INTERFACE ${LIBRARIES} )
message(STATUS "Added inteface ${interface_name} ${INCLUDES} ${LIBRARIES}")
return()
endif()
endif()
if( allow_find_package )
find_package( ${package} QUIET ${find_package_options} )
if ( ${package}_FOUND )
message( STATUS "Using '${package}' system library" )
return()
endif()
endif()
if( system_only )
message( FATAL_ERROR "Failed to find the system package ${package}" )
else()
set( ${option_name} "local" )
set_property( CACHE ${option_name} PROPERTY VALUE "local" )
endif()
endif()
list( APPEND CONAN_REQUIRES ${conan_package_name} )
list( APPEND CONAN_PACKAGE_OPTIONS ${conan_package_options} )
list( APPEND CONAN_RESOLVE_LIST ${package} )
if ( only_debug_release )
message( STATUS "${package} only has Debug and Release versions" )
list( APPEND CONAN_ONLY_DEBUG_RELEASE ${package})
endif()
set( CONAN_REQUIRES ${CONAN_REQUIRES} PARENT_SCOPE )
set( CONAN_PACKAGE_OPTIONS ${CONAN_PACKAGE_OPTIONS} PARENT_SCOPE )
set( CONAN_RESOLVE_LIST ${CONAN_RESOLVE_LIST} PARENT_SCOPE )
set( CONAN_ONLY_DEBUG_RELEASE ${CONAN_ONLY_DEBUG_RELEASE} PARENT_SCOPE )
message (STATUS "Adding Conan dependency ${package}")
endfunction()
macro( set_conan_vars_to_parent )
set( CONAN_REQUIRES ${CONAN_REQUIRES} PARENT_SCOPE )
set( CONAN_PACKAGE_OPTIONS ${CONAN_PACKAGE_OPTIONS} PARENT_SCOPE )
set( CONAN_RESOLVE_LIST ${CONAN_RESOLVE_LIST} PARENT_SCOPE )
set( CONAN_BUILD_REQUIRES ${CONAN_BUILD_REQUIRES} PARENT_SCOPE )
set( CONAN_ONLY_DEBUG_RELEASE ${CONAN_ONLY_DEBUG_RELEASE} PARENT_SCOPE )
endmacro()
function ( _conan_install build_type )
conan_cmake_configure (
REQUIRES ${CONAN_REQUIRES}
GENERATORS cmake_find_package_multi
BUILD_REQUIRES ${CONAN_BUILD_REQUIRES}
${CONAN_CONFIG_OPTIONS}
IMPORTS "bin, *.dll -> ./bin/shared/${build_type} @ keep_path=False"
IMPORTS "lib, *.dll -> ./bin/shared/${build_type} @ keep_path=False"
IMPORTS "lib, *.dylib -> ./lib/shared/${build_type} @ keep_path=False"
IMPORTS "lib, *.so* -> ./lib/shared/${build_type} @ keep_path=False"
OPTIONS ${CONAN_PACKAGE_OPTIONS}
)
message(STATUS "Configuring packages for ${build_type}")
conan_cmake_autodetect(settings BUILD_TYPE ${build_type})
if( CMAKE_SYSTEM_NAME MATCHES "Darwin" )
# We have no AppleSilicon support yet
list( APPEND settings "arch=x86_64" )
list (APPEND settings "os.version=${CMAKE_OSX_DEPLOYMENT_TARGET}")
endif()
if (build_type MATCHES "MinSizeRel|RelWithDebInfo")
message(STATUS "Release only libraries: ${CONAN_ONLY_DEBUG_RELEASE}")
foreach( package ${CONAN_ONLY_DEBUG_RELEASE} )
list( APPEND settings "${package}:build_type=Release")
endforeach()
endif()
conan_cmake_install(PATH_OR_REFERENCE .
BUILD missing
SETTINGS ${settings}
)
endfunction()
macro( resolve_conan_dependencies )
message(STATUS
"Executing Conan: \
REQUIRES ${CONAN_REQUIRES}
GENERATORS cmake_find_package_multi
BUILD_REQUIRES ${CONAN_BUILD_REQUIRES}
${CONAN_CONFIG_OPTIONS}
OPTIONS ${CONAN_PACKAGE_OPTIONS}
")
if(MSVC OR XCODE)
foreach(TYPE ${CMAKE_CONFIGURATION_TYPES})
_conan_install(${TYPE})
endforeach()
else()
_conan_install(${CMAKE_BUILD_TYPE})
endif()
list( REMOVE_DUPLICATES CONAN_REQUIRES )
foreach( package ${CONAN_RESOLVE_LIST} )
message(STATUS "Resolving Conan library ${package}")
find_package(${package} CONFIG)
if (NOT ${package}_FOUND)
message( FATAL_ERROR "Failed to find the conan package ${package}" )
endif()
endforeach()
file(GLOB dependency_helpers "${AUDACITY_MODULE_PATH}/dependencies/*.cmake")
foreach(f ${dependency_helpers})
include(${f})
endforeach()
endmacro()

50
cmake-proxies/cmake-modules/CopyLibs.cmake

@ -7,7 +7,7 @@
# DST destination directory
#
message( "==================================================================" )
message( "Copying wxWidgets libraries:" )
message( "Copying shared libraries:" )
message( "==================================================================" )
# list command no longer ignores empty elements.
@ -39,48 +39,57 @@ function( gather_libs src )
execute( output cmd /k dumpbin /dependents ${src} )
foreach( line ${output} )
if( line MATCHES "^ *wx.*\\.dll" )
set( lib ${WXWIN}/${line} )
set( lib ${WXWIN}/${line} )
if( EXISTS "${lib}" )
list( APPEND libs ${lib} )
gather_libs( ${lib} )
endif()
endforeach()
elseif( CMAKE_HOST_SYSTEM_NAME MATCHES "Darwin" )
message(STATUS "Checking ${src} for libraries...")
execute( output otool -L ${src} )
get_filename_component( libname "${src}" NAME )
if( libname MATCHES ".*dylib" )
string( PREPEND libname "${DST}/" )
else()
set( libname "${src}" )
endif()
set( libname "${src}" )
foreach( line ${output} )
if( line MATCHES "^.*libwx.*\\.dylib " )
if( line MATCHES "^.*\\.dylib " )
string( REGEX REPLACE "dylib .*" "dylib" line "${line}" )
if( NOT line STREQUAL "${src}" AND NOT line MATCHES "@executable" )
set( lib ${line} )
set( lib "${WXWIN}/${line}" )
if( NOT lib STREQUAL "${src}" AND NOT line MATCHES "@executable" AND EXISTS "${lib}")
message(STATUS "\tProcessing ${lib}...")
list( APPEND libs ${lib} )
get_filename_component( refname "${lib}" NAME )
list( APPEND postcmds "sh -c 'install_name_tool -change ${lib} @executable_path/../Frameworks/${refname} ${libname}'" )
message(STATUS "\t\tAdding ${refname} to ${src}")
list( APPEND postcmds "sh -c 'install_name_tool -change ${refname} @executable_path/../Frameworks/${refname} ${src}'" )
gather_libs( ${lib} )
endif()
endif()
endforeach()
elseif( CMAKE_HOST_SYSTEM_NAME MATCHES "Linux" )
message(STATUS "Executing LD_LIBRARY_PATH='${WXWIN}' ldd ${src}")
execute( output sh -c "LD_LIBRARY_PATH='${WXWIN}' ldd ${src}" )
get_filename_component( libname "${src}" NAME )
foreach( line ${output} )
if( line MATCHES ".*libwx.*" )
string( REGEX REPLACE ".* => (.*) \\(.*$" "\\1" line "${line}" )
message (STATUS "\tChecking ${line}...")
string( REGEX REPLACE "(.*) => .* \\(.*$" "\\1" line "${line}" )
set(line "${WXWIN}/${line}")
if (EXISTS "${line}")
message (STATUS "\tAdding ${line}...")
set( lib ${line} )
@ -88,6 +97,7 @@ function( gather_libs src )
gather_libs( ${lib} )
endif()
endforeach()
endif()
@ -97,9 +107,7 @@ endfunction()
gather_libs( "${SRC}" )
list( REMOVE_DUPLICATES libs )
file( INSTALL ${libs} DESTINATION ${DST} FOLLOW_SYMLINK_CHAIN )
list( REMOVE_DUPLICATES postcmds )
foreach( cmd ${postcmds} )
execute_process(
@ -109,3 +117,5 @@ foreach( cmd ${postcmds} )
)
endforeach()
list( REMOVE_DUPLICATES libs )
file( INSTALL ${libs} DESTINATION ${DST} FOLLOW_SYMLINK_CHAIN )

902
cmake-proxies/cmake-modules/conan.cmake

@ -0,0 +1,902 @@
# The MIT License (MIT)
# Copyright (c) 2018 JFrog
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to deal
# in the Software without restriction, including without limitation the rights
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
# The above copyright notice and this permission notice shall be included in all
# copies or substantial portions of the Software.
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
# SOFTWARE.
# This file comes from: https://github.com/conan-io/cmake-conan. Please refer
# to this repository for issues and documentation.
# Its purpose is to wrap and launch Conan C/C++ Package Manager when cmake is called.
# It will take CMake current settings (os, compiler, compiler version, architecture)
# and translate them to conan settings for installing and retrieving dependencies.
# It is intended to facilitate developers building projects that have conan dependencies,
# but it is only necessary on the end-user side. It is not necessary to create conan
# packages, in fact it shouldn't be use for that. Check the project documentation.
# version: 0.17.0-dev
include(CMakeParseArguments)
function(_get_msvc_ide_version result)
set(${result} "" PARENT_SCOPE)
if(NOT MSVC_VERSION VERSION_LESS 1400 AND MSVC_VERSION VERSION_LESS 1500)
set(${result} 8 PARENT_SCOPE)
elseif(NOT MSVC_VERSION VERSION_LESS 1500 AND MSVC_VERSION VERSION_LESS 1600)
set(${result} 9 PARENT_SCOPE)
elseif(NOT MSVC_VERSION VERSION_LESS 1600 AND MSVC_VERSION VERSION_LESS 1700)
set(${result} 10 PARENT_SCOPE)
elseif(NOT MSVC_VERSION VERSION_LESS 1700 AND MSVC_VERSION VERSION_LESS 1800)
set(${result} 11 PARENT_SCOPE)
elseif(NOT MSVC_VERSION VERSION_LESS 1800 AND MSVC_VERSION VERSION_LESS 1900)
set(${result} 12 PARENT_SCOPE)
elseif(NOT MSVC_VERSION VERSION_LESS 1900 AND MSVC_VERSION VERSION_LESS 1910)
set(${result} 14 PARENT_SCOPE)
elseif(NOT MSVC_VERSION VERSION_LESS 1910 AND MSVC_VERSION VERSION_LESS 1920)
set(${result} 15 PARENT_SCOPE)
elseif(NOT MSVC_VERSION VERSION_LESS 1920 AND MSVC_VERSION VERSION_LESS 1930)
set(${result} 16 PARENT_SCOPE)
else()
message(FATAL_ERROR "Conan: Unknown MSVC compiler version [${MSVC_VERSION}]")
endif()
endfunction()
macro(_conan_detect_build_type)
conan_parse_arguments(${ARGV})
if(ARGUMENTS_BUILD_TYPE)
set(_CONAN_SETTING_BUILD_TYPE ${ARGUMENTS_BUILD_TYPE})
elseif(CMAKE_BUILD_TYPE)
set(_CONAN_SETTING_BUILD_TYPE ${CMAKE_BUILD_TYPE})
else()
message(FATAL_ERROR "Please specify in command line CMAKE_BUILD_TYPE (-DCMAKE_BUILD_TYPE=Release)")
endif()
string(TOUPPER ${_CONAN_SETTING_BUILD_TYPE} _CONAN_SETTING_BUILD_TYPE_UPPER)
if (_CONAN_SETTING_BUILD_TYPE_UPPER STREQUAL "DEBUG")
set(_CONAN_SETTING_BUILD_TYPE "Debug")
elseif(_CONAN_SETTING_BUILD_TYPE_UPPER STREQUAL "RELEASE")
set(_CONAN_SETTING_BUILD_TYPE "Release")
elseif(_CONAN_SETTING_BUILD_TYPE_UPPER STREQUAL "RELWITHDEBINFO")
set(_CONAN_SETTING_BUILD_TYPE "RelWithDebInfo")
elseif(_CONAN_SETTING_BUILD_TYPE_UPPER STREQUAL "MINSIZEREL")
set(_CONAN_SETTING_BUILD_TYPE "MinSizeRel")
endif()
endmacro()
macro(_conan_check_system_name)
#handle -s os setting
if(CMAKE_SYSTEM_NAME AND NOT CMAKE_SYSTEM_NAME STREQUAL "Generic")
#use default conan os setting if CMAKE_SYSTEM_NAME is not defined
set(CONAN_SYSTEM_NAME ${CMAKE_SYSTEM_NAME})
if(${CMAKE_SYSTEM_NAME} STREQUAL "Darwin")
set(CONAN_SYSTEM_NAME Macos)
endif()
if(${CMAKE_SYSTEM_NAME} STREQUAL "QNX")
set(CONAN_SYSTEM_NAME Neutrino)
endif()
set(CONAN_SUPPORTED_PLATFORMS Windows Linux Macos Android iOS FreeBSD WindowsStore WindowsCE watchOS tvOS FreeBSD SunOS AIX Arduino Emscripten Neutrino)
list (FIND CONAN_SUPPORTED_PLATFORMS "${CONAN_SYSTEM_NAME}" _index)
if (${_index} GREATER -1)
#check if the cmake system is a conan supported one
set(_CONAN_SETTING_OS ${CONAN_SYSTEM_NAME})
else()
message(FATAL_ERROR "cmake system ${CONAN_SYSTEM_NAME} is not supported by conan. Use one of ${CONAN_SUPPORTED_PLATFORMS}")
endif()
endif()
endmacro()
macro(_conan_check_language)
get_property(_languages GLOBAL PROPERTY ENABLED_LANGUAGES)
if (";${_languages};" MATCHES ";CXX;")
set(LANGUAGE CXX)
set(USING_CXX 1)
elseif (";${_languages};" MATCHES ";C;")
set(LANGUAGE C)
set(USING_CXX 0)
else ()
message(FATAL_ERROR "Conan: Neither C or C++ was detected as a language for the project. Unabled to detect compiler version.")
endif()
endmacro()
macro(_conan_detect_compiler)
conan_parse_arguments(${ARGV})
if(ARGUMENTS_ARCH)
set(_CONAN_SETTING_ARCH ${ARGUMENTS_ARCH})
endif()
if (${CMAKE_${LANGUAGE}_COMPILER_ID} STREQUAL GNU)
# using GCC
# TODO: Handle other params
string(REPLACE "." ";" VERSION_LIST ${CMAKE_${LANGUAGE}_COMPILER_VERSION})
list(GET VERSION_LIST 0 MAJOR)
list(GET VERSION_LIST 1 MINOR)
set(COMPILER_VERSION ${MAJOR}.${MINOR})
if(${MAJOR} GREATER 4)
set(COMPILER_VERSION ${MAJOR})
endif()
set(_CONAN_SETTING_COMPILER gcc)
set(_CONAN_SETTING_COMPILER_VERSION ${COMPILER_VERSION})
if (USING_CXX)
conan_cmake_detect_unix_libcxx(_LIBCXX)
set(_CONAN_SETTING_COMPILER_LIBCXX ${_LIBCXX})
endif ()
elseif (${CMAKE_${LANGUAGE}_COMPILER_ID} STREQUAL Intel)
string(REPLACE "." ";" VERSION_LIST ${CMAKE_${LANGUAGE}_COMPILER_VERSION})
list(GET VERSION_LIST 0 MAJOR)
list(GET VERSION_LIST 1 MINOR)
set(COMPILER_VERSION ${MAJOR}.${MINOR})
set(_CONAN_SETTING_COMPILER intel)
set(_CONAN_SETTING_COMPILER_VERSION ${COMPILER_VERSION})
if (USING_CXX)
conan_cmake_detect_unix_libcxx(_LIBCXX)
set(_CONAN_SETTING_COMPILER_LIBCXX ${_LIBCXX})
endif ()
elseif (${CMAKE_${LANGUAGE}_COMPILER_ID} STREQUAL AppleClang)
# using AppleClang
string(REPLACE "." ";" VERSION_LIST ${CMAKE_${LANGUAGE}_COMPILER_VERSION})
list(GET VERSION_LIST 0 MAJOR)
list(GET VERSION_LIST 1 MINOR)
set(_CONAN_SETTING_COMPILER apple-clang)
set(_CONAN_SETTING_COMPILER_VERSION ${MAJOR}.${MINOR})
if (USING_CXX)
conan_cmake_detect_unix_libcxx(_LIBCXX)
set(_CONAN_SETTING_COMPILER_LIBCXX ${_LIBCXX})
endif ()
elseif (${CMAKE_${LANGUAGE}_COMPILER_ID} STREQUAL Clang)
string(REPLACE "." ";" VERSION_LIST ${CMAKE_${LANGUAGE}_COMPILER_VERSION})
list(GET VERSION_LIST 0 MAJOR)
list(GET VERSION_LIST 1 MINOR)
set(_CONAN_SETTING_COMPILER clang)
set(_CONAN_SETTING_COMPILER_VERSION ${MAJOR}.${MINOR})
if(APPLE)
cmake_policy(GET CMP0025 APPLE_CLANG_POLICY)
if(NOT APPLE_CLANG_POLICY STREQUAL NEW)
message(STATUS "Conan: APPLE and Clang detected. Assuming apple-clang compiler. Set CMP0025 to avoid it")
set(_CONAN_SETTING_COMPILER apple-clang)
endif()
endif()
if(${_CONAN_SETTING_COMPILER} STREQUAL clang AND ${MAJOR} GREATER 7)
set(_CONAN_SETTING_COMPILER_VERSION ${MAJOR})
endif()
if (USING_CXX)
conan_cmake_detect_unix_libcxx(_LIBCXX)
set(_CONAN_SETTING_COMPILER_LIBCXX ${_LIBCXX})
endif ()
elseif(${CMAKE_${LANGUAGE}_COMPILER_ID} STREQUAL MSVC)
set(_VISUAL "Visual Studio")
_get_msvc_ide_version(_VISUAL_VERSION)
if("${_VISUAL_VERSION}" STREQUAL "")
message(FATAL_ERROR "Conan: Visual Studio not recognized")
else()
set(_CONAN_SETTING_COMPILER ${_VISUAL})
set(_CONAN_SETTING_COMPILER_VERSION ${_VISUAL_VERSION})
endif()
if(NOT _CONAN_SETTING_ARCH)
if (MSVC_${LANGUAGE}_ARCHITECTURE_ID MATCHES "64")
set(_CONAN_SETTING_ARCH x86_64)
elseif (MSVC_${LANGUAGE}_ARCHITECTURE_ID MATCHES "^ARM")
message(STATUS "Conan: Using default ARM architecture from MSVC")
set(_CONAN_SETTING_ARCH armv6)
elseif (MSVC_${LANGUAGE}_ARCHITECTURE_ID MATCHES "86")
set(_CONAN_SETTING_ARCH x86)
else ()
message(FATAL_ERROR "Conan: Unknown MSVC architecture [${MSVC_${LANGUAGE}_ARCHITECTURE_ID}]")
endif()
endif()
conan_cmake_detect_vs_runtime(_vs_runtime ${ARGV})
message(STATUS "Conan: Detected VS runtime: ${_vs_runtime}")
set(_CONAN_SETTING_COMPILER_RUNTIME ${_vs_runtime})
if (CMAKE_GENERATOR_TOOLSET)
set(_CONAN_SETTING_COMPILER_TOOLSET ${CMAKE_VS_PLATFORM_TOOLSET})
elseif(CMAKE_VS_PLATFORM_TOOLSET AND (CMAKE_GENERATOR STREQUAL "Ninja"))
set(_CONAN_SETTING_COMPILER_TOOLSET ${CMAKE_VS_PLATFORM_TOOLSET})
endif()
else()
message(FATAL_ERROR "Conan: compiler setup not recognized")
endif()
endmacro()
function(conan_cmake_settings result)
#message(STATUS "COMPILER " ${CMAKE_CXX_COMPILER})
#message(STATUS "COMPILER " ${CMAKE_CXX_COMPILER_ID})
#message(STATUS "VERSION " ${CMAKE_CXX_COMPILER_VERSION})
#message(STATUS "FLAGS " ${CMAKE_LANG_FLAGS})
#message(STATUS "LIB ARCH " ${CMAKE_CXX_LIBRARY_ARCHITECTURE})
#message(STATUS "BUILD TYPE " ${CMAKE_BUILD_TYPE})
#message(STATUS "GENERATOR " ${CMAKE_GENERATOR})
#message(STATUS "GENERATOR WIN64 " ${CMAKE_CL_64})
message(STATUS "Conan: Automatic detection of conan settings from cmake")
conan_parse_arguments(${ARGV})
_conan_detect_build_type(${ARGV})
_conan_check_system_name()
_conan_check_language()
_conan_detect_compiler(${ARGV})
# If profile is defined it is used
if(CMAKE_BUILD_TYPE STREQUAL "Debug" AND ARGUMENTS_DEBUG_PROFILE)
set(_APPLIED_PROFILES ${ARGUMENTS_DEBUG_PROFILE})
elseif(CMAKE_BUILD_TYPE STREQUAL "Release" AND ARGUMENTS_RELEASE_PROFILE)
set(_APPLIED_PROFILES ${ARGUMENTS_RELEASE_PROFILE})
elseif(CMAKE_BUILD_TYPE STREQUAL "RelWithDebInfo" AND ARGUMENTS_RELWITHDEBINFO_PROFILE)
set(_APPLIED_PROFILES ${ARGUMENTS_RELWITHDEBINFO_PROFILE})
elseif(CMAKE_BUILD_TYPE STREQUAL "MinSizeRel" AND ARGUMENTS_MINSIZEREL_PROFILE)
set(_APPLIED_PROFILES ${ARGUMENTS_MINSIZEREL_PROFILE})
elseif(ARGUMENTS_PROFILE)
set(_APPLIED_PROFILES ${ARGUMENTS_PROFILE})
endif()
foreach(ARG ${_APPLIED_PROFILES})
set(_SETTINGS ${_SETTINGS} -pr=${ARG})
endforeach()
foreach(ARG ${ARGUMENTS_PROFILE_BUILD})
conan_check(VERSION 1.24.0 REQUIRED DETECT_QUIET)
set(_SETTINGS ${_SETTINGS} -pr:b=${ARG})
endforeach()
if(NOT _SETTINGS OR ARGUMENTS_PROFILE_AUTO STREQUAL "ALL")
set(ARGUMENTS_PROFILE_AUTO arch build_type compiler compiler.version
compiler.runtime compiler.libcxx compiler.toolset)
endif()
# remove any manually specified settings from the autodetected settings
foreach(ARG ${ARGUMENTS_SETTINGS})
string(REGEX MATCH "[^=]*" MANUAL_SETTING "${ARG}")
message(STATUS "Conan: ${MANUAL_SETTING} was added as an argument. Not using the autodetected one.")
list(REMOVE_ITEM ARGUMENTS_PROFILE_AUTO "${MANUAL_SETTING}")
endforeach()
# Automatic from CMake
foreach(ARG ${ARGUMENTS_PROFILE_AUTO})
string(TOUPPER ${ARG} _arg_name)
string(REPLACE "." "_" _arg_name ${_arg_name})
if(_CONAN_SETTING_${_arg_name})
set(_SETTINGS ${_SETTINGS} -s ${ARG}=${_CONAN_SETTING_${_arg_name}})
endif()
endforeach()
foreach(ARG ${ARGUMENTS_SETTINGS})
set(_SETTINGS ${_SETTINGS} -s ${ARG})
endforeach()
message(STATUS "Conan: Settings= ${_SETTINGS}")
set(${result} ${_SETTINGS} PARENT_SCOPE)
endfunction()
function(conan_cmake_detect_unix_libcxx result)
# Take into account any -stdlib in compile options
get_directory_property(compile_options DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} COMPILE_OPTIONS)
string(GENEX_STRIP "${compile_options}" compile_options)
# Take into account any _GLIBCXX_USE_CXX11_ABI in compile definitions
get_directory_property(defines DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} COMPILE_DEFINITIONS)
string(GENEX_STRIP "${defines}" defines)
foreach(define ${defines})
if(define MATCHES "_GLIBCXX_USE_CXX11_ABI")
if(define MATCHES "^-D")
set(compile_options ${compile_options} "${define}")
else()
set(compile_options ${compile_options} "-D${define}")
endif()
endif()
endforeach()
# add additional compiler options ala cmRulePlaceholderExpander::ExpandRuleVariable
set(EXPAND_CXX_COMPILER ${CMAKE_CXX_COMPILER})
if(CMAKE_CXX_COMPILER_ARG1)
# CMake splits CXX="foo bar baz" into CMAKE_CXX_COMPILER="foo", CMAKE_CXX_COMPILER_ARG1="bar baz"
# without this, ccache, winegcc, or other wrappers might lose all their arguments
separate_arguments(SPLIT_CXX_COMPILER_ARG1 NATIVE_COMMAND ${CMAKE_CXX_COMPILER_ARG1})
list(APPEND EXPAND_CXX_COMPILER ${SPLIT_CXX_COMPILER_ARG1})
endif()
if(CMAKE_CXX_COMPILE_OPTIONS_TARGET AND CMAKE_CXX_COMPILER_TARGET)
# without --target= we may be calling the wrong underlying GCC
list(APPEND EXPAND_CXX_COMPILER "${CMAKE_CXX_COMPILE_OPTIONS_TARGET}${CMAKE_CXX_COMPILER_TARGET}")
endif()
if(CMAKE_CXX_COMPILE_OPTIONS_EXTERNAL_TOOLCHAIN AND CMAKE_CXX_COMPILER_EXTERNAL_TOOLCHAIN)
list(APPEND EXPAND_CXX_COMPILER "${CMAKE_CXX_COMPILE_OPTIONS_EXTERNAL_TOOLCHAIN}${CMAKE_CXX_COMPILER_EXTERNAL_TOOLCHAIN}")
endif()
if(CMAKE_CXX_COMPILE_OPTIONS_SYSROOT)
# without --sysroot= we may find the wrong #include <string>
if(CMAKE_SYSROOT_COMPILE)
list(APPEND EXPAND_CXX_COMPILER "${CMAKE_CXX_COMPILE_OPTIONS_SYSROOT}${CMAKE_SYSROOT_COMPILE}")
elseif(CMAKE_SYSROOT)
list(APPEND EXPAND_CXX_COMPILER "${CMAKE_CXX_COMPILE_OPTIONS_SYSROOT}${CMAKE_SYSROOT}")
endif()
endif()
separate_arguments(SPLIT_CXX_FLAGS NATIVE_COMMAND ${CMAKE_CXX_FLAGS})
if(CMAKE_OSX_SYSROOT)
set(xcode_sysroot_option "--sysroot=${CMAKE_OSX_SYSROOT}")
endif()
execute_process(
COMMAND ${CMAKE_COMMAND} -E echo "#include <string>"
COMMAND ${EXPAND_CXX_COMPILER} ${SPLIT_CXX_FLAGS} -x c++ ${xcode_sysroot_option} ${compile_options} -E -dM -
OUTPUT_VARIABLE string_defines
)
if(string_defines MATCHES "#define __GLIBCXX__")
# Allow -D_GLIBCXX_USE_CXX11_ABI=ON/OFF as argument to cmake
if(DEFINED _GLIBCXX_USE_CXX11_ABI)
if(_GLIBCXX_USE_CXX11_ABI)
set(${result} libstdc++11 PARENT_SCOPE)
return()
else()
set(${result} libstdc++ PARENT_SCOPE)
return()
endif()
endif()
if(string_defines MATCHES "#define _GLIBCXX_USE_CXX11_ABI 1\n")
set(${result} libstdc++11 PARENT_SCOPE)
else()
# Either the compiler is missing the define because it is old, and so
# it can't use the new abi, or the compiler was configured to use the
# old abi by the user or distro (e.g. devtoolset on RHEL/CentOS)
set(${result} libstdc++ PARENT_SCOPE)
endif()
else()
set(${result} libc++ PARENT_SCOPE)
endif()
endfunction()
function(conan_cmake_detect_vs_runtime result)
conan_parse_arguments(${ARGV})
if(ARGUMENTS_BUILD_TYPE)
set(build_type "${ARGUMENTS_BUILD_TYPE}")
elseif(CMAKE_BUILD_TYPE)
set(build_type "${CMAKE_BUILD_TYPE}")
else()
message(FATAL_ERROR "Please specify in command line CMAKE_BUILD_TYPE (-DCMAKE_BUILD_TYPE=Release)")
endif()
if(build_type)
string(TOUPPER "${build_type}" build_type)
endif()
set(variables CMAKE_CXX_FLAGS_${build_type} CMAKE_C_FLAGS_${build_type} CMAKE_CXX_FLAGS CMAKE_C_FLAGS)
foreach(variable ${variables})
if(NOT "${${variable}}" STREQUAL "")
string(REPLACE " " ";" flags "${${variable}}")
foreach (flag ${flags})
if("${flag}" STREQUAL "/MD" OR "${flag}" STREQUAL "/MDd" OR "${flag}" STREQUAL "/MT" OR "${flag}" STREQUAL "/MTd")
string(SUBSTRING "${flag}" 1 -1 runtime)
set(${result} "${runtime}" PARENT_SCOPE)
return()
endif()
endforeach()
endif()
endforeach()
if("${build_type}" STREQUAL "DEBUG")
set(${result} "MDd" PARENT_SCOPE)
else()
set(${result} "MD" PARENT_SCOPE)
endif()
endfunction()
function(_collect_settings result)
set(ARGUMENTS_PROFILE_AUTO arch build_type compiler compiler.version
compiler.runtime compiler.libcxx compiler.toolset)
foreach(ARG ${ARGUMENTS_PROFILE_AUTO})
string(TOUPPER ${ARG} _arg_name)
string(REPLACE "." "_" _arg_name ${_arg_name})
if(_CONAN_SETTING_${_arg_name})
set(detected_setings ${detected_setings} ${ARG}=${_CONAN_SETTING_${_arg_name}})
endif()
endforeach()
set(${result} ${detected_setings} PARENT_SCOPE)
endfunction()
function(conan_cmake_autodetect detected_settings ${ARGV})
_conan_detect_build_type(${ARGV})
_conan_check_system_name()
_conan_check_language()
_conan_detect_compiler(${ARGV})
_collect_settings(collected_settings)
set(${detected_settings} ${collected_settings} PARENT_SCOPE)
endfunction()
macro(conan_parse_arguments)
set(options BASIC_SETUP CMAKE_TARGETS UPDATE KEEP_RPATHS NO_LOAD NO_OUTPUT_DIRS OUTPUT_QUIET NO_IMPORTS SKIP_STD)
set(oneValueArgs CONANFILE ARCH BUILD_TYPE INSTALL_FOLDER CONAN_COMMAND)
set(multiValueArgs DEBUG_PROFILE RELEASE_PROFILE RELWITHDEBINFO_PROFILE MINSIZEREL_PROFILE
PROFILE REQUIRES OPTIONS IMPORTS SETTINGS BUILD ENV GENERATORS PROFILE_AUTO
INSTALL_ARGS CONFIGURATION_TYPES PROFILE_BUILD BUILD_REQUIRES)
cmake_parse_arguments(ARGUMENTS "${options}" "${oneValueArgs}" "${multiValueArgs}" ${ARGN})
endmacro()
function(old_conan_cmake_install)
# Calls "conan install"
# Argument BUILD is equivalant to --build={missing, PkgName,...} or
# --build when argument is 'BUILD all' (which builds all packages from source)
# Argument CONAN_COMMAND, to specify the conan path, e.g. in case of running from source
# cmake does not identify conan as command, even if it is +x and it is in the path
conan_parse_arguments(${ARGV})
if(CONAN_CMAKE_MULTI)
set(ARGUMENTS_GENERATORS ${ARGUMENTS_GENERATORS} cmake_multi)
else()
set(ARGUMENTS_GENERATORS ${ARGUMENTS_GENERATORS} cmake)
endif()
set(CONAN_BUILD_POLICY "")
foreach(ARG ${ARGUMENTS_BUILD})
if(${ARG} STREQUAL "all")
set(CONAN_BUILD_POLICY ${CONAN_BUILD_POLICY} --build)
break()
else()
set(CONAN_BUILD_POLICY ${CONAN_BUILD_POLICY} --build=${ARG})
endif()
endforeach()
if(ARGUMENTS_CONAN_COMMAND)
set(CONAN_CMD ${ARGUMENTS_CONAN_COMMAND})
else()
conan_check(REQUIRED)
endif()
set(CONAN_OPTIONS "")
if(ARGUMENTS_CONANFILE)
if(IS_ABSOLUTE ${ARGUMENTS_CONANFILE})
set(CONANFILE ${ARGUMENTS_CONANFILE})
else()
set(CONANFILE ${CMAKE_CURRENT_SOURCE_DIR}/${ARGUMENTS_CONANFILE})
endif()
else()
set(CONANFILE ".")
endif()
foreach(ARG ${ARGUMENTS_OPTIONS})
set(CONAN_OPTIONS ${CONAN_OPTIONS} -o=${ARG})
endforeach()
if(ARGUMENTS_UPDATE)
set(CONAN_INSTALL_UPDATE --update)
endif()
if(ARGUMENTS_NO_IMPORTS)
set(CONAN_INSTALL_NO_IMPORTS --no-imports)
endif()
set(CONAN_INSTALL_FOLDER "")
if(ARGUMENTS_INSTALL_FOLDER)
set(CONAN_INSTALL_FOLDER -if=${ARGUMENTS_INSTALL_FOLDER})
endif()
foreach(ARG ${ARGUMENTS_GENERATORS})
set(CONAN_GENERATORS ${CONAN_GENERATORS} -g=${ARG})
endforeach()
foreach(ARG ${ARGUMENTS_ENV})
set(CONAN_ENV_VARS ${CONAN_ENV_VARS} -e=${ARG})
endforeach()
set(conan_args install ${CONANFILE} ${settings} ${CONAN_ENV_VARS} ${CONAN_GENERATORS} ${CONAN_BUILD_POLICY} ${CONAN_INSTALL_UPDATE} ${CONAN_INSTALL_NO_IMPORTS} ${CONAN_OPTIONS} ${CONAN_INSTALL_FOLDER} ${ARGUMENTS_INSTALL_ARGS})
string (REPLACE ";" " " _conan_args "${conan_args}")
message(STATUS "Conan executing: ${CONAN_CMD} ${_conan_args}")
if(ARGUMENTS_OUTPUT_QUIET)
execute_process(COMMAND ${CONAN_CMD} ${conan_args}
RESULT_VARIABLE return_code
OUTPUT_VARIABLE conan_output
ERROR_VARIABLE conan_output
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR})
else()
execute_process(COMMAND ${CONAN_CMD} ${conan_args}
RESULT_VARIABLE return_code
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR})
endif()
if(NOT "${return_code}" STREQUAL "0")
message(FATAL_ERROR "Conan install failed='${return_code}'")
endif()
endfunction()
function(conan_cmake_install)
if(DEFINED CONAN_COMMAND)
set(CONAN_CMD ${CONAN_COMMAND})
else()
conan_check(REQUIRED)
endif()
set(installOptions UPDATE NO_IMPORTS OUTPUT_QUIET ERROR_QUIET)
set(installOneValueArgs PATH_OR_REFERENCE REFERENCE REMOTE LOCKFILE LOCKFILE_OUT LOCKFILE_NODE_ID INSTALL_FOLDER)
set(installMultiValueArgs GENERATOR BUILD ENV ENV_HOST ENV_BUILD OPTIONS_HOST OPTIONS OPTIONS_BUILD PROFILE
PROFILE_HOST PROFILE_BUILD SETTINGS SETTINGS_HOST SETTINGS_BUILD)
cmake_parse_arguments(ARGS "${installOptions}" "${installOneValueArgs}" "${installMultiValueArgs}" ${ARGN})
foreach(arg ${installOptions})
if(ARGS_${arg})
set(${arg} ${${arg}} ${ARGS_${arg}})
endif()
endforeach()
foreach(arg ${installOneValueArgs})
if(DEFINED ARGS_${arg})
if("${arg}" STREQUAL "REMOTE")
set(flag "--remote")
elseif("${arg}" STREQUAL "LOCKFILE")
set(flag "--lockfile")
elseif("${arg}" STREQUAL "LOCKFILE_OUT")
set(flag "--lockfile-out")
elseif("${arg}" STREQUAL "LOCKFILE_NODE_ID")
set(flag "--lockfile-node-id")
elseif("${arg}" STREQUAL "INSTALL_FOLDER")
set(flag "--install-folder")
endif()
set(${arg} ${${arg}} ${flag} ${ARGS_${arg}})
endif()
endforeach()
foreach(arg ${installMultiValueArgs})
if(DEFINED ARGS_${arg})
if("${arg}" STREQUAL "GENERATOR")
set(flag "--generator")
elseif("${arg}" STREQUAL "BUILD")
set(flag "--build")
elseif("${arg}" STREQUAL "ENV")
set(flag "--env")
elseif("${arg}" STREQUAL "ENV_HOST")
set(flag "--env:host")
elseif("${arg}" STREQUAL "ENV_BUILD")
set(flag "--env:build")
elseif("${arg}" STREQUAL "OPTIONS")
set(flag "--options")
elseif("${arg}" STREQUAL "OPTIONS_HOST")
set(flag "--options:host")
elseif("${arg}" STREQUAL "OPTIONS_BUILD")
set(flag "--options:build")
elseif("${arg}" STREQUAL "PROFILE")
set(flag "--profile")
elseif("${arg}" STREQUAL "PROFILE_HOST")
set(flag "--profile:host")
elseif("${arg}" STREQUAL "PROFILE_BUILD")
set(flag "--profile:build")
elseif("${arg}" STREQUAL "SETTINGS")
set(flag "--settings")
elseif("${arg}" STREQUAL "SETTINGS_HOST")
set(flag "--settings:host")
elseif("${arg}" STREQUAL "SETTINGS_BUILD")
set(flag "--settings:build")
endif()
list(LENGTH ARGS_${arg} numargs)
foreach(item ${ARGS_${arg}})
if(${item} STREQUAL "all" AND ${arg} STREQUAL "BUILD")
set(${arg} "--build")
break()
endif()
set(${arg} ${${arg}} ${flag} ${item})
endforeach()
endif()
endforeach()
if(DEFINED UPDATE)
set(UPDATE --update)
endif()
if(DEFINED NO_IMPORTS)
set(NO_IMPORTS --no-imports)
endif()
set(install_args install ${PATH_OR_REFERENCE} ${REFERENCE} ${UPDATE} ${NO_IMPORTS} ${REMOTE} ${LOCKFILE} ${LOCKFILE_OUT} ${LOCKFILE_NODE_ID} ${INSTALL_FOLDER}
${GENERATOR} ${BUILD} ${ENV} ${ENV_HOST} ${ENV_BUILD} ${OPTIONS} ${OPTIONS_HOST} ${OPTIONS_BUILD}
${PROFILE} ${PROFILE_HOST} ${PROFILE_BUILD} ${SETTINGS} ${SETTINGS_HOST} ${SETTINGS_BUILD})
string(REPLACE ";" " " _install_args "${install_args}")
message(STATUS "Conan executing: ${CONAN_CMD} ${_install_args}")
if(ARGS_OUTPUT_QUIET)
set(OUTPUT_OPT OUTPUT_QUIET)
endif()
if(ARGS_ERROR_QUIET)
set(ERROR_OPT ERROR_QUIET)
endif()
execute_process(COMMAND ${CONAN_CMD} ${install_args}
RESULT_VARIABLE return_code
${OUTPUT_OPT}
${ERROR_OPT}
WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR})
if(NOT "${return_code}" STREQUAL "0")
if (ARGS_ERROR_QUIET)
message(WARNING "Conan install failed='${return_code}'")
else()
message(FATAL_ERROR "Conan install failed='${return_code}'")
endif()
endif()
endfunction()
function(conan_cmake_setup_conanfile)
conan_parse_arguments(${ARGV})
if(ARGUMENTS_CONANFILE)
get_filename_component(_CONANFILE_NAME ${ARGUMENTS_CONANFILE} NAME)
# configure_file will make sure cmake re-runs when conanfile is updated
configure_file(${ARGUMENTS_CONANFILE} ${CMAKE_CURRENT_BINARY_DIR}/${_CONANFILE_NAME}.junk COPYONLY)
file(REMOVE ${CMAKE_CURRENT_BINARY_DIR}/${_CONANFILE_NAME}.junk)
else()
conan_cmake_generate_conanfile(ON ${ARGV})
endif()
endfunction()
function(conan_cmake_configure)
conan_cmake_generate_conanfile(OFF ${ARGV})
endfunction()
# Generate, writing in disk a conanfile.txt with the requires, options, and imports
# specified as arguments
# This will be considered as temporary file, generated in CMAKE_CURRENT_BINARY_DIR)
function(conan_cmake_generate_conanfile DEFAULT_GENERATOR)
conan_parse_arguments(${ARGV})
set(_FN "${CMAKE_CURRENT_BINARY_DIR}/conanfile.txt")
file(WRITE ${_FN} "")
if(DEFINED ARGUMENTS_REQUIRES)
file(APPEND ${_FN} "[requires]\n")
foreach(REQUIRE ${ARGUMENTS_REQUIRES})
file(APPEND ${_FN} ${REQUIRE} "\n")
endforeach()
endif()
if (DEFAULT_GENERATOR OR DEFINED ARGUMENTS_GENERATORS)
file(APPEND ${_FN} "[generators]\n")
if (DEFAULT_GENERATOR)
file(APPEND ${_FN} "cmake\n")
endif()
if (DEFINED ARGUMENTS_GENERATORS)
foreach(GENERATOR ${ARGUMENTS_GENERATORS})
file(APPEND ${_FN} ${GENERATOR} "\n")
endforeach()
endif()
endif()
if(DEFINED ARGUMENTS_BUILD_REQUIRES)
file(APPEND ${_FN} "[build_requires]\n")
foreach(BUILD_REQUIRE ${ARGUMENTS_BUILD_REQUIRES})
file(APPEND ${_FN} ${BUILD_REQUIRE} "\n")
endforeach()
endif()
if(DEFINED ARGUMENTS_IMPORTS)
file(APPEND ${_FN} "[imports]\n")
foreach(IMPORTS ${ARGUMENTS_IMPORTS})
file(APPEND ${_FN} ${IMPORTS} "\n")
endforeach()
endif()
if(DEFINED ARGUMENTS_OPTIONS)
file(APPEND ${_FN} "[options]\n")
foreach(OPTION ${ARGUMENTS_OPTIONS})
file(APPEND ${_FN} ${OPTION} "\n")
endforeach()
endif()
endfunction()
macro(conan_load_buildinfo)
if(CONAN_CMAKE_MULTI)
set(_CONANBUILDINFO conanbuildinfo_multi.cmake)
else()
set(_CONANBUILDINFO conanbuildinfo.cmake)
endif()
if(ARGUMENTS_INSTALL_FOLDER)
set(_CONANBUILDINFOFOLDER ${ARGUMENTS_INSTALL_FOLDER})
else()
set(_CONANBUILDINFOFOLDER ${CMAKE_CURRENT_BINARY_DIR})
endif()
# Checks for the existence of conanbuildinfo.cmake, and loads it
# important that it is macro, so variables defined at parent scope
if(EXISTS "${_CONANBUILDINFOFOLDER}/${_CONANBUILDINFO}")
message(STATUS "Conan: Loading ${_CONANBUILDINFO}")
include(${_CONANBUILDINFOFOLDER}/${_CONANBUILDINFO})
else()
message(FATAL_ERROR "${_CONANBUILDINFO} doesn't exist in ${CMAKE_CURRENT_BINARY_DIR}")
endif()
endmacro()
macro(conan_cmake_run)
conan_parse_arguments(${ARGV})
if(ARGUMENTS_CONFIGURATION_TYPES AND NOT CMAKE_CONFIGURATION_TYPES)
message(WARNING "CONFIGURATION_TYPES should only be specified for multi-configuration generators")
elseif(ARGUMENTS_CONFIGURATION_TYPES AND ARGUMENTS_BUILD_TYPE)
message(WARNING "CONFIGURATION_TYPES and BUILD_TYPE arguments should not be defined at the same time.")
endif()
if(CMAKE_CONFIGURATION_TYPES AND NOT CMAKE_BUILD_TYPE AND NOT CONAN_EXPORTED
AND NOT ARGUMENTS_BUILD_TYPE)
set(CONAN_CMAKE_MULTI ON)
if (NOT ARGUMENTS_CONFIGURATION_TYPES)
set(ARGUMENTS_CONFIGURATION_TYPES "Release;Debug")
endif()
message(STATUS "Conan: Using cmake-multi generator")
else()
set(CONAN_CMAKE_MULTI OFF)
endif()
if(NOT CONAN_EXPORTED)
conan_cmake_setup_conanfile(${ARGV})
if(CONAN_CMAKE_MULTI)
foreach(CMAKE_BUILD_TYPE ${ARGUMENTS_CONFIGURATION_TYPES})
set(ENV{CONAN_IMPORT_PATH} ${CMAKE_BUILD_TYPE})
conan_cmake_settings(settings ${ARGV})
old_conan_cmake_install(SETTINGS ${settings} ${ARGV})
endforeach()
set(CMAKE_BUILD_TYPE)
else()
conan_cmake_settings(settings