Skip to content

Commit 87ce470

Browse files
committed
Add add_lib_include_interface_target
1 parent 6e867c8 commit 87ce470

File tree

3 files changed

+57
-12
lines changed

3 files changed

+57
-12
lines changed

CMake/ystdlib-cpp-helpers.cmake

Lines changed: 51 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,43 @@ function(check_if_header_only SOURCE_LIST IS_HEADER_ONLY NON_HEADER_FILE)
1414
set(${NON_HEADER_FILE} "" PARENT_SCOPE)
1515
endfunction()
1616

17+
# Defines a CMake interface target to expose the include path resolution directory of a third-party
18+
# library.
19+
20+
# The created target can be linked against `ystdlib-cpp` libraries to ensure
21+
# consistent header resolution across dependent projects.
22+
#
23+
# This is useful for third-party libraries that do not properly configure target-based include paths
24+
# using `target_include_directories($<INSTALL_INTERFACE>)`.
25+
#
26+
# Call this function after using the `find_package()` call so that `<LIB_NAME>_ROOT` is defined.
27+
#
28+
# @param LIB_NAME The base name of the library (expects <LIB_NAME>_ROOT to be defined).
29+
# @param [DEP_LIST] Optional list of interface dependencies (e.g., nested include targets).
30+
function(add_lib_include_interface_target)
31+
set(options "")
32+
set(oneValueArgs LIB_NAME)
33+
set(multiValueArgs DEP_LIST)
34+
cmake_parse_arguments(arg "${options}" "${oneValueArgs}" "${multiValueArgs}" ${ARGN})
35+
36+
# Extract path to package library installation
37+
set(_LIB_ROOT_PATH_VAR "${arg_LIB_NAME}_ROOT")
38+
if(NOT DEFINED ${_LIB_ROOT_PATH_VAR})
39+
message(FATAL_ERROR "${arg_LIB_NAME} install path `${_LIB_ROOT_PATH_VAR}` is not defined.")
40+
endif()
41+
set(_LIB_ROOT_PATH "${${_LIB_ROOT_PATH_VAR}}")
42+
43+
set(_TARGET_NAME "${arg_LIB_NAME}_include")
44+
add_library(${_TARGET_NAME} INTERFACE)
45+
add_library(${arg_LIB_NAME}::${_TARGET_NAME} ALIAS ${_TARGET_NAME})
46+
target_include_directories(
47+
${_TARGET_NAME}
48+
INTERFACE
49+
"$<BUILD_INTERFACE:${_LIB_ROOT_PATH}/include>"
50+
)
51+
target_link_libraries(${_TARGET_NAME} INTERFACE ${arg_DEP_LIST})
52+
endfunction()
53+
1754
# Adds a c++20 interface library in the subdirectory NAME with the target NAME and alias
1855
# NAMESPACE::NAME. Libraries with multiple levels of namespace nesting are currently not supported.
1956
#
@@ -65,12 +102,19 @@ function(cpp_library)
65102

66103
check_if_header_only(arg_cpp_lib_PRIVATE_SOURCES _IS_INTERFACE_LIB _)
67104
if(_IS_INTERFACE_LIB)
105+
if(arg_cpp_lib_PRIVATE_LINK_LIBRARIES)
106+
message(
107+
FATAL_ERROR
108+
"Private dependency specifications disabled for interface library target ${_ALIAS_TARGET_NAME}."
109+
)
110+
endif()
68111
add_library(${arg_cpp_lib_NAME} INTERFACE)
69112
target_include_directories(
70113
${arg_cpp_lib_NAME}
71114
INTERFACE
72115
"$<BUILD_INTERFACE:${arg_cpp_lib_BUILD_INCLUDE_DIR}>"
73116
)
117+
target_link_libraries(${arg_cpp_lib_NAME} INTERFACE ${arg_cpp_lib_PUBLIC_LINK_LIBRARIES})
74118
target_compile_features(${arg_cpp_lib_NAME} INTERFACE cxx_std_20)
75119
else()
76120
# The library type is specified by `BUILD_SHARED_LIBS` if it is defined. Otherwise, the type
@@ -87,16 +131,16 @@ function(cpp_library)
87131
PUBLIC
88132
"$<BUILD_INTERFACE:${arg_cpp_lib_BUILD_INCLUDE_DIR}>"
89133
)
134+
target_link_libraries(
135+
${arg_cpp_lib_NAME}
136+
PUBLIC
137+
${arg_cpp_lib_PUBLIC_LINK_LIBRARIES}
138+
PRIVATE
139+
${arg_cpp_lib_PRIVATE_LINK_LIBRARIES}
140+
)
90141
target_compile_features(${arg_cpp_lib_NAME} PUBLIC cxx_std_20)
91142
endif()
92143

93-
target_link_libraries(
94-
${arg_cpp_lib_NAME}
95-
PUBLIC
96-
${arg_cpp_lib_PUBLIC_LINK_LIBRARIES}
97-
PRIVATE
98-
${arg_cpp_lib_PRIVATE_LINK_LIBRARIES}
99-
)
100144
add_library(${_ALIAS_TARGET_NAME} ALIAS ${arg_cpp_lib_NAME})
101145

102146
if(YSTDLIB_CPP_ENABLE_TESTS)

CMakeLists.txt

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
cmake_minimum_required(VERSION 3.22.1)
22

3+
list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}/CMake)
4+
include(ystdlib-cpp-helpers)
5+
36
project(YSTDLIB_CPP LANGUAGES CXX)
47

58
set(YSTDLIB_CPP_VERSION "0.0.1" CACHE STRING "Project version.")
@@ -53,6 +56,8 @@ endif()
5356
find_package(outcome REQUIRED)
5457
if(outcome_FOUND)
5558
message(STATUS "Found outcome.")
59+
add_lib_include_interface_target(LIB_NAME quickcpplib)
60+
add_lib_include_interface_target(LIB_NAME outcome DEP_LIST quickcpplib::quickcpplib_include)
5661
else()
5762
message(FATAL_ERROR "Could not find libraries for outcome.")
5863
endif()
@@ -81,9 +86,4 @@ if(YSTDLIB_CPP_ENABLE_TESTS)
8186
catch_discover_tests(${UNIFIED_UNIT_TEST_TARGET} WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/testbin)
8287
endif()
8388

84-
# Import CMake helper functions
85-
list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}/CMake)
86-
87-
include(ystdlib-cpp-helpers)
88-
8989
add_subdirectory(src/ystdlib)

taskfiles/deps.yaml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ vars:
1111
tasks:
1212
install-all:
1313
desc: "Install all dependencies required by ystdlib-cpp."
14+
run: "once"
1415
cmds:
1516
- task: "install-all-init"
1617
- task: "install-all-run"

0 commit comments

Comments
 (0)