Cmake include_directories()
Это мое дерево проектов:
project
| + src
| + external
| | + foo
| | | + include
| | | | - foo.hpp
| | | + src
| | | | - foo.cpp
| | | | - CMakeLists.txt
| | | - CMakeLists.txt
| | + CMakeLists.txt
| + src
| | - main.cpp
| - CMakeLists.txt
foo.cpp включает foo.hpp:
// foo.cpp
#include "foo.hpp"
Теперь проблема заключается в том, что включение каталога в верхнем CMake успешно находит foo.hpp,
но если я включу в подпроект, это не так. Любые причины для этого? (каталоги включены до компиляции исполняемого файла).
// project/CMakeLists.txt
include_directories(external/foo/include) //OK
add_subdirectory(external)
add_executable(main main.cpp)
target_link_libraries(main foo)
// project/external/CMakeLists.txt
add_subdirectory(foo)
// project/external/foo/CMakeLists.txt
include_directories(include) // NOT WORKING
add_subdirectory(src)
// project/external/foo/src/CMakeLists.txt
add_library(foo foo.cpp)
Ответы
Ответ 1
Указание документации для include_directories
:
Каталоги include добавляются в свойство каталога INCLUDE_DIRECTORIES для текущего файла CMakeLists. Они также добавлено к целевому свойству INCLUDE_DIRECTORIES для каждой цели в текущий файл CMakeLists. Значения целевых свойств являются значениями используемые генераторами.
include_directories
свойство каталога наследуется ко всем подкаталогам и всем целям в каталоге.
- Указание
${CMAKE_CURRENT_SOURCE_DIR}
для include_directories
избыточно, поскольку относительные пути интерпретируются как относительные по отношению к этому каталогу по умолчанию. Вы должны выбросить его, чтобы повысить удобочитаемость.
- Указание каталога include как в подкаталоге, так и в его родительском элементе является избыточным. Вам следует избегать этого и поселиться в одном месте.
- Используйте
get_property
и message
, чтобы дважды проверьте, что все каталоги и целевые объекты содержат правильные записи в свойстве include_directories
.
- Если вы свободны требовать CMake 2.8.11 в качестве минимального требования, рассмотрите полностью отказаться от
include_directories
и вместо этого используйте target_include_directories
. Это имеет то преимущество, что включение зависимостей разрешается исключительно на основе каждой цели, что обычно является более желательным.
Ответ 2
Это может быть проблема с областью. Я чувствую, что вы пытаетесь сделать здесь, это распространять настройки с /project/external/foo/CMakeLists
на /project/CMakeLists
и таким образом, чтобы этот параметр можно было распространить на /project/src/CMakeLists
. Но, к сожалению, распространение с CMakeLists более низкого уровня на более высокий уровень невозможно в cmake, за исключением кешированных значений. Это означает, что вам также необходимо добавить include_directories (${CMAKE_SOURCE_DIR}/external/foo/include
) в /project/src/CMakeLists.txt
. Или, как вы уже это сделали, вы можете просто добавить эту строку в CMakeLists верхнего уровня.