Spec-Zone.ru › CMake 3.27

CMakePackageConfigHelpers

Функции-помощники для создания конфигурационных файлов, которые могут быть включены другими проектами для поиска и использования пакета.

Добавляет команды configure_package_config_file() и write_basic_package_version_file().

Генерация файла конфигурации пакета

configure_package_config_file

Создайте конфигурационный файл для проекта:

configure_package_config_file(<input> <output>
  INSTALL_DESTINATION <path>
  [PATH_VARS <var1> <var2> ... <varN>]
  [NO_SET_AND_CHECK_MACRO]
  [NO_CHECK_REQUIRED_COMPONENTS_MACRO]
  [INSTALL_PREFIX <path>]
  )

Следует использовать configure_package_config_file(), а не обычную команду configure_file(), при создании файла <PackageName>Config.cmake или <PackageName>-config.cmake для установки проекта или библиотеки. Это помогает сделать релоцируемым получившийся пакет, избегая жёстко заданных путей в установленных файлах Config.cmake.

В файле FooConfig.cmake может быть код, подобный этому, чтобы сделать известными целевые места установки использующему проекту:

set(FOO_INCLUDE_DIR   "@CMAKE_INSTALL_FULL_INCLUDEDIR@" )
set(FOO_DATA_DIR   "@CMAKE_INSTALL_PREFIX@/@RELATIVE_DATA_INSTALL_DIR@" )
set(FOO_ICONS_DIR   "@CMAKE_INSTALL_PREFIX@/share/icons" )
#...logic to determine installedPrefix from the own location...
set(FOO_CONFIG_DIR  "${installedPrefix}/@CONFIG_INSTALL_DIR@" )

Все 4 представленных варианта недостаточно эффективны, так как первые 3 жёстко фиксируют абсолютные расположения каталогов, а четвёртый работает только если логика определения installedPrefix верна, и если CONFIG_INSTALL_DIR содержит относительный путь, что в общем случае гарантировать нельзя. В результате получившийся файл FooConfig.cmake будет плохо работать в Windows и OSX, где пользователи привыкли выбирать место установки бинарного пакета во время установки, независимо от того, как был установлен CMAKE_INSTALL_PREFIX при построении/cmake.

Использование configure_package_config_file помогает. При правильном использовании, это делает получившийся файл FooConfig.cmake релоцируемым. Использование:

  1. Напишите файл FooConfig.cmake.in, как вы привыкли
  2. Вставьте строку, содержащую только строку @PACKAGE_INIT@
  3. Вместо set(FOO_DIR "@SOME_INSTALL_DIR@"), используйте set(FOO_DIR "@PACKAGE_SOME_INSTALL_DIR@") (это должно следовать за строкой @PACKAGE_INIT@)
  4. Вместо обычной configure_file() используйте configure_package_config_file()

Аргументы <input> и <output> — входной и выходной файлы, так же, как и в configure_file().

<path> переданный в INSTALL_DESTINATION должен быть местом назначения, куда будет установлен файл FooConfig.cmake. Этот путь может быть абсолютным или относительным к пути INSTALL_PREFIX.

Переменные <var1> до <varN>, переданные как PATH_VARS, являются переменными, содержащими места установки. Для каждой из них макрос создаст вспомогательную переменную PACKAGE_<var...>. Эти вспомогательные переменные должны использоваться в файле FooConfig.cmake.in для установки места установки. Они вычисляются макросом configure_package_config_file, чтобы они всегда были относительны к месту установки пакета. Это работает как для относительных, так и для абсолютных путей. Для абсолютных путей это работает только если абсолютный путь является подкаталогом INSTALL_PREFIX.

Новое в версии 3.1: Если передан аргумент INSTALL_PREFIX, он используется в качестве базового пути для вычисления всех относительных путей. Аргумент <path> должен быть абсолютным путём. Если этот аргумент не передан, используется переменная CMAKE_INSTALL_PREFIX. Значение по умолчанию хорошо подходит при генерации файла FooConfig.cmake для использования пакета из дерева установки. При генерации файла FooConfig.cmake для использования пакета из дерева сборки следует использовать этот параметр.

По умолчанию configure_package_config_file также генерирует в файл FooConfig.cmake два вспомогательных макроса set_and_check() и check_required_components().

set_and_check() должен использоваться вместо обычной команды set() для установки каталогов и местоположений файлов. Помимо установки переменной, он также проверяет, что указанный файл или каталог действительно существуют, и выдает ошибку в противном случае. Это гарантирует, что созданный файл FooConfig.cmake не содержит неверных ссылок. При использовании NO_SET_AND_CHECK_MACRO, этот макрос не генерируется в файл FooConfig.cmake.

check_required_components(<PackageName>) должен вызываться в конце файла FooConfig.cmake . Этот макрос проверяет, были ли найдены все запрошенные, не опциональные компоненты, и если это не так, устанавливает переменную Foo_FOUND в FALSE, чтобы пакет считался не найденным. Он делает это, тестируя переменные Foo_<Component>_FOUND для всех запрошенных необходимых компонентов. Этот макрос следует вызывать, даже если пакет не предоставляет никаких компонентов, чтобы убедиться, что пользователи не указывают компоненты ошибочно. При использовании параметра NO_CHECK_REQUIRED_COMPONENTS_MACRO, этот макрос не генерируется в файл FooConfig.cmake.

Пример смотрите в документации для write_basic_package_version_file().

Генерация файла версии пакета

write_basic_package_version_file

Создайте файл версии для проекта:

write_basic_package_version_file(<filename>
  [VERSION <major.minor.patch>]
  COMPATIBILITY <AnyNewerVersion|SameMajorVersion|SameMinorVersion|ExactVersion>
  [ARCH_INDEPENDENT] )

Создаёт файл для использования в качестве файла <PackageName>ConfigVersion.cmake в <filename>. Подробности см. в документации для find_package().

<filename> — имя выходного файла, он должен находиться в дереве сборки. <major.minor.patch> — номер версии устанавливаемого проекта.

Если VERSION не задан, используется переменная PROJECT_VERSION. Если она не установлена, возникает ошибка.

Режим COMPATIBILITY AnyNewerVersion означает, что установленная версия пакета будет считаться совместимой, если она новее или точно такая же, как запрошенная версия. Этот режим следует использовать для пакетов, которые полностью совместимы, также и между версиями основных релизов. Если используется SameMajorVersion, поведение отличается от AnyNewerVersion тем, что номер основной версии должен совпадать с запрошенным, например, версия 2.0 не будет считаться совместимой, если запрошена версия 1.0. Этот режим следует использовать для пакетов, гарантирующих обратную совместимость в рамках одной основной версии. Если используется SameMinorVersion, поведение аналогично SameMajorVersion, но должны совпадать и главная, и второстепенная версия, например версия 0.2 не будет считаться совместимой при запросе версии 0.1. Если используется ExactVersion, пакет считается совместимым только если запрошенная версия точно соответствует собственной версии пакета (не учитывая версию с поправками). Например, версия 1.2.3 пакета считается совместимой только с запрошенной версией 1.2.3. Этот режим предназначен для пакетов без гарантий совместимости. Если ваш проект имеет более сложные правила сопоставления версий, вам потребуется написать собственный пользовательский файл ConfigVersion.cmake вместо использования этого макроса.

Новое в версии 3.11: Режим совместимости SameMinorVersion.

Новое в версии 3.14: Если передан ARCH_INDEPENDENT, установленная версия пакета будет считаться совместимой, даже если она была скомпилирована для другого архитектурного типа, чем запрошенный. В противном случае будет выполнена проверка архитектуры, и пакет будет считаться совместимым только если архитектура совпадёт точно. Например, если пакет скомпилирован для 32-битной архитектуры, пакет считается совместимым только если он используется на 32-битной архитектуре, если не передан ARCH_INDEPENDENT, в этом случае пакет считается совместимым с любой архитектурой.

Примечание

ARCH_INDEPENDENT предназначен для библиотек только с заголовками или аналогичных пакетов без бинарных файлов.

Новое в версии 3.19: Файл версии, сгенерированный аргументами AnyNewerVersion, SameMajorVersion и SameMinorVersion команды COMPATIBILITY обрабатывают диапазон версий, если он указан (см. команду find_package() для получения подробностей). Режим ExactVersion несовместим с диапазонами версий и выведет предупреждение разработчика, если такой диапазон указан.

Внутренне, этот макрос выполняет configure_file() для создания получившегося файла версии. В зависимости от COMPATIBILITY, используется соответствующий файл BasicConfigVersion-<COMPATIBILITY>.cmake.in . Обратите внимание, что эти файлы являются внутренними для CMake и вы не должны вызывать configure_file() на них самостоятельно, но они могут быть использованы в качестве отправной точки для создания более сложных пользовательских файлов ConfigVersion.cmake.

Пример генерации файлов пакета

Пример использования как configure_package_config_file(), так и write_basic_package_version_file():

CMakeLists.txt:

include(GNUInstallDirs)
set(INCLUDE_INSTALL_DIR ${CMAKE_INSTALL_INCLUDEDIR}/Foo
    CACHE PATH "Location of header files" )
set(SYSCONFIG_INSTALL_DIR ${CMAKE_INSTALL_SYSCONFDIR}/foo
    CACHE PATH "Location of configuration files" )
#...
include(CMakePackageConfigHelpers)
configure_package_config_file(FooConfig.cmake.in
  ${CMAKE_CURRENT_BINARY_DIR}/FooConfig.cmake
  INSTALL_DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Foo
  PATH_VARS INCLUDE_INSTALL_DIR SYSCONFIG_INSTALL_DIR)
write_basic_package_version_file(
  ${CMAKE_CURRENT_BINARY_DIR}/FooConfigVersion.cmake
  VERSION 1.2.3
  COMPATIBILITY SameMajorVersion )
install(FILES ${CMAKE_CURRENT_BINARY_DIR}/FooConfig.cmake
              ${CMAKE_CURRENT_BINARY_DIR}/FooConfigVersion.cmake
        DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Foo )

FooConfig.cmake.in:

set(FOO_VERSION x.y.z)
...
@PACKAGE_INIT@
...
set_and_check(FOO_INCLUDE_DIR "@PACKAGE_INCLUDE_INSTALL_DIR@")
set_and_check(FOO_SYSCONFIG_DIR "@PACKAGE_SYSCONFIG_INSTALL_DIR@")

check_required_components(Foo)

© 2000–2024 Kitware, Inc. and Contributors
Licensed under the BSD 3-clause License.
https://cmake.org/cmake/help/v3.27/module/CMakePackageConfigHelpers.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API