CMake - заставить find_package обновлять переменные кэша

В моем проекте CMake я предоставляю по умолчанию путь к Boost, редактируемый пользователем.

set(PATH_BOOST_DEFAULT "/softs/boost/${BOOST_VER}/${ARCH}/gcc/${GCCVER}")
set(PATH_BOOST "${PATH_BOOST_DEFAULT}" CACHE PATH "Default path to Boost")

После этого я пытаюсь найти libs с:

set(BOOST_ROOT "${PATH_BOOST}")
set(Boost_USE_MULTITHREAD ON)
set(Boost_USE_STATIC_LIBS ON)
find_package(Boost 1.53.0 REQUIRED COMPONENTS thread system)

Это работает отлично, и генерируется много переменных кэша, таких как Boost_INCLUDE_DIR, Boost_LIBRARY_DIRS или Boost_THREAD_LIBRARY_DEBUG.

Моя проблема возникает, когда я пытаюсь изменить переменную кеша PATH_BOOST: переменные кэша, созданные FindBoost.cmake, не обновляются. Сценарий FindBoost.cmake кажется, снова вызван (он печатает сообщения о найденных компонентах). Я думаю, что переменные типа Boost_INCLUDE_DIR не обновляются, поскольку они находятся в кеше.

Есть ли способ сказать cmake "если путь изменен пользователем, переустановите пакет, заставив переменные кэша"?

Кроме того, существует ли более удобный способ определения переменной кэша, только что измененной, чем следующая уродливая идея? : -/

set(MY_VAR ${MY_VAR_DEFAULT} CACHE TYPE "")
if(NOT DEFINED MY_VAR_copy)
  set(MY_VAR_copy ${MY_VAR} CACHE INTERNAL "")
  mark_as_advanced(FORCE MY_VAR_copy)
endif()
if(NOT "${MY_VAR}" STREQUAL "${MY_VAR_copy}")
  # my_var is modified : do something
  set(MY_VAR_copy ${MY_VAR} CACHE INTERNAL "")
endif()

Ответ 1

Я думаю, у меня такая же проблема, как и вы. Моя установка пытается найти определенную версию пакета:

set (MYPACK_REQUIRED_VERSION 1.2.3)
find_package (mypack ${MYPACK_REQUIRED_VERSION} EXACT)

В сценарии конфигурации пакета MYPACK_LIBRARIES кешированная переменная MYPACK_LIBRARIES которая затем используется на более позднем этапе. Однако, когда я MYPACK_REQUIRED_VERSION переменную MYPACK_REQUIRED_VERSION cmake по-прежнему использует старые MYPACK_LIBRARIES вместо того, чтобы искать новую версию.

Я думаю, что я решил проблему сейчас, отключив эту переменную кэша:

set (MYPACK_REQUIRED_VERSION 1.2.3)
unset (MYPACK_LIBRARIES CACHE)
find_package (mypack ${MYPACK_REQUIRED_VERSION} EXACT)

Это, похоже, снова вызовет процедуру find_package в моем случае. Есть некоторые более тонкие детали процедуры find_package, которые я не совсем понимаю, поэтому это может не работать в вашем случае, но, возможно, стоит попробовать.