Warning, /frameworks/extra-cmake-modules/modules/ECMFindModuleHelpers.cmake is written in an unsupported language. File is not indexed.
0001 # SPDX-FileCopyrightText: 2014 Alex Merry <alex.merry@kde.org>
0002 #
0003 # SPDX-License-Identifier: BSD-3-Clause
0004
0005 #[=======================================================================[.rst:
0006 ECMFindModuleHelpers
0007 --------------------
0008
0009 Helper macros for find modules: ``ecm_find_package_version_check()``,
0010 ``ecm_find_package_parse_components()`` and
0011 ``ecm_find_package_handle_library_components()``.
0012
0013 ::
0014
0015 ecm_find_package_version_check(<name>)
0016
0017 Prints warnings if the CMake version or the project's required CMake version
0018 is older than that required by extra-cmake-modules.
0019
0020 ::
0021
0022 ecm_find_package_parse_components(<name>
0023 RESULT_VAR <variable>
0024 KNOWN_COMPONENTS <component1> [<component2> [...]]
0025 [SKIP_DEPENDENCY_HANDLING])
0026
0027 This macro will populate <variable> with a list of components found in
0028 <name>_FIND_COMPONENTS, after checking that all those components are in the
0029 list of ``KNOWN_COMPONENTS``; if there are any unknown components, it will print
0030 an error or warning (depending on the value of <name>_FIND_REQUIRED) and call
0031 ``return()``.
0032
0033 The order of components in <variable> is guaranteed to match the order they
0034 are listed in the ``KNOWN_COMPONENTS`` argument.
0035
0036 If ``SKIP_DEPENDENCY_HANDLING`` is not set, for each component the variable
0037 <name>_<component>_component_deps will be checked for dependent components.
0038 If <component> is listed in <name>_FIND_COMPONENTS, then all its (transitive)
0039 dependencies will also be added to <variable>.
0040
0041 ::
0042
0043 ecm_find_package_handle_library_components(<name>
0044 COMPONENTS <component> [<component> [...]]
0045 [SKIP_DEPENDENCY_HANDLING])
0046 [SKIP_PKG_CONFIG])
0047
0048 Creates an imported library target for each component. The operation of this
0049 macro depends on the presence of a number of CMake variables.
0050
0051 The <name>_<component>_lib variable should contain the name of this library,
0052 and <name>_<component>_header variable should contain the name of a header
0053 file associated with it (whatever relative path is normally passed to
0054 '#include'). <name>_<component>_header_subdir variable can be used to specify
0055 which subdirectory of the include path the headers will be found in.
0056 ``ecm_find_package_components()`` will then search for the library
0057 and include directory (creating appropriate cache variables) and create an
0058 imported library target named <name>::<component>.
0059
0060 Additional variables can be used to provide additional information:
0061
0062 If ``SKIP_PKG_CONFIG``, the <name>_<component>_pkg_config variable is set, and
0063 pkg-config is found, the pkg-config module given by
0064 <name>_<component>_pkg_config will be searched for and used to help locate the
0065 library and header file. It will also be used to set
0066 <name>_<component>_VERSION.
0067
0068 Note that if version information is found via pkg-config,
0069 <name>_<component>_FIND_VERSION can be set to require a particular version
0070 for each component.
0071
0072 If ``SKIP_DEPENDENCY_HANDLING`` is not set, the ``INTERFACE_LINK_LIBRARIES`` property
0073 of the imported target for <component> will be set to contain the imported
0074 targets for the components listed in <name>_<component>_component_deps.
0075 <component>_FOUND will also be set to ``FALSE`` if any of the components in
0076 <name>_<component>_component_deps are not found. This requires the components
0077 in <name>_<component>_component_deps to be listed before <component> in the
0078 ``COMPONENTS`` argument.
0079
0080 The following variables will be set:
0081
0082 ``<name>_TARGETS``
0083 the imported targets
0084 ``<name>_LIBRARIES``
0085 the found libraries
0086 ``<name>_INCLUDE_DIRS``
0087 the combined required include directories for the components
0088 ``<name>_DEFINITIONS``
0089 the "other" CFLAGS provided by pkg-config, if any
0090 ``<name>_VERSION``
0091 the value of ``<name>_<component>_VERSION`` for the first component that
0092 has this variable set (note that components are searched for in the order
0093 they are passed to the macro), although if it is already set, it will not
0094 be altered
0095
0096 .. note::
0097 These variables are never cleared, so if
0098 ``ecm_find_package_handle_library_components()`` is called multiple times with
0099 different components (typically because of multiple ``find_package()`` calls) then
0100 ``<name>_TARGETS``, for example, will contain all the targets found in any
0101 call (although no duplicates).
0102
0103 Since pre-1.0.0.
0104 #]=======================================================================]
0105
0106 macro(ecm_find_package_version_check module_name)
0107 if(CMAKE_VERSION VERSION_LESS 3.16.0)
0108 message(FATAL_ERROR "CMake 3.16.0 is required by Find${module_name}.cmake")
0109 endif()
0110 if(CMAKE_MINIMUM_REQUIRED_VERSION VERSION_LESS 3.16.0)
0111 message(AUTHOR_WARNING "Your project should require at least CMake 3.16.0 to use Find${module_name}.cmake")
0112 endif()
0113 endmacro()
0114
0115 macro(ecm_find_package_parse_components module_name)
0116 set(ecm_fppc_options SKIP_DEPENDENCY_HANDLING)
0117 set(ecm_fppc_oneValueArgs RESULT_VAR)
0118 set(ecm_fppc_multiValueArgs KNOWN_COMPONENTS DEFAULT_COMPONENTS)
0119 cmake_parse_arguments(ECM_FPPC "${ecm_fppc_options}" "${ecm_fppc_oneValueArgs}" "${ecm_fppc_multiValueArgs}" ${ARGN})
0120
0121 if(ECM_FPPC_UNPARSED_ARGUMENTS)
0122 message(FATAL_ERROR "Unexpected arguments to ecm_find_package_parse_components: ${ECM_FPPC_UNPARSED_ARGUMENTS}")
0123 endif()
0124 if(NOT ECM_FPPC_RESULT_VAR)
0125 message(FATAL_ERROR "Missing RESULT_VAR argument to ecm_find_package_parse_components")
0126 endif()
0127 if(NOT ECM_FPPC_KNOWN_COMPONENTS)
0128 message(FATAL_ERROR "Missing KNOWN_COMPONENTS argument to ecm_find_package_parse_components")
0129 endif()
0130 if(NOT ECM_FPPC_DEFAULT_COMPONENTS)
0131 set(ECM_FPPC_DEFAULT_COMPONENTS ${ECM_FPPC_KNOWN_COMPONENTS})
0132 endif()
0133
0134 if(${module_name}_FIND_COMPONENTS)
0135 set(ecm_fppc_requestedComps ${${module_name}_FIND_COMPONENTS})
0136
0137 if(NOT ECM_FPPC_SKIP_DEPENDENCY_HANDLING)
0138 # Make sure deps are included
0139 foreach(ecm_fppc_comp ${ecm_fppc_requestedComps})
0140 foreach(ecm_fppc_dep_comp ${${module_name}_${ecm_fppc_comp}_component_deps})
0141 list(FIND ecm_fppc_requestedComps "${ecm_fppc_dep_comp}" ecm_fppc_index)
0142 if("${ecm_fppc_index}" STREQUAL "-1")
0143 if(NOT ${module_name}_FIND_QUIETLY)
0144 message(STATUS "${module_name}: ${ecm_fppc_comp} requires ${${module_name}_${ecm_fppc_comp}_component_deps}")
0145 endif()
0146 list(APPEND ecm_fppc_requestedComps "${ecm_fppc_dep_comp}")
0147 endif()
0148 endforeach()
0149 endforeach()
0150 else()
0151 message(STATUS "Skipping dependency handling for ${module_name}")
0152 endif()
0153 list(REMOVE_DUPLICATES ecm_fppc_requestedComps)
0154
0155 # This makes sure components are listed in the same order as
0156 # KNOWN_COMPONENTS (potentially important for inter-dependencies)
0157 set(${ECM_FPPC_RESULT_VAR})
0158 foreach(ecm_fppc_comp ${ECM_FPPC_KNOWN_COMPONENTS})
0159 list(FIND ecm_fppc_requestedComps "${ecm_fppc_comp}" ecm_fppc_index)
0160 if(NOT "${ecm_fppc_index}" STREQUAL "-1")
0161 list(APPEND ${ECM_FPPC_RESULT_VAR} "${ecm_fppc_comp}")
0162 list(REMOVE_AT ecm_fppc_requestedComps ${ecm_fppc_index})
0163 endif()
0164 endforeach()
0165 # if there are any left, they are unknown components
0166 if(ecm_fppc_requestedComps)
0167 set(ecm_fppc_msgType STATUS)
0168 if(${module_name}_FIND_REQUIRED)
0169 set(ecm_fppc_msgType FATAL_ERROR)
0170 endif()
0171 if(NOT ${module_name}_FIND_QUIETLY)
0172 message(${ecm_fppc_msgType} "${module_name}: requested unknown components ${ecm_fppc_requestedComps}")
0173 endif()
0174 return()
0175 endif()
0176 else()
0177 set(${ECM_FPPC_RESULT_VAR} ${ECM_FPPC_DEFAULT_COMPONENTS})
0178 endif()
0179 endmacro()
0180
0181 macro(ecm_find_package_handle_library_components module_name)
0182 set(ecm_fpwc_options SKIP_PKG_CONFIG SKIP_DEPENDENCY_HANDLING)
0183 set(ecm_fpwc_oneValueArgs)
0184 set(ecm_fpwc_multiValueArgs COMPONENTS)
0185 cmake_parse_arguments(ECM_FPWC "${ecm_fpwc_options}" "${ecm_fpwc_oneValueArgs}" "${ecm_fpwc_multiValueArgs}" ${ARGN})
0186
0187 if(ECM_FPWC_UNPARSED_ARGUMENTS)
0188 message(FATAL_ERROR "Unexpected arguments to ecm_find_package_handle_components: ${ECM_FPWC_UNPARSED_ARGUMENTS}")
0189 endif()
0190 if(NOT ECM_FPWC_COMPONENTS)
0191 message(FATAL_ERROR "Missing COMPONENTS argument to ecm_find_package_handle_components")
0192 endif()
0193
0194 include(FindPackageHandleStandardArgs)
0195 find_package(PkgConfig QUIET)
0196 foreach(ecm_fpwc_comp ${ECM_FPWC_COMPONENTS})
0197 set(ecm_fpwc_dep_vars)
0198 set(ecm_fpwc_dep_targets)
0199 if(NOT SKIP_DEPENDENCY_HANDLING)
0200 foreach(ecm_fpwc_dep ${${module_name}_${ecm_fpwc_comp}_component_deps})
0201 list(APPEND ecm_fpwc_dep_vars "${module_name}_${ecm_fpwc_dep}_FOUND")
0202 list(APPEND ecm_fpwc_dep_targets "${module_name}::${ecm_fpwc_dep}")
0203 endforeach()
0204 endif()
0205
0206 if(NOT ECM_FPWC_SKIP_PKG_CONFIG AND ${module_name}_${ecm_fpwc_comp}_pkg_config)
0207 pkg_check_modules(PKG_${module_name}_${ecm_fpwc_comp} QUIET
0208 ${${module_name}_${ecm_fpwc_comp}_pkg_config})
0209 endif()
0210
0211 find_path(${module_name}_${ecm_fpwc_comp}_INCLUDE_DIR
0212 NAMES ${${module_name}_${ecm_fpwc_comp}_header}
0213 HINTS ${PKG_${module_name}_${ecm_fpwc_comp}_INCLUDE_DIRS}
0214 PATH_SUFFIXES ${${module_name}_${ecm_fpwc_comp}_header_subdir}
0215 )
0216 find_library(${module_name}_${ecm_fpwc_comp}_LIBRARY
0217 NAMES ${${module_name}_${ecm_fpwc_comp}_lib}
0218 HINTS ${PKG_${module_name}_${ecm_fpwc_comp}_LIBRARY_DIRS}
0219 )
0220
0221 set(${module_name}_${ecm_fpwc_comp}_VERSION "${PKG_${module_name}_${ecm_fpwc_comp}_VERSION}")
0222 if(NOT ${module_name}_VERSION)
0223 set(${module_name}_VERSION ${${module_name}_${ecm_fpwc_comp}_VERSION})
0224 endif()
0225
0226 set(FPHSA_NAME_MISMATCHED 1)
0227 find_package_handle_standard_args(${module_name}_${ecm_fpwc_comp}
0228 FOUND_VAR
0229 ${module_name}_${ecm_fpwc_comp}_FOUND
0230 REQUIRED_VARS
0231 ${module_name}_${ecm_fpwc_comp}_LIBRARY
0232 ${module_name}_${ecm_fpwc_comp}_INCLUDE_DIR
0233 ${ecm_fpwc_dep_vars}
0234 VERSION_VAR
0235 ${module_name}_${ecm_fpwc_comp}_VERSION
0236 )
0237 unset(FPHSA_NAME_MISMATCHED)
0238
0239 mark_as_advanced(
0240 ${module_name}_${ecm_fpwc_comp}_LIBRARY
0241 ${module_name}_${ecm_fpwc_comp}_INCLUDE_DIR
0242 )
0243
0244 if(${module_name}_${ecm_fpwc_comp}_FOUND)
0245 list(APPEND ${module_name}_LIBRARIES
0246 "${${module_name}_${ecm_fpwc_comp}_LIBRARY}")
0247 list(APPEND ${module_name}_INCLUDE_DIRS
0248 "${${module_name}_${ecm_fpwc_comp}_INCLUDE_DIR}")
0249 set(${module_name}_DEFINITIONS
0250 ${${module_name}_DEFINITIONS}
0251 ${PKG_${module_name}_${ecm_fpwc_comp}_DEFINITIONS})
0252 if(NOT TARGET ${module_name}::${ecm_fpwc_comp})
0253 add_library(${module_name}::${ecm_fpwc_comp} UNKNOWN IMPORTED)
0254 set_target_properties(${module_name}::${ecm_fpwc_comp} PROPERTIES
0255 IMPORTED_LOCATION "${${module_name}_${ecm_fpwc_comp}_LIBRARY}"
0256 INTERFACE_COMPILE_OPTIONS "${PKG_${module_name}_${ecm_fpwc_comp}_DEFINITIONS}"
0257 INTERFACE_INCLUDE_DIRECTORIES "${${module_name}_${ecm_fpwc_comp}_INCLUDE_DIR}"
0258 INTERFACE_LINK_LIBRARIES "${ecm_fpwc_dep_targets}"
0259 )
0260 endif()
0261 list(APPEND ${module_name}_TARGETS
0262 "${module_name}::${ecm_fpwc_comp}")
0263 endif()
0264 endforeach()
0265 if(${module_name}_LIBRARIES)
0266 list(REMOVE_DUPLICATES ${module_name}_LIBRARIES)
0267 endif()
0268 if(${module_name}_INCLUDE_DIRS)
0269 list(REMOVE_DUPLICATES ${module_name}_INCLUDE_DIRS)
0270 endif()
0271 if(${module_name}_DEFINITIONS)
0272 list(REMOVE_DUPLICATES ${module_name}_DEFINITIONS)
0273 endif()
0274 if(${module_name}_TARGETS)
0275 list(REMOVE_DUPLICATES ${module_name}_TARGETS)
0276 endif()
0277 endmacro()