Answer the question
In order to leave comments, you need to log in
CMake. How to include a library from a file?
There are thousands of articles on the Internet about how to include a prebuilt library in your project using cmake, but none of the articles helped me.
I have a library for representing approximate numbers, which is compiled into a static library.
cmake_minimum_required(VERSION 3.19)
project(approx_lib)
set(CMAKE_CXX_STANDARD 20)
set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib)
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/lib)
set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin/examples)
add_library(approx_lib STATIC include/approx_number.h src/approx_number.cpp)
target_include_directories(approx_lib PUBLIC include/)
install(TARGETS approx_lib LIBRARY DESTINATION lib)
cmake_minimum_required(VERSION 3.19)
project(just_calculator VERSION 1.0.0.0 LANGUAGES CXX)
set(CMAKE_CXX_STANDARD 20)
find_library(APPROX_LIB approx_lib HINTS /usr/local/lib REQUIRED)
message(STATUS "Found approx_lib: ${APPROX_LIB}")
add_executable(just_calculator main.cpp)
target_link_libraries(just_calculator LINK_PUBLIC ${APPROX_LIB})
-- Found approx_lib: /usr/local/lib/libapprox_lib.a
-- Configuring done
-- Generating done
#include <approx_number.h>
Answer the question
In order to leave comments, you need to log in
So you have two parts - actually, the .a archive, and the header (or headers).
install(TARGETS approx_lib LIBRARY DESTINATION lib) - installs only the built target (i.e. the static lib file itself), but not the header!
If you do not install, you can connect either as add_subdirectory with the path to the sources. Then it will be part of the main project, it will be assembled with it and everything you need will be found (as long as the target_include_directories is registered and knows where to look).
If you install - then, obviously, you need to install headers too. And somehow tell the project where everything is.
Here is a snippet from our custom build of icu (let the package name be foo, not icu. And the namespace be baz. That's more interesting!)
add_library(icu .....)
target_include_directories(icu PUBLIC $<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/source/common>$<INSTALL_INTERFACE:include/icu>)
install ( TARGETS icu EXPORT icuExport RUNTIME DESTINATION lib LIBRARY DESTINATION lib )
install ( DIRECTORY source/common/unicode DESTINATION include/icu FILES_MATCHING PATTERN "*.h")
# install exports
set ( CMAKE_CMAKE_DIR "lib/cmake/foo" )
install ( EXPORT icuExport FILE foo-targets.cmake DESTINATION "${CMAKE_CMAKE_DIR}" NAMESPACE baz:: )
file ( WRITE foo-config.cmake
"if(NOT TARGET baz::icu)
include(\"\${CMAKE_CURRENT_LIST_DIR}/foo-targets.cmake\")
endif()")
install ( FILES foo-config.cmake DESTINATION "${CMAKE_CMAKE_DIR}" )
LIST (APPEND CMAKE_PREFIX_PATH "/root/bar")
find_package(foo)
add_executable(my_prog main.cpp)
target_link_libraries(my_prog PRIVATE baz::icu)
... # это сгенерированный код!
# Create imported target baz::icu
add_library(baz::icu STATIC IMPORTED)
set_target_properties(baz::icu PROPERTIES
INTERFACE_COMPILE_DEFINITIONS "U_STATIC_IMPLEMENTATION;U_CHARSET_IS_UTF8=1;U_NO_DEFAULT_INCLUDE_UTF_HEADERS=1"
INTERFACE_INCLUDE_DIRECTORIES "${_IMPORT_PREFIX}/include/icu"
)
...
# Load information for each installed configuration.
get_filename_component(_DIR "${CMAKE_CURRENT_LIST_FILE}" PATH)
file(GLOB CONFIG_FILES "${_DIR}/foo-targets-*.cmake")
foreach(f ${CONFIG_FILES})
include(${f})
endforeach()
...
... а это файл foo-targets-relwithdebinfo.cmake
# Import target "baz::icu" for configuration "RelWithDebInfo"
set_property(TARGET baz::icu APPEND PROPERTY IMPORTED_CONFIGURATIONS RELWITHDEBINFO)
set_target_properties(baz::icu PROPERTIES
IMPORTED_LINK_INTERFACE_LANGUAGES_RELWITHDEBINFO "CXX"
IMPORTED_LOCATION_RELWITHDEBINFO "${_IMPORT_PREFIX}/lib/libicu.a"
)
Didn't find what you were looking for?
Ask your questionAsk a Question
731 491 924 answers to any question