8

I have one project that produces a library:

project (myCoolLibrary) ADD_LIBRARY(my_cool_library SHARED ${mysources_SRC}) 

And another project that should be using this library:

find_package (myCoolLibrary REQUIRED) INCLUDE_DIRECTORIES("${myCoolLibrary_INCLUDE_DIRS}" ) add_executable(myCoolExe ${my_sources_SRC} ) TARGET_LINK_LIBRARIES(myCoolExe ${myCoolLibrary_LIBRARIES} ) 

Is there a way that I can change the first file so that the second file works automatically? That by running CMake on the first file and then running make on the output, then running CMake on the second file, CMake is able to find the package?

An answer where I just give the address of where the first project is built to the second package is also acceptable.

6
  • 1
    Something like this CMake tutorial on how to make a ProjectConfig.cmake file? Commented Nov 1, 2015 at 13:36
  • 2
    DevSolar, I had read that article. To be honest I found it a bit too complex for my liking. I was hoping for a simpler method. Also, if I am right, I would have to run "make install" for it to work, although that would make sense. Commented Nov 1, 2015 at 14:22
  • 1
    The same article points to another article as a newer solution. I will try this and see what happens. Commented Nov 1, 2015 at 15:47
  • 1
    Just a hint: a more compact description can be found in a blog post by daniperez: Use CMake-enabled libraries in your CMake project (III). Commented Nov 2, 2015 at 8:39
  • @Florian this was the one that finally worked, and this was the one that I wanted. I'll have to fix the question to correctly reflect what I wanted. Also if you write a solution I'll flag it as the answer, if not I'll do it myself in a few days. Thanks. Commented Nov 6, 2015 at 9:53

1 Answer 1

4

Taking the code found in a blog post by @daniperez - Use CMake-enabled libraries in your CMake project (III) - I've come up with the following minimal solution:

myCoolLibrary/CMakeLists.txt

cmake_minimum_required(VERSION 3.3) project(myCoolLibrary) function(my_export_target _target _include_dir) file( WRITE "${CMAKE_CURRENT_BINARY_DIR}/${_target}Config.cmake" " include(\"\$\{CMAKE_CURRENT_LIST_DIR\}/${_target}Targets.cmake\") set_property( TARGET ${_target} APPEND PROPERTY INTERFACE_INCLUDE_DIRECTORIES \"${_include_dir}\" ) " ) export(TARGETS ${_target} FILE "${CMAKE_CURRENT_BINARY_DIR}/${_target}Targets.cmake") # NOTE: The following call can pollute your PC's CMake package registry # See comments/alternatives below export(PACKAGE ${_target}) endfunction(my_export_target) ... add_library(${PROJECT_NAME} SHARED ${mysources_SRC}) my_export_target(${PROJECT_NAME} "${CMAKE_CURRENT_SOURCE_DIR}") 

myCoolExe/CMakeLists.txt

cmake_minimum_required(VERSION 3.3) project(myCoolExe) find_package(myCoolLibrary REQUIRED) ... add_executable(${PROJECT_NAME} ${my_sources_SRC}) target_link_libraries(${PROJECT_NAME} myCoolLibrary) 

To make it reusable I have packed everything into my_export_target(). And I'm friend of self-propagating properties like INTERFACE_INCLUDE_DIRECTORIES.

As commented by @ruslo, using export(PACKAGE ...) can pollute your package registry. So alternatively you can:

  1. Write the target configuration files directly to some dedicated place specific for a certain toolchain

    See e.g. How to install your custom CMake-Find module and 0003659: FIND_PACKAGE command improvements.

  2. Set CMAKE_MODULE_PATH via the second project's CMake command line (injecting the search path(s) from the outside). If you are building the two projects anyway with a build script, then this is the most direct way to propagate the module search path(s).

Additional References

Sign up to request clarification or add additional context in comments.

2 Comments

@ruslo Thanks for the feedback. I'll check and update my answer(s) accordingly.
This seems like a great start, but I am having trouble modifying it to correctly pass on transitive library dependencies. The library I am trying to export depends itself on another library (and its header files), and I cannot get this stuff added to the correct link/include information for my package. Any ideas how this should work?

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.