1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178
|
#===============================================================================
# Define targets for linking against the selected ABI library
#
# After including this file, the following targets are defined:
# - libcxx-abi-headers: An interface target that allows getting access to the
# headers of the selected ABI library.
# - libcxx-abi-shared: A target representing the selected shared ABI library.
# - libcxx-abi-static: A target representing the selected static ABI library.
#
# Furthermore, some ABI libraries also define the following target:
# - libcxx-abi-shared-objects: An object library representing a set of object files
# constituting the ABI library, suitable for bundling
# into a shared library.
# - libcxx-abi-static-objects: An object library representing a set of object files
# constituting the ABI library, suitable for bundling
# into a static library.
#===============================================================================
include(GNUInstallDirs)
# This function copies the provided headers to a private directory and adds that
# path to the given INTERFACE target. That target can then be linked against to
# get access to those headers (and only those).
#
# The problem this solves is that when building against a system-provided ABI library,
# the ABI headers might live side-by-side with an actual C++ Standard Library
# installation. For that reason, we can't just add `-I <path-to-ABI-headers>`,
# since we would end up also adding the system-provided C++ Standard Library to
# the search path. Instead, what we do is copy just the ABI library headers to
# a private directory and add just that path when we build libc++.
function(import_private_headers target include_dirs headers)
foreach(header ${headers})
set(found FALSE)
foreach(incpath ${include_dirs})
if (EXISTS "${incpath}/${header}")
set(found TRUE)
message(STATUS "Looking for ${header} in ${incpath} - found")
get_filename_component(dstdir ${header} PATH)
get_filename_component(header_file ${header} NAME)
set(src ${incpath}/${header})
set(dst "${LIBCXX_BINARY_DIR}/private-abi-headers/${dstdir}/${header_file}")
add_custom_command(OUTPUT ${dst}
DEPENDS ${src}
COMMAND ${CMAKE_COMMAND} -E make_directory "${LIBCXX_BINARY_DIR}/private-abi-headers/${dstdir}"
COMMAND ${CMAKE_COMMAND} -E copy_if_different ${src} ${dst}
COMMENT "Copying C++ ABI header ${header}")
list(APPEND abilib_headers "${dst}")
else()
message(STATUS "Looking for ${header} in ${incpath} - not found")
endif()
endforeach()
if (NOT found)
message(WARNING "Failed to find ${header} in ${include_dirs}")
endif()
endforeach()
# Work around https://gitlab.kitware.com/cmake/cmake/-/issues/18399
add_library(${target}-generate-private-headers OBJECT ${abilib_headers})
set_target_properties(${target}-generate-private-headers PROPERTIES LINKER_LANGUAGE CXX)
target_link_libraries(${target} INTERFACE ${target}-generate-private-headers)
target_include_directories(${target} INTERFACE "${LIBCXX_BINARY_DIR}/private-abi-headers")
endfunction()
# This function creates an imported static library named <target>.
# It imports a library named <name> searched at the given <path>.
function(import_static_library target path name)
add_library(${target} STATIC IMPORTED GLOBAL)
find_library(file
NAMES "${CMAKE_STATIC_LIBRARY_PREFIX}${name}${CMAKE_STATIC_LIBRARY_SUFFIX}"
PATHS "${path}"
NO_CACHE)
set_target_properties(${target} PROPERTIES IMPORTED_LOCATION "${file}")
endfunction()
# This function creates an imported shared (interface) library named <target>
# for the given library <name>.
function(import_shared_library target name)
add_library(${target} INTERFACE IMPORTED GLOBAL)
set_target_properties(${target} PROPERTIES IMPORTED_LIBNAME "${name}")
endfunction()
# Link against a system-provided libstdc++
if ("${LIBCXX_CXX_ABI}" STREQUAL "libstdc++")
add_library(libcxx-abi-headers INTERFACE)
import_private_headers(libcxx-abi-headers "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
"cxxabi.h;bits/c++config.h;bits/os_defines.h;bits/cpu_defines.h;bits/cxxabi_tweaks.h;bits/cxxabi_forced.h")
target_compile_definitions(libcxx-abi-headers INTERFACE "-DLIBSTDCXX" "-D__GLIBCXX__")
import_shared_library(libcxx-abi-shared stdc++)
target_link_libraries(libcxx-abi-shared INTERFACE libcxx-abi-headers)
import_static_library(libcxx-abi-static "${LIBCXX_CXX_ABI_LIBRARY_PATH}" stdc++)
target_link_libraries(libcxx-abi-static INTERFACE libcxx-abi-headers)
# Link against a system-provided libsupc++
elseif ("${LIBCXX_CXX_ABI}" STREQUAL "libsupc++")
add_library(libcxx-abi-headers INTERFACE)
import_private_headers(libcxx-abi-headers "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
"cxxabi.h;bits/c++config.h;bits/os_defines.h;bits/cpu_defines.h;bits/cxxabi_tweaks.h;bits/cxxabi_forced.h")
target_compile_definitions(libcxx-abi-headers INTERFACE "-D__GLIBCXX__")
import_shared_library(libcxx-abi-shared supc++)
target_link_libraries(libcxx-abi-shared INTERFACE libcxx-abi-headers)
import_static_library(libcxx-abi-static "${LIBCXX_CXX_ABI_LIBRARY_PATH}" supc++)
target_link_libraries(libcxx-abi-static INTERFACE libcxx-abi-headers)
# Link against the in-tree libc++abi
elseif ("${LIBCXX_CXX_ABI}" STREQUAL "libcxxabi")
add_library(libcxx-abi-headers INTERFACE)
target_link_libraries(libcxx-abi-headers INTERFACE cxxabi-headers)
target_compile_definitions(libcxx-abi-headers INTERFACE "-DLIBCXX_BUILDING_LIBCXXABI")
if (TARGET cxxabi_shared)
add_library(libcxx-abi-shared ALIAS cxxabi_shared)
endif()
if (TARGET cxxabi_static)
add_library(libcxx-abi-static ALIAS cxxabi_static)
endif()
if (TARGET cxxabi_shared_objects)
add_library(libcxx-abi-shared-objects ALIAS cxxabi_shared_objects)
endif()
if (TARGET cxxabi_static_objects)
add_library(libcxx-abi-static-objects ALIAS cxxabi_static_objects)
endif()
# Link against a system-provided libc++abi
elseif ("${LIBCXX_CXX_ABI}" STREQUAL "system-libcxxabi")
add_library(libcxx-abi-headers INTERFACE)
import_private_headers(libcxx-abi-headers "${LIBCXX_CXX_ABI_INCLUDE_PATHS}" "cxxabi.h;__cxxabi_config.h")
target_compile_definitions(libcxx-abi-headers INTERFACE "-DLIBCXX_BUILDING_LIBCXXABI")
import_shared_library(libcxx-abi-shared c++abi)
target_link_libraries(libcxx-abi-shared INTERFACE libcxx-abi-headers)
import_static_library(libcxx-abi-static "${LIBCXX_CXX_ABI_LIBRARY_PATH}" c++abi)
target_link_libraries(libcxx-abi-static INTERFACE libcxx-abi-headers)
# Link against a system-provided libcxxrt
elseif ("${LIBCXX_CXX_ABI}" STREQUAL "libcxxrt")
if(NOT LIBCXX_CXX_ABI_INCLUDE_PATHS)
message(STATUS "LIBCXX_CXX_ABI_INCLUDE_PATHS not set, using /usr/include/c++/v1")
set(LIBCXX_CXX_ABI_INCLUDE_PATHS "/usr/include/c++/v1")
endif()
add_library(libcxx-abi-headers INTERFACE)
import_private_headers(libcxx-abi-headers "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
"cxxabi.h;unwind.h;unwind-arm.h;unwind-itanium.h")
target_compile_definitions(libcxx-abi-headers INTERFACE "-DLIBCXXRT")
import_shared_library(libcxx-abi-shared cxxrt)
target_link_libraries(libcxx-abi-shared INTERFACE libcxx-abi-headers)
import_static_library(libcxx-abi-static "${LIBCXX_CXX_ABI_LIBRARY_PATH}" cxxrt)
target_link_libraries(libcxx-abi-static INTERFACE libcxx-abi-headers)
# Link against a system-provided vcruntime
# FIXME: Figure out how to configure the ABI library on Windows.
elseif ("${LIBCXX_CXX_ABI}" STREQUAL "vcruntime")
add_library(libcxx-abi-headers INTERFACE)
add_library(libcxx-abi-shared INTERFACE)
add_library(libcxx-abi-static INTERFACE)
# Don't link against any ABI library
elseif ("${LIBCXX_CXX_ABI}" STREQUAL "none")
add_library(libcxx-abi-headers INTERFACE)
target_compile_definitions(libcxx-abi-headers INTERFACE "-D_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY")
add_library(libcxx-abi-shared INTERFACE)
target_link_libraries(libcxx-abi-shared INTERFACE libcxx-abi-headers)
add_library(libcxx-abi-static INTERFACE)
target_link_libraries(libcxx-abi-static INTERFACE libcxx-abi-headers)
endif()
|