如何解决CMake子目录包含问题
我有一个结构如下的项目:
.
├── CMakeLists.txt
├── src
│ └── temp.cpp
└── thirdparty
├── build
├── CMakeLists.txt
├── include
│ └── thirdparty.h
└── src
└── thirdparty.cpp
CMakeLists.txt
文件夹中的thirdparty
文件如下:
cmake_minimum_required(VERSION 3.10)
project(thirdparty LANGUAGES CXX VERSION 0.0.1)
add_library(thirdparty SHARED "${PROJECT_SOURCE_DIR}/src/thirdparty.cpp")
target_include_directories(thirdparty PRIVATE "${PROJECT_SOURCE_DIR}/include/")
项目根目录下的CMakeLists.txt
文件如下:
cmake_minimum_required(VERSION 3.10)
project(temp LANGUAGES CXX VERSION 0.0.1)
add_subdirectory("${PROJECT_SOURCE_DIR}/thirdparty"
"${PROJECT_SOURCE_DIR}/thirdparty/build"
EXCLUDE_FROM_ALL)
#include_directories ("${PROJECT_SOURCE_DIR}/thirdparty/include")
add_executable(temp "${PROJECT_SOURCE_DIR}/src/temp.cpp")
target_link_libraries(temp PRIVATE thirdparty)
问题出在试图包括thirdparty
库中的头文件:
.../temp/src/temp.cpp:1:10: fatal error: thirdparty.h: No such file or directory
target_include_directories(thirdparty PRIVATE "${PROJECT_SOURCE_DIR}/include/")
指令在thirdparty
库中可以正常工作。但是,add_subdirectory
命令未显示标头包含路径。相反,只要我执行libthirdparty.so
和add_subdirectory
,target_link_libraries(temp PRIVATE thirdparty)
文件生成的链接就可以了。
如果我取消对根#include_directories ("${PROJECT_SOURCE_DIR}/thirdparty/include")
中的CMakeLists.txt
行的注释,那么整个过程将正常工作,但是我不想使用全局include指令。
是否可以通过仅修改thirdparty
中的CMakeLists.txt
(以及根中的thirdpary
和add_subdirectory
)使target_link_libraries
标头可见?
解决方法
您必须在thirdparty
内建的库中提供包含目录PUBLIC或INTERFACE,然后使用目标名称(而不是文件)链接到该库名称等)。这将利用cmake的目标属性系统。问题是您获得的thirdparty
项目可能已过时(cmake 2.8样式或类似样式),因此可能无法正确支持此项目。通常情况下,“第三方”项目CMakeList会被巧妙地破坏,从而使其在多模块项目中变得毫无用处,因此必须进行更改或直接重写。
在任何情况下,您都不需要任何显式的include目录指令等。仅与子目录中生成的库目标链接就足以使cmake根据需要引入所有PUBLIC和INTERFACE依赖项。这就是使cmake“理智”的机制。 您不应该使用任何变量,例如FOOBAR_LIBRARY_INCLUDES等-这是古老的东西,在任何现代cmake项目中都完全不合时宜,就现代而言,我指的是至少过去5年以上的任何东西。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。