[clang] [compiler-rt] [libcxx] [llvm] [libc++] Replace LIBCXX_ENABLE_STATIC_ABI_LIBRARY & friends by a new LIBCXX_CXX_ABI choice (PR #112978)
Louis Dionne via cfe-commits
cfe-commits at lists.llvm.org
Tue Nov 19 15:47:36 PST 2024
https://github.com/ldionne updated https://github.com/llvm/llvm-project/pull/112978
>From e42db172b2397e6358dc60850e4c8b085c6bd4bf Mon Sep 17 00:00:00 2001
From: Louis Dionne <ldionne.2 at gmail.com>
Date: Fri, 13 May 2022 09:26:01 -0400
Subject: [PATCH 1/4] [libc++] Replace LIBCXX_ENABLE_STATIC_ABI_LIBRARY &
friends by a new LIBCXX_CXX_ABI choice
Instead of having complicated options like LIBCXX_ENABLE_STATIC_ABI_LIBRARY
and LIBCXX_STATICALLY_LINK_ABI_IN_STATIC_LIBRARY, introduce a more general
mechanism to select the ABI library used by libc++. The new mechanism allows
specifying the ABI library for the static libc++ and the shared libc++
separately, and allows selecting a "merged" flavor of libc++ for both
the in-tree libc++abi and any external static ABI library.
As an example, one can now specify arbitrary combinations like
-DLIBCXX_ABILIB_FOR_SHARED="shared-libcxxabi"
-DLIBCXX_ABILIB_FOR_STATIC="merged-libcxxabi"
which would have been impossible or very brittle in the past. In theory,
one can even select an entirely different ABI library for the static and
the shared libc++ (e.g. libc++abi vs libsupc++), although supporting that
is not a primary goal of this patch but merely a result of the general
mechanism.
Closes #77655
Fixes #57759
Differential Revision: https://reviews.llvm.org/D125683
---
clang/cmake/caches/Android.cmake | 4 +-
clang/cmake/caches/CrossWinToARMLinux.cmake | 4 +-
clang/cmake/caches/Fuchsia-stage2.cmake | 8 +-
clang/cmake/caches/Fuchsia.cmake | 4 +-
compiler-rt/cmake/Modules/AddCompilerRT.cmake | 3 +-
libcxx/CMakeLists.txt | 68 +++--
libcxx/cmake/Modules/HandleLibCXXABI.cmake | 254 +++++++++---------
libcxx/cmake/caches/AMDGPU.cmake | 4 +-
libcxx/cmake/caches/AndroidNDK.cmake | 2 +-
libcxx/cmake/caches/Generic-merged.cmake | 3 +-
libcxx/cmake/caches/MinGW.cmake | 4 +-
libcxx/cmake/caches/NVPTX.cmake | 4 +-
libcxx/docs/ReleaseNotes/20.rst | 6 +-
libcxx/docs/VendorDocumentation.rst | 24 +-
libcxx/include/CMakeLists.txt | 2 +-
libcxx/src/CMakeLists.txt | 19 +-
libcxx/utils/ci/run-buildbot | 4 -
.../docs/HowToBuildWindowsItaniumPrograms.rst | 28 +-
18 files changed, 215 insertions(+), 230 deletions(-)
diff --git a/clang/cmake/caches/Android.cmake b/clang/cmake/caches/Android.cmake
index d5ca6b50d4ada7..dbf66539591394 100644
--- a/clang/cmake/caches/Android.cmake
+++ b/clang/cmake/caches/Android.cmake
@@ -21,8 +21,8 @@ if (LIBCXX_ENABLE_ABI_LINKER_SCRIPT)
list(APPEND EXTRA_ARGS -DLIBCXX_ENABLE_ABI_LINKER_SCRIPT=${LIBCXX_ENABLE_ABI_LINKER_SCRIPT})
endif()
-if (LIBCXX_ENABLE_STATIC_ABI_LIBRARY)
- list(APPEND EXTRA_ARGS -DLIBCXX_ENABLE_STATIC_ABI_LIBRARY=${LIBCXX_ENABLE_STATIC_ABI_LIBRARY})
+if (LIBCXX_CXX_ABI)
+ list(APPEND EXTRA_ARGS -DLIBCXX_CXX_ABI=${LIBCXX_CXX_ABI})
endif()
if (LLVM_BUILD_EXTERNAL_COMPILER_RT)
diff --git a/clang/cmake/caches/CrossWinToARMLinux.cmake b/clang/cmake/caches/CrossWinToARMLinux.cmake
index 87118bbd33377d..15341aeb283801 100644
--- a/clang/cmake/caches/CrossWinToARMLinux.cmake
+++ b/clang/cmake/caches/CrossWinToARMLinux.cmake
@@ -215,10 +215,8 @@ set(RUNTIMES_${TOOLCHAIN_TARGET_TRIPLE}_LIBCXXABI_ENABLE_SHARED
set(RUNTIMES_${TOOLCHAIN_TARGET_TRIPLE}_LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
set(RUNTIMES_${TOOLCHAIN_TARGET_TRIPLE}_LIBCXX_ENABLE_SHARED ${TOOLCHAIN_SHARED_LIBS} CACHE BOOL "")
set(RUNTIMES_${TOOLCHAIN_TARGET_TRIPLE}_LIBCXX_ABI_VERSION ${LIBCXX_ABI_VERSION} CACHE STRING "")
-set(RUNTIMES_${TOOLCHAIN_TARGET_TRIPLE}_LIBCXX_CXX_ABI "libcxxabi" CACHE STRING "") #!!!
+set(RUNTIMES_${TOOLCHAIN_TARGET_TRIPLE}_LIBCXX_CXX_ABI "merged-libcxxabi" CACHE STRING "") #!!!
set(RUNTIMES_${TOOLCHAIN_TARGET_TRIPLE}_LIBCXX_ENABLE_NEW_DELETE_DEFINITIONS ON CACHE BOOL "")
-# Merge libc++ and libc++abi libraries into the single libc++ library file.
-set(RUNTIMES_${TOOLCHAIN_TARGET_TRIPLE}_LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
# Avoid searching for the python3 interpreter during the runtimes configuration for the cross builds.
# It starts searching the python3 package using the target's sysroot path, that usually is not compatible with the build host.
diff --git a/clang/cmake/caches/Fuchsia-stage2.cmake b/clang/cmake/caches/Fuchsia-stage2.cmake
index 747d9974828984..14f55541944793 100644
--- a/clang/cmake/caches/Fuchsia-stage2.cmake
+++ b/clang/cmake/caches/Fuchsia-stage2.cmake
@@ -83,7 +83,7 @@ if(APPLE)
set(LIBCXXABI_USE_LLVM_UNWINDER ON CACHE BOOL "")
set(LIBCXX_ABI_VERSION 2 CACHE STRING "")
set(LIBCXX_ENABLE_SHARED OFF CACHE BOOL "")
- set(LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
+ set(LIBCXX_CXX_ABI "merged-libcxxabi" CACHE STRING "")
set(LIBCXX_HARDENING_MODE "none" CACHE STRING "")
set(LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
set(RUNTIMES_CMAKE_ARGS "-DCMAKE_OSX_DEPLOYMENT_TARGET=10.13;-DCMAKE_OSX_ARCHITECTURES=arm64|x86_64" CACHE STRING "")
@@ -180,9 +180,9 @@ foreach(target aarch64-unknown-linux-gnu;armv7-unknown-linux-gnueabihf;i386-unkn
set(RUNTIMES_${target}_LIBCXXABI_ENABLE_SHARED OFF CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXXABI_USE_LLVM_UNWINDER ON CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXXABI_INSTALL_LIBRARY OFF CACHE BOOL "")
+ set(RUNTIMES_${target}_LIBCXX_CXX_ABI "merged-libcxxabi" CACHE STRING "")
set(RUNTIMES_${target}_LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXX_ENABLE_SHARED OFF CACHE BOOL "")
- set(RUNTIMES_${target}_LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXX_ABI_VERSION 2 CACHE STRING "")
set(RUNTIMES_${target}_LLVM_ENABLE_ASSERTIONS OFF CACHE BOOL "")
set(RUNTIMES_${target}_SANITIZER_CXX_ABI "libc++" CACHE STRING "")
@@ -244,10 +244,10 @@ if(FUCHSIA_SDK)
set(RUNTIMES_${target}_LIBCXXABI_USE_LLVM_UNWINDER ON CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXXABI_HERMETIC_STATIC_LIBRARY ON CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXXABI_INSTALL_STATIC_LIBRARY OFF CACHE BOOL "")
+ set(RUNTIMES_${target}_LIBCXX_ABILIB_FOR_STATIC "merged-libcxxabi" CACHE STRING "")
+ set(RUNTIMES_${target}_LIBCXX_ABILIB_FOR_SHARED "shared-libcxxabi" CACHE STRING "")
set(RUNTIMES_${target}_LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
- set(RUNTIMES_${target}_LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXX_HERMETIC_STATIC_LIBRARY ON CACHE BOOL "")
- set(RUNTIMES_${target}_LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY OFF CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXX_ABI_VERSION 2 CACHE STRING "")
set(RUNTIMES_${target}_LLVM_ENABLE_ASSERTIONS OFF CACHE BOOL "")
set(RUNTIMES_${target}_LLVM_ENABLE_RUNTIMES "compiler-rt;libcxx;libcxxabi;libunwind" CACHE STRING "")
diff --git a/clang/cmake/caches/Fuchsia.cmake b/clang/cmake/caches/Fuchsia.cmake
index 2d2dcb9ae6798d..5e31fe4fdd33df 100644
--- a/clang/cmake/caches/Fuchsia.cmake
+++ b/clang/cmake/caches/Fuchsia.cmake
@@ -109,6 +109,7 @@ endif()
if(WIN32)
set(LIBCXX_ABI_VERSION 2 CACHE STRING "")
+ set(LIBCXX_CXX_ABI "merged-libcxxabi" CACHE STRING "")
set(LIBCXX_ENABLE_ABI_LINKER_SCRIPT OFF CACHE BOOL "")
set(LIBCXX_ENABLE_SHARED OFF CACHE BOOL "")
set(BUILTINS_CMAKE_ARGS -DCMAKE_SYSTEM_NAME=Windows CACHE STRING "")
@@ -125,7 +126,6 @@ else()
set(LIBCXXABI_USE_LLVM_UNWINDER ON CACHE BOOL "")
set(LIBCXX_ABI_VERSION 2 CACHE STRING "")
set(LIBCXX_ENABLE_SHARED OFF CACHE BOOL "")
- set(LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
set(LIBCXX_HARDENING_MODE "none" CACHE STRING "")
set(LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
set(LLVM_ENABLE_RUNTIMES "compiler-rt;libcxx;libcxxabi;libunwind" CACHE STRING "")
@@ -155,8 +155,8 @@ if(BOOTSTRAP_CMAKE_SYSTEM_NAME)
set(RUNTIMES_${target}_LIBCXXABI_INSTALL_LIBRARY OFF CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXX_ENABLE_SHARED OFF CACHE BOOL "")
- set(RUNTIMES_${target}_LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
set(RUNTIMES_${target}_LIBCXX_ABI_VERSION 2 CACHE STRING "")
+ set(RUNTIMES_${target}_LIBCXX_CXX_ABI "merged-libcxxabi" CACHE STRING "")
set(RUNTIMES_${target}_LLVM_ENABLE_ASSERTIONS OFF CACHE BOOL "")
set(RUNTIMES_${target}_LLVM_ENABLE_RUNTIMES "compiler-rt;libcxx;libcxxabi;libunwind" CACHE STRING "")
set(RUNTIMES_${target}_SANITIZER_CXX_ABI "libc++" CACHE STRING "")
diff --git a/compiler-rt/cmake/Modules/AddCompilerRT.cmake b/compiler-rt/cmake/Modules/AddCompilerRT.cmake
index 77261f631ea117..319468ae93aabb 100644
--- a/compiler-rt/cmake/Modules/AddCompilerRT.cmake
+++ b/compiler-rt/cmake/Modules/AddCompilerRT.cmake
@@ -697,12 +697,11 @@ macro(add_custom_libcxx name prefix)
-DLIBCXXABI_ENABLE_SHARED=OFF
-DLIBCXXABI_HERMETIC_STATIC_LIBRARY=ON
-DLIBCXXABI_INCLUDE_TESTS=OFF
- -DLIBCXX_CXX_ABI=libcxxabi
+ -DLIBCXX_CXX_ABI="merged-libcxxabi"
-DLIBCXX_ENABLE_SHARED=OFF
-DLIBCXX_HERMETIC_STATIC_LIBRARY=ON
-DLIBCXX_INCLUDE_BENCHMARKS=OFF
-DLIBCXX_INCLUDE_TESTS=OFF
- -DLIBCXX_ENABLE_STATIC_ABI_LIBRARY=ON
-DLLVM_INCLUDE_TESTS=OFF
-DLLVM_INCLUDE_DOCS=OFF
${LIBCXX_CMAKE_ARGS}
diff --git a/libcxx/CMakeLists.txt b/libcxx/CMakeLists.txt
index abe12c2805a7cf..57d86d97e33f02 100644
--- a/libcxx/CMakeLists.txt
+++ b/libcxx/CMakeLists.txt
@@ -241,11 +241,22 @@ else()
endif()
set(LIBCXX_SUPPORTED_ABI_LIBRARIES none libcxxabi system-libcxxabi libcxxrt libstdc++ libsupc++ vcruntime)
-set(LIBCXX_CXX_ABI "${LIBCXX_DEFAULT_ABI_LIBRARY}" CACHE STRING "Specify C++ ABI library to use. Supported values are ${LIBCXX_SUPPORTED_ABI_LIBRARIES}.")
-if (NOT "${LIBCXX_CXX_ABI}" IN_LIST LIBCXX_SUPPORTED_ABI_LIBRARIES)
- message(FATAL_ERROR "Unsupported C++ ABI library: '${LIBCXX_CXX_ABI}'. Supported values are ${LIBCXX_SUPPORTED_ABI_LIBRARIES}.")
-endif()
-
+set(LIBCXX_CXX_ABI "${LIBCXX_DEFAULT_ABI_LIBRARY}" CACHE STRING
+ "Specify the C++ ABI library to use for the shared and the static libc++ libraries. Supported values are ${LIBCXX_SUPPORTED_ABI_LIBRARIES}.
+ This CMake option also supports \"consumption specifiers\", which specify how the selected ABI library should be consumed by
+ libc++. The supported specifiers are:
+ - `shared`: The selected ABI library should be used as a shared library.
+ - `static`: The selected ABI library should be used as a static library.
+ - `merged`: The selected ABI library should be a static library whose object files will be merged directly into the produced libc++ library.
+
+ A consumption specifier is provided by appending it to the name of the library, such as `LIBCXX_CXX_ABI=merged-libcxxabi`.
+ If no consumption specifier is provided, the libc++ shared library will default to using a shared ABI library, and the
+ libc++ static library will default to using a static ABI library.")
+set(LIBCXX_ABILIB_FOR_SHARED "${LIBCXX_CXX_ABI}" CACHE STRING "C++ ABI library to use for the shared libc++ library.")
+set(LIBCXX_ABILIB_FOR_STATIC "${LIBCXX_CXX_ABI}" CACHE STRING "C++ ABI library to use for the static libc++ library.")
+
+#############################
+# TODO: Remove these options in LLVM 21.
option(LIBCXX_ENABLE_STATIC_ABI_LIBRARY
"Use a static copy of the ABI library when linking libc++.
This option cannot be used with LIBCXX_ENABLE_ABI_LINKER_SCRIPT." OFF)
@@ -258,17 +269,34 @@ option(LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY
"Statically link the ABI library to shared library"
${LIBCXX_ENABLE_STATIC_ABI_LIBRARY})
+if (LIBCXX_ENABLE_STATIC_ABI_LIBRARY OR LIBCXX_STATICALLY_LINK_ABI_IN_STATIC_LIBRARY OR LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY)
+ message(WARNING "The LIBCXX_ENABLE_STATIC_ABI_LIBRARY, LIBCXX_STATICALLY_LINK_ABI_IN_STATIC_LIBRARY and "
+ "LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY options have been deprecated in favor of "
+ "using LIBCXX_CXX_ABI=merged-libcxxabi. This will become an error in LLVM 21.")
+endif()
+if (LIBCXX_STATICALLY_LINK_ABI_IN_STATIC_LIBRARY)
+ set(LIBCXX_ABILIB_FOR_STATIC "merged-libcxxabi" CACHE STRING "" FORCE)
+endif()
+if (LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY)
+ set(LIBCXX_ABILIB_FOR_SHARED "merged-libcxxabi" CACHE STRING "" FORCE)
+endif()
+#############################
+
# Generate and install a linker script inplace of libc++.so. The linker script
# will link libc++ to the correct ABI library. This option is on by default
-# on UNIX platforms other than Apple, and on the Fuchsia platform unless we
-# statically link libc++abi inside libc++.so, we don't build libc++.so at all
-# or we don't have any ABI library.
-if (LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY
- OR NOT LIBCXX_ENABLE_SHARED
- OR LIBCXX_CXX_ABI STREQUAL "none")
- set(ENABLE_LINKER_SCRIPT_DEFAULT_VALUE OFF)
-elseif((UNIX OR FUCHSIA) AND NOT APPLE)
- set(ENABLE_LINKER_SCRIPT_DEFAULT_VALUE ON)
+# on UNIX platforms other than Apple unless we are linking the ABI library as
+# an object library. This option is also disabled when the ABI library is not
+# specified or is specified to be "none".
+if(LIBCXX_ENABLE_SHARED)
+ if ((UNIX OR FUCHSIA) AND NOT APPLE)
+ if (LIBCXX_ABILIB_FOR_SHARED STREQUAL "merged-libcxxabi" OR LIBCXX_ABILIB_FOR_SHARED STREQUAL "none")
+ set(ENABLE_LINKER_SCRIPT_DEFAULT_VALUE OFF)
+ else()
+ set(ENABLE_LINKER_SCRIPT_DEFAULT_VALUE ON)
+ endif()
+ else()
+ set(ENABLE_LINKER_SCRIPT_DEFAULT_VALUE OFF)
+ endif()
else()
set(ENABLE_LINKER_SCRIPT_DEFAULT_VALUE OFF)
endif()
@@ -382,12 +410,6 @@ if (LIBCXX_ENABLE_ABI_LINKER_SCRIPT)
endif()
endif()
-if (LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY AND LIBCXX_ENABLE_ABI_LINKER_SCRIPT)
- message(FATAL_ERROR "Conflicting options given.
- LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY cannot be specified with
- LIBCXX_ENABLE_ABI_LINKER_SCRIPT")
-endif()
-
if (LIBCXX_ABI_FORCE_ITANIUM AND LIBCXX_ABI_FORCE_MICROSOFT)
message(FATAL_ERROR "Only one of LIBCXX_ABI_FORCE_ITANIUM and LIBCXX_ABI_FORCE_MICROSOFT can be specified.")
endif ()
@@ -484,10 +506,6 @@ include(config-ix)
#===============================================================================
# Setup Compiler Flags
#===============================================================================
-
-include(HandleLibC) # Setup the C library flags
-include(HandleLibCXXABI) # Setup the ABI library flags
-
# FIXME(EricWF): See the FIXME on LIBCXX_ENABLE_PEDANTIC.
# Remove the -pedantic flag and -Wno-pedantic and -pedantic-errors
# so they don't get transformed into -Wno and -errors respectively.
@@ -820,7 +838,7 @@ if (DEFINED WIN32 AND LIBCXX_ENABLE_STATIC AND NOT LIBCXX_ENABLE_SHARED)
config_define(ON _LIBCPP_DISABLE_VISIBILITY_ANNOTATIONS)
endif()
-if (WIN32 AND LIBCXX_ENABLE_STATIC_ABI_LIBRARY)
+if (WIN32 AND LIBCXX_CXX_ABI STREQUAL "merged-libcxxabi")
# If linking libcxxabi statically into libcxx, skip the dllimport attributes
# on symbols we refer to from libcxxabi.
add_definitions(-D_LIBCXXABI_DISABLE_VISIBILITY_ANNOTATIONS)
diff --git a/libcxx/cmake/Modules/HandleLibCXXABI.cmake b/libcxx/cmake/Modules/HandleLibCXXABI.cmake
index 52236f473f35de..fa4b761e818021 100644
--- a/libcxx/cmake/Modules/HandleLibCXXABI.cmake
+++ b/libcxx/cmake/Modules/HandleLibCXXABI.cmake
@@ -2,18 +2,10 @@
# 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.
+# - libcxx-abi-shared: A target representing the selected ABI library for linking into
+# the libc++ shared library.
+# - libcxx-abi-static: A target representing the selected ABI library for linking into
+# the libc++ static library.
#===============================================================================
include(GNUInstallDirs)
@@ -29,6 +21,9 @@ include(GNUInstallDirs)
# 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)
+ if (NOT ${include_dirs})
+ message(FATAL_ERROR "Missing include paths for the selected ABI library!")
+ endif()
foreach(header ${headers})
set(found FALSE)
foreach(incpath ${include_dirs})
@@ -38,11 +33,11 @@ function(import_private_headers target include_dirs headers)
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}")
+ set(dst "${LIBCXX_BINARY_DIR}/private-abi-headers/${target}/${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 make_directory "${LIBCXX_BINARY_DIR}/private-abi-headers/${target}/${dstdir}"
COMMAND ${CMAKE_COMMAND} -E copy_if_different ${src} ${dst}
COMMENT "Copying C++ ABI header ${header}")
list(APPEND abilib_headers "${dst}")
@@ -60,7 +55,7 @@ function(import_private_headers target include_dirs 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")
+ target_include_directories(${target} INTERFACE "${LIBCXX_BINARY_DIR}/private-abi-headers/${target}")
endfunction()
# This function creates an imported static library named <target>.
@@ -74,128 +69,135 @@ function(import_static_library target path name)
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++")
- if(NOT LIBCXX_CXX_ABI_INCLUDE_PATHS)
- message(FATAL_ERROR "LIBCXX_CXX_ABI_INCLUDE_PATHS must be set when selecting libstdc++ as an ABI library")
+# This function creates a library target for linking against an external ABI library.
+#
+# <target>: The name of the target to create
+# <name>: The name of the library file to search for (e.g. c++abi, stdc++, cxxrt, supc++)
+# <type>: Whether to set up a static or a shared library (e.g. SHARED or STATIC)
+# <merged>: Whether to include the ABI library's object files directly into libc++. Only makes sense for a static ABI library.
+function(import_external_abi_library target name type merged)
+ if (${merged} AND "${type}" STREQUAL "SHARED")
+ message(FATAL_ERROR "Can't import an external ABI library for merging when requesting a shared ABI library.")
endif()
- 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++")
- if(NOT LIBCXX_CXX_ABI_INCLUDE_PATHS)
- message(FATAL_ERROR "LIBCXX_CXX_ABI_INCLUDE_PATHS must be set when selecting libsupc++ as an ABI library")
+ if ("${type}" STREQUAL "SHARED")
+ add_library(${target} INTERFACE IMPORTED GLOBAL)
+ set_target_properties(${target} PROPERTIES IMPORTED_LIBNAME "${name}")
+ elseif ("${type}" STREQUAL "STATIC")
+ if (${merged})
+ import_static_library(${target}-impl "${LIBCXX_CXX_ABI_LIBRARY_PATH}" ${name})
+ add_library(${target} INTERFACE)
+ if (APPLE)
+ target_link_options(${target} INTERFACE
+ "-Wl,-force_load" "$<TARGET_PROPERTY:${target}-impl,IMPORTED_LOCATION>")
+ else()
+ target_link_options(${target} INTERFACE
+ "-Wl,--whole-archive" "-Wl,-Bstatic"
+ "$<TARGET_PROPERTY:${target}-impl,IMPORTED_LOCATION>"
+ "-Wl,-Bdynamic" "-Wl,--no-whole-archive")
+ endif()
+ else()
+ import_static_library(${target} "${LIBCXX_CXX_ABI_LIBRARY_PATH}" ${name})
+ endif()
endif()
+endfunction()
- 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")
+# This function parses an ABI library choice (including optional consumption specifiers)
+# and generates a target representing the ABI library to link against.
+#
+# When a merged ABI library is requested, we only look for a static ABI library because
+# doing otherwise makes no sense. Otherwise, we search for the same type of ABI library
+# as we're linking into, i.e. we search for a shared ABI library when linking the shared
+# libc++ library, and a static ABI library otherwise.
+#
+# <abi_target>: The name of the target to create
+# <linked_into>: Whether this ABI library is linked into a STATIC or SHARED libc++
+# <input>: Input to parse as an ABI library choice with an optional consumption specifier.
+function(setup_abi_library abi_target linked_into input)
+ if ("${input}" MATCHES "^merged-(.+)$")
+ set(merged TRUE)
+ set(search_type "STATIC")
+ elseif ("${input}" MATCHES "^static-(.+)$")
+ set(merged FALSE)
+ set(search_type "STATIC")
+ elseif ("${input}" MATCHES "^shared-(.+)$")
+ set(merged FALSE)
+ set(search_type "SHARED")
+ else()
+ set(merged FALSE)
+ set(search_type "${linked_into}")
+ endif()
- if (TARGET cxxabi_shared)
- add_library(libcxx-abi-shared INTERFACE)
- target_link_libraries(libcxx-abi-shared INTERFACE cxxabi_shared)
+ # Strip the consumption specifier from the name, which leaves the name of the standard library.
+ string(REGEX REPLACE "^(merged-|static-|shared-)" "" stdlib "${input}")
+
+ # Link against a system-provided libstdc++
+ if ("${stdlib}" STREQUAL "libstdc++")
+ import_external_abi_library(${abi_target} stdc++ ${search_type} ${merged})
+ import_private_headers(${abi_target} "${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(${abi_target} INTERFACE "-DLIBSTDCXX" "-D__GLIBCXX__")
+
+ # Link against a system-provided libsupc++
+ elseif ("${stdlib}" STREQUAL "libsupc++")
+ import_external_abi_library(${abi_target} supc++ ${search_type} ${merged})
+ import_private_headers(${abi_target} "${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(${abi_target} INTERFACE "-D__GLIBCXX__")
+
+ # Link against a system-provided libcxxrt
+ elseif ("${stdlib}" STREQUAL "libcxxrt")
+ import_external_abi_library(${abi_target} cxxrt ${search_type} ${merged})
+ import_private_headers(${abi_target} "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
+ "cxxabi.h;unwind.h;unwind-arm.h;unwind-itanium.h")
+ target_compile_definitions(${abi_target} INTERFACE "-DLIBCXXRT")
+
+ # Link against a system-provided vcruntime
+ elseif ("${stdlib}" STREQUAL "vcruntime")
+ # FIXME: Figure out how to configure the ABI library on Windows.
+ add_library(${abi_target} INTERFACE)
+
+ # Link against a system-provided libc++abi
+ elseif ("${stdlib}" STREQUAL "system-libcxxabi")
+ import_external_abi_library(${abi_target} c++abi ${search_type} ${merged})
+ import_private_headers(${abi_target} "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
+ "cxxabi.h;__cxxabi_config.h")
+ target_compile_definitions(${abi_target} INTERFACE "-DLIBCXX_BUILDING_LIBCXXABI")
+
+ # Link against the in-tree libc++abi.
+ elseif ("${stdlib}" STREQUAL "libcxxabi")
+ if (${merged})
+ get_target_property(_outdir cxxabi_static ARCHIVE_OUTPUT_DIRECTORY)
+ get_target_property(_outname cxxabi_static OUTPUT_NAME)
+ set(LIBCXX_CXX_ABI_LIBRARY_PATH "${_outdir}")
+ import_external_abi_library(${abi_target} "${_outname}" STATIC TRUE)
+ else()
+ string(TOLOWER "${search_type}" type)
+ add_library(${abi_target} INTERFACE)
+ target_link_libraries(${abi_target} INTERFACE cxxabi_${type})
+
+ # Populate the OUTPUT_NAME property of the target because that is used when
+ # generating a linker script.
+ get_target_property(_outname cxxabi_${type} OUTPUT_NAME)
+ set_target_properties(${abi_target} PROPERTIES "OUTPUT_NAME" "${_outname}")
+ endif()
# When using the in-tree libc++abi as an ABI library, libc++ re-exports the
# libc++abi symbols (on platforms where it can) because libc++abi is only an
# implementation detail of libc++.
- target_link_libraries(libcxx-abi-shared INTERFACE cxxabi-reexports)
+ target_link_libraries(${abi_target} INTERFACE cxxabi-reexports)
- # Populate the OUTPUT_NAME property of libcxx-abi-shared because that is used when
- # generating a linker script.
- get_target_property(_output_name cxxabi_shared OUTPUT_NAME)
- set_target_properties(libcxx-abi-shared PROPERTIES "OUTPUT_NAME" "${_output_name}")
- endif()
-
- if (TARGET cxxabi_static)
- add_library(libcxx-abi-static ALIAS cxxabi_static)
- endif()
+ target_compile_definitions(${abi_target} INTERFACE "LIBCXX_BUILDING_LIBCXXABI")
- if (TARGET cxxabi_shared_objects)
- add_library(libcxx-abi-shared-objects ALIAS cxxabi_shared_objects)
- endif()
+ # Don't link against any ABI library
+ elseif ("${stdlib}" STREQUAL "none")
+ add_library(${abi_target} INTERFACE)
+ target_compile_definitions(${abi_target} INTERFACE "-D_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY")
- if (TARGET cxxabi_static_objects)
- add_library(libcxx-abi-static-objects ALIAS cxxabi_static_objects)
+ else()
+ message(FATAL_ERROR "Unsupported C++ ABI library selection: Got ABI selection '${input}', which parsed into standard library '${stdlib}'.")
endif()
+endfunction()
-# Link against a system-provided libc++abi
-elseif ("${LIBCXX_CXX_ABI}" STREQUAL "system-libcxxabi")
- if(NOT LIBCXX_CXX_ABI_INCLUDE_PATHS)
- message(FATAL_ERROR "LIBCXX_CXX_ABI_INCLUDE_PATHS must be set when selecting system-libcxxabi as an ABI library")
- endif()
-
- 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()
+setup_abi_library(libcxx-abi-shared SHARED "${LIBCXX_ABILIB_FOR_SHARED}")
+setup_abi_library(libcxx-abi-static STATIC "${LIBCXX_ABILIB_FOR_STATIC}")
diff --git a/libcxx/cmake/caches/AMDGPU.cmake b/libcxx/cmake/caches/AMDGPU.cmake
index 49abb6475fc41e..a3a7a38d3ecc07 100644
--- a/libcxx/cmake/caches/AMDGPU.cmake
+++ b/libcxx/cmake/caches/AMDGPU.cmake
@@ -1,5 +1,5 @@
# Configuration options for libcxx.
-set(LIBCXX_CXX_ABI libcxxabi CACHE STRING "")
+set(LIBCXX_CXX_ABI "merged-libcxxabi" CACHE STRING "")
set(LIBCXX_ENABLE_EXCEPTIONS OFF CACHE BOOL "")
set(LIBCXX_ENABLE_FILESYSTEM OFF CACHE BOOL "")
set(LIBCXX_ENABLE_LOCALIZATION OFF CACHE BOOL "")
@@ -8,7 +8,6 @@ set(LIBCXX_ENABLE_NEW_DELETE_DEFINITIONS ON CACHE BOOL "")
set(LIBCXX_ENABLE_RANDOM_DEVICE OFF CACHE BOOL "")
set(LIBCXX_ENABLE_RTTI OFF CACHE BOOL "")
set(LIBCXX_ENABLE_SHARED OFF CACHE BOOL "")
-set(LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
set(LIBCXX_ENABLE_STATIC ON CACHE BOOL "")
set(LIBCXX_ENABLE_THREADS OFF CACHE BOOL "")
set(LIBCXX_ENABLE_UNICODE OFF CACHE BOOL "")
@@ -16,7 +15,6 @@ set(LIBCXX_ENABLE_WIDE_CHARACTERS OFF CACHE BOOL "")
set(LIBCXX_HAS_TERMINAL_AVAILABLE OFF CACHE BOOL "")
set(LIBCXX_INSTALL_LIBRARY ON CACHE BOOL "")
set(LIBCXX_LIBC "llvm-libc" CACHE STRING "")
-set(LIBCXX_STATICALLY_LINK_ABI_IN_STATIC_LIBRARY ON CACHE BOOL "")
set(LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
# Configuration options for libcxxabi.
diff --git a/libcxx/cmake/caches/AndroidNDK.cmake b/libcxx/cmake/caches/AndroidNDK.cmake
index 298518781e9b7a..9d923328a75e44 100644
--- a/libcxx/cmake/caches/AndroidNDK.cmake
+++ b/libcxx/cmake/caches/AndroidNDK.cmake
@@ -19,7 +19,7 @@ set(LIBCXX_ABI_NAMESPACE __ndk1 CACHE STRING "")
# output path (the script clobbers the binary). Turn off the linker script.
set(LIBCXX_ENABLE_ABI_LINKER_SCRIPT OFF CACHE BOOL "")
-set(LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY ON CACHE BOOL "")
+set(LIBCXX_CXX_ABI "merged-libcxxabi" CACHE STRING "")
set(LIBCXXABI_ENABLE_SHARED OFF CACHE BOOL "")
# Android uses its own unwinder library
diff --git a/libcxx/cmake/caches/Generic-merged.cmake b/libcxx/cmake/caches/Generic-merged.cmake
index 7ebb8026236ddf..e86f7ced358f43 100644
--- a/libcxx/cmake/caches/Generic-merged.cmake
+++ b/libcxx/cmake/caches/Generic-merged.cmake
@@ -1,8 +1,7 @@
# Build a libc++ shared library, but merge libc++abi and libunwind into it.
set(LIBCXX_ENABLE_SHARED ON CACHE BOOL "")
set(LIBCXX_ENABLE_ABI_LINKER_SCRIPT OFF CACHE BOOL "")
-set(LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
-set(LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY ON CACHE BOOL "")
+set(LIBCXX_CXX_ABI "merged-libcxxabi" CACHE STRING "")
set(LIBCXXABI_ENABLE_SHARED OFF CACHE BOOL "")
set(LIBCXXABI_ENABLE_STATIC_UNWINDER ON CACHE BOOL "")
diff --git a/libcxx/cmake/caches/MinGW.cmake b/libcxx/cmake/caches/MinGW.cmake
index 09e6ea5c1bab20..595eb90974c1df 100644
--- a/libcxx/cmake/caches/MinGW.cmake
+++ b/libcxx/cmake/caches/MinGW.cmake
@@ -1,7 +1,5 @@
-set(LIBCXX_CXX_ABI libcxxabi CACHE STRING "")
-
+set(LIBCXX_CXX_ABI "merged-libcxxabi" CACHE STRING "")
set(LIBCXXABI_ENABLE_SHARED OFF CACHE BOOL "")
-set(LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
set(LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
set(LIBCXXABI_USE_COMPILER_RT ON CACHE BOOL "")
diff --git a/libcxx/cmake/caches/NVPTX.cmake b/libcxx/cmake/caches/NVPTX.cmake
index b6ec6c04ea700c..b7e93c8e9b1d0c 100644
--- a/libcxx/cmake/caches/NVPTX.cmake
+++ b/libcxx/cmake/caches/NVPTX.cmake
@@ -1,5 +1,5 @@
# Configuration options for libcxx.
-set(LIBCXX_CXX_ABI libcxxabi CACHE STRING "")
+set(LIBCXX_CXX_ABI "merged-libcxxabi" CACHE STRING "")
set(LIBCXX_ENABLE_EXCEPTIONS OFF CACHE BOOL "")
set(LIBCXX_ENABLE_FILESYSTEM OFF CACHE BOOL "")
set(LIBCXX_ENABLE_LOCALIZATION OFF CACHE BOOL "")
@@ -8,7 +8,6 @@ set(LIBCXX_ENABLE_NEW_DELETE_DEFINITIONS ON CACHE BOOL "")
set(LIBCXX_ENABLE_RANDOM_DEVICE OFF CACHE BOOL "")
set(LIBCXX_ENABLE_RTTI OFF CACHE BOOL "")
set(LIBCXX_ENABLE_SHARED OFF CACHE BOOL "")
-set(LIBCXX_ENABLE_STATIC_ABI_LIBRARY ON CACHE BOOL "")
set(LIBCXX_ENABLE_STATIC ON CACHE BOOL "")
set(LIBCXX_ENABLE_THREADS OFF CACHE BOOL "")
set(LIBCXX_ENABLE_UNICODE OFF CACHE BOOL "")
@@ -16,7 +15,6 @@ set(LIBCXX_ENABLE_WIDE_CHARACTERS OFF CACHE BOOL "")
set(LIBCXX_HAS_TERMINAL_AVAILABLE OFF CACHE BOOL "")
set(LIBCXX_INSTALL_LIBRARY ON CACHE BOOL "")
set(LIBCXX_LIBC "llvm-libc" CACHE STRING "")
-set(LIBCXX_STATICALLY_LINK_ABI_IN_STATIC_LIBRARY ON CACHE BOOL "")
set(LIBCXX_USE_COMPILER_RT ON CACHE BOOL "")
# Configuration options for libcxxabi.
diff --git a/libcxx/docs/ReleaseNotes/20.rst b/libcxx/docs/ReleaseNotes/20.rst
index 9039c6f046445b..41390891195525 100644
--- a/libcxx/docs/ReleaseNotes/20.rst
+++ b/libcxx/docs/ReleaseNotes/20.rst
@@ -144,4 +144,8 @@ ABI Affecting Changes
Build System Changes
--------------------
-- TODO
+- The following CMake options to control how the ABI library is linked into libc++ have been deprecated:
+ ``LIBCXX_ENABLE_STATIC_ABI_LIBRARY``, ``LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY``,
+ ``LIBCXX_STATICALLY_LINK_ABI_IN_STATIC_LIBRARY``. If you want to merge the objects of libc++abi into
+ libc++, please specify ``-DLIBCXX_CXX_ABI=merged-libcxxabi`` instead. These options will be
+ removed entirely in LLVM 21.
diff --git a/libcxx/docs/VendorDocumentation.rst b/libcxx/docs/VendorDocumentation.rst
index 959a28607d75dd..ac41dd1d9e0b5a 100644
--- a/libcxx/docs/VendorDocumentation.rst
+++ b/libcxx/docs/VendorDocumentation.rst
@@ -304,10 +304,20 @@ The following options allow building libc++ for a different ABI version.
See ``include/__config`` for the list of ABI macros.
.. option:: LIBCXX_CXX_ABI:STRING
+.. option:: LIBCXX_ABILIB_FOR_SHARED:STRING
+.. option:: LIBCXX_ABILIB_FOR_STATIC:STRING
**Values**: ``none``, ``libcxxabi``, ``system-libcxxabi``, ``libcxxrt``, ``libstdc++``, ``libsupc++``, ``vcruntime``.
- Select the ABI library to build libc++ against.
+ Select the ABI library to build libc++ against. This CMake option also supports "consumption specifiers", which
+ specify how the selected ABI library should be consumed by libc++. The supported specifiers are:
+ - ``shared``: The selected ABI library should be used as a shared library.
+ - ``static``: The selected ABI library should be used as a static library.
+ - ``merged``: The selected ABI library should be a static library whose object files will be merged directly into the produced libc++ library.
+
+ A consumption specifier is provided by appending it to the name of the library, such as ``LIBCXX_CXX_ABI=merged-libcxxabi``.
+ If no consumption specifier is provided, the libc++ shared library will default to using a shared ABI library, and the
+ libc++ static library will default to using a static ABI library.
.. option:: LIBCXX_CXX_ABI_INCLUDE_PATHS:PATHS
@@ -318,17 +328,10 @@ The following options allow building libc++ for a different ABI version.
Provide the path to the ABI library that libc++ should link against. This is only
useful when linking against an out-of-tree ABI library.
-.. option:: LIBCXX_ENABLE_STATIC_ABI_LIBRARY:BOOL
-
- **Default**: ``OFF``
-
- If this option is enabled, libc++ will try and link the selected ABI library
- statically.
-
.. option:: LIBCXX_ENABLE_ABI_LINKER_SCRIPT:BOOL
**Default**: ``ON`` by default on UNIX platforms other than Apple unless
- 'LIBCXX_ENABLE_STATIC_ABI_LIBRARY' is ON. Otherwise the default value is ``OFF``.
+ using the ``merged-libcxxabi`` ABI library. Otherwise the default value is ``OFF``.
This option generate and installs a linker script as ``libc++.so`` which
links the correct ABI library.
@@ -444,8 +447,7 @@ e.g. the ``mingw-w64-x86_64-clang`` package), together with CMake and ninja.
-DCMAKE_CXX_COMPILER=clang++ \
-DLLVM_ENABLE_LLD=ON \
-DLLVM_ENABLE_RUNTIMES="libcxx;libcxxabi" \
- -DLIBCXXABI_ENABLE_SHARED=OFF \
- -DLIBCXX_ENABLE_STATIC_ABI_LIBRARY=ON
+ -DLIBCXX_CXX_ABI="merged-libcxxabi"
> ninja -C build cxx
> ninja -C build check-cxx
diff --git a/libcxx/include/CMakeLists.txt b/libcxx/include/CMakeLists.txt
index 0ae031e5365aef..f555ac4b6ab86e 100644
--- a/libcxx/include/CMakeLists.txt
+++ b/libcxx/include/CMakeLists.txt
@@ -1070,7 +1070,7 @@ list(APPEND _all_includes "${LIBCXX_GENERATED_INCLUDE_DIR}/libcxx.imp")
add_custom_target(generate-cxx-headers ALL DEPENDS ${_all_includes})
add_library(cxx-headers INTERFACE)
-target_link_libraries(cxx-headers INTERFACE libcxx-libc-headers libcxx-abi-headers)
+target_link_libraries(cxx-headers INTERFACE libcxx-libc-headers)
add_dependencies(cxx-headers generate-cxx-headers)
# It's important that the arch directory be included first so that its header files
# which interpose on the default include dir be included instead of the default ones.
diff --git a/libcxx/src/CMakeLists.txt b/libcxx/src/CMakeLists.txt
index cce8b8976f73c0..f08a64018b49ee 100644
--- a/libcxx/src/CMakeLists.txt
+++ b/libcxx/src/CMakeLists.txt
@@ -174,11 +174,13 @@ split_list(LIBCXX_COMPILE_FLAGS)
split_list(LIBCXX_LINK_FLAGS)
include(FindLibcCommonUtils)
+include(HandleLibC)
+include(HandleLibCXXABI)
# Build the shared library.
add_library(cxx_shared SHARED ${LIBCXX_SOURCES} ${LIBCXX_HEADERS})
target_include_directories(cxx_shared PRIVATE ${CMAKE_CURRENT_SOURCE_DIR})
-target_link_libraries(cxx_shared PUBLIC cxx-headers libcxx-libc-shared
+target_link_libraries(cxx_shared PUBLIC cxx-headers libcxx-libc-shared libcxx-abi-shared
PRIVATE ${LIBCXX_LIBRARIES}
PRIVATE llvm-libc-common-utilities)
set_target_properties(cxx_shared
@@ -203,17 +205,10 @@ if(ZOS)
)
endif()
-# Link against libc++abi
-if (LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY)
- target_link_libraries(cxx_shared PRIVATE libcxx-abi-shared-objects)
-else()
- target_link_libraries(cxx_shared PUBLIC libcxx-abi-shared)
-endif()
-
# Maybe force some symbols to be weak, not weak or not exported.
# TODO: This shouldn't depend on the platform, and ideally it should be done in the sources.
-if (APPLE AND LIBCXX_CXX_ABI MATCHES "libcxxabi$"
- AND NOT LIBCXX_STATICALLY_LINK_ABI_IN_SHARED_LIBRARY)
+if (APPLE AND LIBCXX_ABILIB_FOR_SHARED MATCHES "(.*)libcxxabi$"
+ AND NOT LIBCXX_ABILIB_FOR_SHARED MATCHES "^merged-(.+)")
target_link_libraries(cxx_shared PRIVATE
"-Wl,-force_symbols_not_weak_list,${CMAKE_CURRENT_SOURCE_DIR}/../lib/notweak.exp"
"-Wl,-force_symbols_weak_list,${CMAKE_CURRENT_SOURCE_DIR}/../lib/weak.exp")
@@ -301,10 +296,6 @@ endif()
if (LIBCXX_ENABLE_STATIC)
list(APPEND LIBCXX_BUILD_TARGETS "cxx_static")
endif()
-# Attempt to merge the libc++.a archive and the ABI library archive into one.
-if (LIBCXX_STATICALLY_LINK_ABI_IN_STATIC_LIBRARY)
- target_link_libraries(cxx_static PRIVATE libcxx-abi-static-objects)
-endif()
# Add a meta-target for both libraries.
add_custom_target(cxx DEPENDS ${LIBCXX_BUILD_TARGETS})
diff --git a/libcxx/utils/ci/run-buildbot b/libcxx/utils/ci/run-buildbot
index 3df7b00a8aa09d..0873c92e75d03b 100755
--- a/libcxx/utils/ci/run-buildbot
+++ b/libcxx/utils/ci/run-buildbot
@@ -143,7 +143,6 @@ function generate-cmake-base() {
function generate-cmake() {
generate-cmake-base \
-DLLVM_ENABLE_RUNTIMES="libcxx;libcxxabi;libunwind" \
- -DLIBCXX_CXX_ABI=libcxxabi \
"${@}"
}
@@ -158,7 +157,6 @@ function generate-cmake-libcxx-win() {
function generate-cmake-android() {
generate-cmake-base \
-DLLVM_ENABLE_RUNTIMES="libcxx;libcxxabi" \
- -DLIBCXX_CXX_ABI=libcxxabi \
"${@}"
}
@@ -560,7 +558,6 @@ apple-system-hardened)
-DCMAKE_INSTALL_PREFIX="${INSTALL_DIR}/cxx" \
-DLLVM_LIT_ARGS="-sv --xunit-xml-output test-results.xml --timeout=1500 --time-tests" \
-DLLVM_ENABLE_RUNTIMES="libcxx;libcxxabi" \
- -DLIBCXX_CXX_ABI=libcxxabi \
-C "${MONOREPO_ROOT}/libcxx/cmake/caches/Apple.cmake" \
-DLIBCXX_TEST_CONFIG="apple-libc++-system.cfg.in" \
-DLIBCXXABI_TEST_CONFIG="apple-libc++abi-system.cfg.in" \
@@ -606,7 +603,6 @@ apple-system)
-DCMAKE_INSTALL_PREFIX="${INSTALL_DIR}/cxx" \
-DLLVM_LIT_ARGS="-sv --xunit-xml-output test-results.xml --timeout=1500 --time-tests" \
-DLLVM_ENABLE_RUNTIMES="libcxx;libcxxabi" \
- -DLIBCXX_CXX_ABI=libcxxabi \
-C "${MONOREPO_ROOT}/libcxx/cmake/caches/Apple.cmake" \
-DLIBCXX_TEST_CONFIG="apple-libc++-system.cfg.in" \
-DLIBCXXABI_TEST_CONFIG="apple-libc++abi-system.cfg.in" \
diff --git a/llvm/docs/HowToBuildWindowsItaniumPrograms.rst b/llvm/docs/HowToBuildWindowsItaniumPrograms.rst
index 48ca7b25b11ef8..0c972330bc4fbf 100644
--- a/llvm/docs/HowToBuildWindowsItaniumPrograms.rst
+++ b/llvm/docs/HowToBuildWindowsItaniumPrograms.rst
@@ -110,13 +110,14 @@ We use the MS runtime.
The CMake files will need to be edited to prevent them adding GNU specific libraries to the link line.
-Building libc++abi:
--------------------
+Building libc++ and libc++abi:
+------------------------------
+* ``-DLIBCXX_ENABLE_SHARED=ON``
+* ``-DLIBCXX_ENABLE_STATIC=OFF``
+* ``-DLIBCXX_CXX_ABI="merged-libcxxabi"``
* ``-DLIBCXXABI_ENABLE_SHARED=OFF``
* ``-DLIBCXXABI_ENABLE_STATIC=ON``
-* ``-DLIBCXX_ENABLE_SHARED=ON'``
-* ``-DLIBCXX_ENABLE_STATIC_ABI_LIBRARY=ON``
To break the symbol dependency between libc++abi and libc++ we
build libc++abi as a static library and then statically link it
@@ -125,18 +126,6 @@ to ensure that the visibility macros (which expand to dllexport/import)
are expanded as they will be needed when creating the final libc++
DLL later, see: https://reviews.llvm.org/D90021.
-* ``-DLIBCXXABI_LIBCXX_INCLUDES=<path to libcxx>/include``
-
-Where to find the libc++ headers
-
-Building libc++:
-----------------
-
-* ``-DLIBCXX_ENABLE_SHARED=ON``
-* ``-DLIBCXX_ENABLE_STATIC=OFF``
-
-We build libc++ as a DLL and statically link libc++abi into it.
-
* ``-DLIBCXX_INSTALL_HEADERS=ON``
Install the headers.
@@ -149,13 +138,6 @@ We use the MS runtime.
Windows Itanium does not offer a POSIX-like layer over WIN32.
-* ``-DLIBCXX_ENABLE_STATIC_ABI_LIBRARY=ON``
-* ``-DLIBCXX_CXX_ABI=libcxxabi``
-* ``-DLIBCXX_CXX_ABI_INCLUDE_PATHS=<libcxxabi src path>/include``
-* ``-DLIBCXX_CXX_ABI_LIBRARY_PATH=<libcxxabi build path>/lib``
-
-Use the static libc++abi library built earlier.
-
* ``-DLIBCXX_NO_VCRUNTIME=ON``
Remove any dependency on the VC runtime - we need libc++abi to supply the C++ runtime.
>From d149f83a396f100d09e08f02fab9bd79735a6d84 Mon Sep 17 00:00:00 2001
From: Louis Dionne <ldionne.2 at gmail.com>
Date: Mon, 21 Oct 2024 10:43:38 -0400
Subject: [PATCH 2/4] Fix indentation in documentation
---
libcxx/docs/VendorDocumentation.rst | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/libcxx/docs/VendorDocumentation.rst b/libcxx/docs/VendorDocumentation.rst
index ac41dd1d9e0b5a..e46110e79f58c4 100644
--- a/libcxx/docs/VendorDocumentation.rst
+++ b/libcxx/docs/VendorDocumentation.rst
@@ -311,9 +311,9 @@ The following options allow building libc++ for a different ABI version.
Select the ABI library to build libc++ against. This CMake option also supports "consumption specifiers", which
specify how the selected ABI library should be consumed by libc++. The supported specifiers are:
- - ``shared``: The selected ABI library should be used as a shared library.
- - ``static``: The selected ABI library should be used as a static library.
- - ``merged``: The selected ABI library should be a static library whose object files will be merged directly into the produced libc++ library.
+ - ``shared``: The selected ABI library should be used as a shared library.
+ - ``static``: The selected ABI library should be used as a static library.
+ - ``merged``: The selected ABI library should be a static library whose object files will be merged directly into the produced libc++ library.
A consumption specifier is provided by appending it to the name of the library, such as ``LIBCXX_CXX_ABI=merged-libcxxabi``.
If no consumption specifier is provided, the libc++ shared library will default to using a shared ABI library, and the
>From 81b197b036a1ddc62f7fc8bcf196a4cbf6ba0f7a Mon Sep 17 00:00:00 2001
From: Louis Dionne <ldionne.2 at gmail.com>
Date: Mon, 21 Oct 2024 11:29:54 -0400
Subject: [PATCH 3/4] Simplify and fix dependencies for headers
---
libcxx/cmake/Modules/HandleLibCXXABI.cmake | 71 +++++++++++-----------
1 file changed, 36 insertions(+), 35 deletions(-)
diff --git a/libcxx/cmake/Modules/HandleLibCXXABI.cmake b/libcxx/cmake/Modules/HandleLibCXXABI.cmake
index fa4b761e818021..689306d46587f1 100644
--- a/libcxx/cmake/Modules/HandleLibCXXABI.cmake
+++ b/libcxx/cmake/Modules/HandleLibCXXABI.cmake
@@ -20,7 +20,7 @@ include(GNUInstallDirs)
# 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)
+function(_import_private_headers target include_dirs headers)
if (NOT ${include_dirs})
message(FATAL_ERROR "Missing include paths for the selected ABI library!")
endif()
@@ -58,15 +58,14 @@ function(import_private_headers target include_dirs headers)
target_include_directories(${target} INTERFACE "${LIBCXX_BINARY_DIR}/private-abi-headers/${target}")
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}")
+# This function adds linker flags to a <target> appropriate for merging the object
+# files of another static <library> into whoever links against <target>.
+function(_merge_static_library target library)
+ if (APPLE)
+ target_link_options(${target} INTERFACE "-Wl,-force_load" "${library}")
+ else()
+ target_link_options(${target} INTERFACE "-Wl,--whole-archive" "-Wl,-Bstatic" "${library}" "-Wl,-Bdynamic" "-Wl,--no-whole-archive")
+ endif()
endfunction()
# This function creates a library target for linking against an external ABI library.
@@ -75,7 +74,7 @@ endfunction()
# <name>: The name of the library file to search for (e.g. c++abi, stdc++, cxxrt, supc++)
# <type>: Whether to set up a static or a shared library (e.g. SHARED or STATIC)
# <merged>: Whether to include the ABI library's object files directly into libc++. Only makes sense for a static ABI library.
-function(import_external_abi_library target name type merged)
+function(_import_external_abi_library target name type merged)
if (${merged} AND "${type}" STREQUAL "SHARED")
message(FATAL_ERROR "Can't import an external ABI library for merging when requesting a shared ABI library.")
endif()
@@ -83,21 +82,23 @@ function(import_external_abi_library target name type merged)
if ("${type}" STREQUAL "SHARED")
add_library(${target} INTERFACE IMPORTED GLOBAL)
set_target_properties(${target} PROPERTIES IMPORTED_LIBNAME "${name}")
+
elseif ("${type}" STREQUAL "STATIC")
+ add_library(${target}-imported STATIC IMPORTED GLOBAL)
+ find_library(file
+ NAMES "${CMAKE_STATIC_LIBRARY_PREFIX}${name}${CMAKE_STATIC_LIBRARY_SUFFIX}"
+ PATHS "${LIBCXX_CXX_ABI_LIBRARY_PATH}"
+ NO_CACHE)
+ if (NOT "${file}")
+ message(FATAL_ERROR "Failed to find static library ${name} at path ${LIBCXX_CXX_ABI_LIBRARY_PATH}")
+ endif()
+ set_target_properties(${target}-imported PROPERTIES IMPORTED_LOCATION "${file}")
+
+ add_library(${target} INTERFACE)
if (${merged})
- import_static_library(${target}-impl "${LIBCXX_CXX_ABI_LIBRARY_PATH}" ${name})
- add_library(${target} INTERFACE)
- if (APPLE)
- target_link_options(${target} INTERFACE
- "-Wl,-force_load" "$<TARGET_PROPERTY:${target}-impl,IMPORTED_LOCATION>")
- else()
- target_link_options(${target} INTERFACE
- "-Wl,--whole-archive" "-Wl,-Bstatic"
- "$<TARGET_PROPERTY:${target}-impl,IMPORTED_LOCATION>"
- "-Wl,-Bdynamic" "-Wl,--no-whole-archive")
- endif()
+ _merge_static_library(${target} "$<TARGET_PROPERTY:${target}-imported,IMPORTED_LOCATION>")
else()
- import_static_library(${target} "${LIBCXX_CXX_ABI_LIBRARY_PATH}" ${name})
+ target_link_libraries(${target} INTERFACE ${target}-imported)
endif()
endif()
endfunction()
@@ -133,22 +134,22 @@ function(setup_abi_library abi_target linked_into input)
# Link against a system-provided libstdc++
if ("${stdlib}" STREQUAL "libstdc++")
- import_external_abi_library(${abi_target} stdc++ ${search_type} ${merged})
- import_private_headers(${abi_target} "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
+ _import_external_abi_library(${abi_target} stdc++ ${search_type} ${merged})
+ _import_private_headers(${abi_target} "${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(${abi_target} INTERFACE "-DLIBSTDCXX" "-D__GLIBCXX__")
# Link against a system-provided libsupc++
elseif ("${stdlib}" STREQUAL "libsupc++")
- import_external_abi_library(${abi_target} supc++ ${search_type} ${merged})
- import_private_headers(${abi_target} "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
+ _import_external_abi_library(${abi_target} supc++ ${search_type} ${merged})
+ _import_private_headers(${abi_target} "${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(${abi_target} INTERFACE "-D__GLIBCXX__")
# Link against a system-provided libcxxrt
elseif ("${stdlib}" STREQUAL "libcxxrt")
- import_external_abi_library(${abi_target} cxxrt ${search_type} ${merged})
- import_private_headers(${abi_target} "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
+ _import_external_abi_library(${abi_target} cxxrt ${search_type} ${merged})
+ _import_private_headers(${abi_target} "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
"cxxabi.h;unwind.h;unwind-arm.h;unwind-itanium.h")
target_compile_definitions(${abi_target} INTERFACE "-DLIBCXXRT")
@@ -159,18 +160,18 @@ function(setup_abi_library abi_target linked_into input)
# Link against a system-provided libc++abi
elseif ("${stdlib}" STREQUAL "system-libcxxabi")
- import_external_abi_library(${abi_target} c++abi ${search_type} ${merged})
- import_private_headers(${abi_target} "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
+ _import_external_abi_library(${abi_target} c++abi ${search_type} ${merged})
+ _import_private_headers(${abi_target} "${LIBCXX_CXX_ABI_INCLUDE_PATHS}"
"cxxabi.h;__cxxabi_config.h")
target_compile_definitions(${abi_target} INTERFACE "-DLIBCXX_BUILDING_LIBCXXABI")
# Link against the in-tree libc++abi.
elseif ("${stdlib}" STREQUAL "libcxxabi")
if (${merged})
- get_target_property(_outdir cxxabi_static ARCHIVE_OUTPUT_DIRECTORY)
- get_target_property(_outname cxxabi_static OUTPUT_NAME)
- set(LIBCXX_CXX_ABI_LIBRARY_PATH "${_outdir}")
- import_external_abi_library(${abi_target} "${_outname}" STATIC TRUE)
+ add_library(${abi_target} INTERFACE)
+ _merge_static_library(${abi_target}
+ "$<TARGET_PROPERTY:cxxabi_static,LIBRARY_OUTPUT_DIRECTORY>/${CMAKE_STATIC_LIBRARY_PREFIX}$<TARGET_PROPERTY:cxxabi_static,OUTPUT_NAME>${CMAKE_STATIC_LIBRARY_SUFFIX}")
+ target_link_libraries(${abi_target} INTERFACE cxxabi-headers)
else()
string(TOLOWER "${search_type}" type)
add_library(${abi_target} INTERFACE)
>From 614968a1557b95e84daba431703c34adacafa2ea Mon Sep 17 00:00:00 2001
From: Louis Dionne <ldionne.2 at gmail.com>
Date: Tue, 22 Oct 2024 16:02:45 -0400
Subject: [PATCH 4/4] Fix missing dependency on cxxabi_static
---
libcxx/cmake/Modules/HandleLibCXXABI.cmake | 1 +
1 file changed, 1 insertion(+)
diff --git a/libcxx/cmake/Modules/HandleLibCXXABI.cmake b/libcxx/cmake/Modules/HandleLibCXXABI.cmake
index 689306d46587f1..4a6cfe0cf84fdc 100644
--- a/libcxx/cmake/Modules/HandleLibCXXABI.cmake
+++ b/libcxx/cmake/Modules/HandleLibCXXABI.cmake
@@ -172,6 +172,7 @@ function(setup_abi_library abi_target linked_into input)
_merge_static_library(${abi_target}
"$<TARGET_PROPERTY:cxxabi_static,LIBRARY_OUTPUT_DIRECTORY>/${CMAKE_STATIC_LIBRARY_PREFIX}$<TARGET_PROPERTY:cxxabi_static,OUTPUT_NAME>${CMAKE_STATIC_LIBRARY_SUFFIX}")
target_link_libraries(${abi_target} INTERFACE cxxabi-headers)
+ add_dependencies(${abi_target} cxxabi_static)
else()
string(TOLOWER "${search_type}" type)
add_library(${abi_target} INTERFACE)
More information about the cfe-commits
mailing list