我有一组库和可执行文件都有自己的CMakeLists.txt。所有库都将目标构建到同一路径(例如../build/bin
和../build/lib
)...以及导出其头文件(../build/inc
)。
现在我希望构建一个构建系统,让CMake找出依赖关系(使用add_subdirectory
和全局构建设置)。
问题是:所有库在构建之后(在调用build/inc
时)都会将其标头导出到make install
。当我执行整个系统时,直到结束之后才会调用make install
(并且所有内容都已构建)。因此,例如progfoo
与target_link_libraries( progfoo onelib )
的可执行文件将失败,因为CMake将依赖关系计算为onelib
(构建正常),但progfoo
失败,因为它在build/inc
中查找标头{1}} ...尚未导出。同样的事情通常适用于许多图书馆。
处理这些案件的正确CMake方式是什么?谢谢!
答案 0 :(得分:1)
安装是最后一步,即应该对用户可见的步骤。因此,当您导出二进制文件和标题时,您应该已经在原始位置中针对标题构建了二进制文件。
从CMake的角度来看,您一次只有1个目标。例如,您可以构建Web服务器并使用依赖项libcurl
和boost::asio
。使用add_subdirectory
将依赖项添加到当前目标是非常可能的(并且很好),但是当您必须添加包含目录时,您必须基于每个依赖项执行此操作,在示例中如果每个都是方便的依赖项已经提供了一个带有当前包含的绝对路径的变量。
在示例中,请参阅设置绝对包含目录的路径的虚拟 libcurl的CMakeLists.txt
get_filename_component(_DIR "${CMAKE_CURRENT_LIST_FILE}" PATH)
// export into parent scope libcurl header location
set (LIBCURL_INCLUDES ${_DIR}/include PARENT_SCOPE)
然后您可以使用 Web服务器的CMakeLists.txt 进行构建,稍后再次使用相同的路径来提取文件以便在需要时安装它们
add_subdirectory(PATH_TO_LIBCURL_CMAKELISTS)
# add include directories for building web server
include_directories( ${LIBCURL_INCLUDES})
#I assume you are installing headers because final user will need them,
#in case you needed them just for building you are already done here
#without even installing them
#gather headers list
file(GLOB libCurlHeadersList
"${LIBCURL_INCLUDES}/*.h"
"${LIBCURL_INCLUDES}/*.hpp"
)
#install header list
install( FILES
${libCurlHeadersList}
DESTINATION ../build/inc/libcurl
)