简体   繁体   中英

Include header files from static library with CMake

I have a problem building a CMake project with a static library. My project strucutre looks like that:

Foo/
|-- CMakeLists.txt
|-- lib/
    |-- CMakeLists.txt
    |-- libA/
        |-- CMakeLists.txt
        |-- libA.cpp
        |-- libA.h
        |-- libAB.h
|-- src/
    |-- CMakeLists.txt
    |-- main.cpp
    |-- srcDirA/
        |-- CMakeLists.txt
        |-- srcA.h
    |-- srcDirB/
        |-- CMakeLists.txt
        |-- srcB.cpp
        |-- srcB.h

And the */CMakeLists.txt look like that:

Foo/CMakeLists.txt:

cmake_minimum_required(VERSION 3.5.1)
project(FOO)

set(CMAKE_CXX_STANDARD 11)

add_subdirectory(lib)
add_subdirectory(src)

Foo/lib/CMakeLists.txt:

add_subdirectory(libA)

Foo/lib/libA/CMakeLists.txt:

add_library (staticLibA STATIC libA.cpp)

Foo/src/CMakeLists.txt:

add_subdirectory(srcDirA)
add_subdirectory(srcDirB)
include_directories(".")

add_executable(foo main.cpp)
target_link_libraries(foo LINK_PUBLIC libA)

Foo/src/srcDirA/CMakeLists.txt is empty

Foo/src/srcDirB/CMakeLists.txt is empty

Now I am trying to include the header from my static library into my main project like this:

Foo/src/main.cpp:

#include "srcDirB/srcB.h"
#include "libA/libA.h"  

int main() {
   //...
   return 0;
}

If I try to build this with CMake, libA is generated but I am getting a fatal error:

libA/libA.h: No such file or directory.

Does anyone know what I am doing wrong? Do I have to create a ProjectConfig.cmake file ?

You don't need to create any Config files; these are for importing 3rd-party projects.

Since you're using CMake >= 3.5.1, you can esaily specify usage requirements for your libraries. Usage requirements are things like flags or include directories which clients need to build with the library.

So in Foo/lib/libA/CMakeLists.txt:, you'll do this:

add_library (staticLibA STATIC libA.cpp)
target_include_directories(staticLibA INTERFACE ${CMAKE_CURRENT_SOURCE_DIR}/..)

Or, if you want the same include directory to apply to libA itself (which is likely), use PUBLIC instead of INTERFACE .

That's all you really need to do. However, given the modern CMake you're using, you should replace your use of the legacy keyword LINK_PUBLIC with its modern equivalent PUBLIC .

Also, since you mention both CMakeLists in .../srcDir* are empty, why have them there in the first place? You can easily get rid of both them and the related add_subdirectory calls.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM