考虑一个可以一次性构建为共享和静态库的库 frob
。这是 usually 通过两个仅在 STATIC
/ SHARED
上不同的库实现的(参见下面的设置详细信息)。为方便起见,我们添加了第三个接口库 (automatic
),专门用于根据 BUILD_SHARED_LIBS
选择正确的库版本。
这在构建项目本身时非常有效。但是该库也应该可以从安装中使用。在这种情况下,automatic
的自动检测不再起作用。这是因为标准是在已安装的项目中评估的,而不是在使用的项目中(Frob::automatic
对已安装的 static
中的 shared
或 FrobConfig.cmake
具有固定的依赖性}}).
问题:如何安装 Frob::automatic
s.t.它取决于 Frob::static
或 Frob::shared
取决于 BUILD_SHARED_LIBS
(消费项目)?换句话说,如何安装动态依赖(例如依赖于 BUILD_SHARED_LIBS
)?
让我们从 frob
的非常基本的库设置开始:
project(frob CXX)
# User configuration
option(FROB_BUILD_STATIC "Build statically linked library version." ON)
option(FROB_BUILD_SHARED "Build shared, dynamically linked library version." ON)
if (FROB_BUILD_STATIC)
add_library(frob-static STATIC ...)
set_target_properties(frob-static PROPERTIES EXPORT_NAME static)
add_library(Frob::static ALIAS frob-static)
endif()
if (FROB_BUILD_SHARED)
add_library(frob-shared SHARED ...)
set_target_properties(frob-shared PROPERTIES EXPORT_NAME shared)
add_library(Frob::shared ALIAS frob-shared)
endif()
# For convenience, we provide an interface library to automagically select the right version
# (depending on build setup and `BUILD_SHARED_LIBS`)
add_library(frob-automatic INTERFACE)
if (FROB_BUILD_SHARED AND (BUILD_SHARED_LIBS OR NOT FROB_BUILD_STATIC))
target_link_libraries(frob-automatic INTERFACE frob-shared)
else ()
target_link_libraries(frob-automatic INTERFACE frob-static)
endif ()
add_library(Frob::automatic ALIAS frob-automatic)
set_target_properties(frob-automatic PROPERTIES EXPORT_NAME automatic)
# Furthermore `frob` should be installable:
if(CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR)
include(GNUInstallDirs)
# [...] meta data
install(
TARGETS frob-shared frob-static frob-automatic
EXPORT frob
INCLUDES DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
)
install(
EXPORT frob
FILE FrobConfig.cmake
DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Frob
NAMESPACE Frob::
)
include(CPack)
endif()
考虑消费项目 consume
project(consume CXX)
set(BUILD_SHARED_LIBS OFF)
add_executable(auto Automatic.cpp)
target_link_libraries(auto Frob::automatic)
上面的问题是如何安装frob
s.t. BUILD_SHARED_LIBS
-ing 项目中 consume
的配置控制 auto
是链接到 Frob::static
还是 Frob::shared
。
答案 0 :(得分:0)
诀窍是不安装 automatic
,而是通过额外的间接层提供它。以下是 frob
的更新项目详情:
# [...] as above
if(CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR)
include(GNUInstallDirs)
# [...] meta data
install(
TARGETS frob-shared frob-static # no frob-automatic any more
EXPORT frob
INCLUDES DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
)
install(
EXPORT frob
FILE FrobConfigGenerated.cmake # new Generated suffix
DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Frob
NAMESPACE Frob::
)
# Here's the new layer of indirection.
install(
FILES FrobConfig.cmake
DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/Frob
)
include(CPack)
endif()
新的 FrobConfig.cmake
包含的位置
# Import central (generated) configuration details.
get_filename_component(_DIR "${CMAKE_CURRENT_LIST_FILE}" PATH)
include(${_DIR}/FrobConfigGenerated.cmake)
# Introduce automatic aliases
if (BUILD_SHARED_LIBS)
add_library(Frob::automatic ALIAS Frob::shared)
else ()
add_library(Frob::automatic ALIAS Frob::static)
endif ()
当消费项目(即在 find_package(Frob)
之后)链接到 Frob::automatic
时,根据 Frob::shared
引用 Frob::static
/ BUILD_SHARED_LIBS
。