CMake include header-only-library into another library, make fail

Viewed 39

I have the following folder structure:

- lib/
    -libA/
        -include/
            - libA.h
        -src/
            - libA.cpp
        -CMakeLists.txt (1)
    -libB/
        -headerB1.h
        -headerB2.h
        -headerBx.h
        -CMakeLists.txt (2)
 - src/
    -main.cpp
 - CMakeLists.txt (3)

in libA.h I try to include one of the header files from libB. In this case that would be headerB1.h by doing

#include <headerB1.h>

But unfortunately, I get the following error in cmake: fatal error C1083: cannot open include file: 'headerB1.h': No such file or directory from the libA.h file.

I have the following CMake contents: /CMakeLists.txt (3)

cmake_minimum_required(VERSION 3.10)

project(project)

set(CMAKE_CXX_STANDARD 11)
set(CMAKE_CXX_STANDARD_REQUIRED True)

set(SOURCES 
    src/main.cpp
)

add_executable(${PROJECT_NAME} ${SOURCES})

add_subdirectory("lib/libA")
add_subdirectory("lib/libB")

target_link_libraries(${PROJECT_NAME} PUBLIC libA)
target_link_libraries(${PROJECT_NAME} PUBLIC libB)

lib/libA/CMakeLists.txt (1)

add_library(libA STATIC)

target_sources(libA PRIVATE src/libA.cpp)
target_include_directories(libA
    PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/include
    PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/src
)

lib/libB/CMakeLists.txt (2)

add_library(libB INTERFACE)
target_include_directories(libB INTERFACE ${CMAKE_CURRENT_SOURCE_DIR})

library B (libB) is a header only library in my view (correct me if I'm using the incorrect terms). So libA actually 'uses' libB but somehow, adding or creating libB is not executed as I thought it would. What are my misconceptions here and how can I solve it?

main.cpp:

#include <libA.h> //This works!

int main(void) {
    //do something with libA class / functions
}

libA.h:

#include <headerB1.h> //This causes the cmake (mingw32-make.exe) error

I use:

  • cmake
  • vscode
  • mingw32-make

I actually did take a look at: CMake include library in another library But making my CMakeLists (1) like the following code did not work for me unfortunately. Or, again, I have misunderstood the solution.

add_library(libA SHARED)

target_sources(libA PRIVATE src/libA.cpp)
target_include_directories(libA
    PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/include
    PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/src
)
target_link_libraries(libA PRIVATE libB)
target_include_directories(libA PUBLIC ${CMAKE_ROOT}/lib/libB)
1 Answers

Ok, this was actually pretty straightforward for a solution but it does make sense that libB would have to be compiled first because libA makes use of it.

So, in CMakeLists.txt (3) I have switched the two following lines:

add_subdirectory("lib/libA")
add_subdirectory("lib/libB")

to

add_subdirectory("lib/libB")
add_subdirectory("lib/libA")

And I also made sure to have added the following code snippet like suggested in the other stackoverflow question, to the libA CMakeLists.txt (1). CMake include library in another library

target_link_libraries(libA PRIVATE libB)
target_include_directories(libA PUBLIC ${CMAKE_ROOT}/lib/libB)

Now, all compiles as expected without errors.

Related