[libcxx-commits] [libcxx] 4356228 - [libc++] Granularize <exception>
Nikolas Klauser via libcxx-commits
libcxx-commits at lists.llvm.org
Sun Mar 12 14:19:47 PDT 2023
Author: Nikolas Klauser
Date: 2023-03-12T22:19:41+01:00
New Revision: 43562287a816c74be390478d32adc0cb4c4abca4
URL: https://github.com/llvm/llvm-project/commit/43562287a816c74be390478d32adc0cb4c4abca4
DIFF: https://github.com/llvm/llvm-project/commit/43562287a816c74be390478d32adc0cb4c4abca4.diff
LOG: [libc++] Granularize <exception>
This patch also updates the moved code to the new style (i.e. formatted, replaced marcos and typedefs)
Reviewed By: ldionne, #libc
Spies: arichardson, libcxx-commits
Differential Revision: https://reviews.llvm.org/D145095
Added:
libcxx/include/__exception/exception.h
libcxx/include/__exception/exception_ptr.h
libcxx/include/__exception/nested_exception.h
libcxx/include/__exception/operations.h
libcxx/include/__exception/terminate.h
Modified:
libcxx/include/CMakeLists.txt
libcxx/include/__format/formatter_integral.h
libcxx/include/__iterator/common_iterator.h
libcxx/include/__memory/allocator.h
libcxx/include/__memory/shared_ptr.h
libcxx/include/__tree
libcxx/include/any
libcxx/include/deque
libcxx/include/exception
libcxx/include/istream
libcxx/include/libcxx.imp
libcxx/include/module.modulemap.in
libcxx/include/optional
libcxx/include/ostream
libcxx/include/span
libcxx/include/string
libcxx/include/string_view
libcxx/include/valarray
libcxx/include/variant
libcxx/include/vector
libcxx/test/libcxx/private_headers.verify.cpp
libcxx/test/std/containers/sequences/array/contiguous.pass.cpp
libcxx/test/std/utilities/memory/allocator.uses/allocator.uses.trait/uses_allocator.pass.cpp
libcxx/utils/data/ignore_format.txt
Removed:
################################################################################
diff --git a/libcxx/include/CMakeLists.txt b/libcxx/include/CMakeLists.txt
index 34932dee692ed..f8b00e9918e22 100644
--- a/libcxx/include/CMakeLists.txt
+++ b/libcxx/include/CMakeLists.txt
@@ -297,6 +297,11 @@ set(files
__debug
__debug_utils/randomize_range.h
__errc
+ __exception/exception.h
+ __exception/exception_ptr.h
+ __exception/nested_exception.h
+ __exception/operations.h
+ __exception/terminate.h
__expected/bad_expected_access.h
__expected/expected.h
__expected/unexpect.h
diff --git a/libcxx/include/__exception/exception.h b/libcxx/include/__exception/exception.h
new file mode 100644
index 0000000000000..49a58dd16999a
--- /dev/null
+++ b/libcxx/include/__exception/exception.h
@@ -0,0 +1,91 @@
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___EXCEPTION_EXCEPTION_H
+#define _LIBCPP___EXCEPTION_EXCEPTION_H
+
+#include <__config>
+
+// <vcruntime_exception.h> defines its own std::exception and std::bad_exception types,
+// which we use in order to be ABI-compatible with other STLs on Windows.
+#if defined(_LIBCPP_ABI_VCRUNTIME)
+# include <vcruntime_exception.h>
+#endif
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+# pragma GCC system_header
+#endif
+
+namespace std { // purposefully not using versioning namespace
+
+#if defined(_LIBCPP_ABI_VCRUNTIME) && (!defined(_HAS_EXCEPTIONS) || _HAS_EXCEPTIONS != 0)
+// The std::exception class was already included above, but we're explicit about this condition here for clarity.
+
+#elif defined(_LIBCPP_ABI_VCRUNTIME) && _HAS_EXCEPTIONS == 0
+// However, <vcruntime_exception.h> does not define std::exception and std::bad_exception
+// when _HAS_EXCEPTIONS == 0.
+//
+// Since libc++ still wants to provide the std::exception hierarchy even when _HAS_EXCEPTIONS == 0
+// (after all those are simply types like any other), we define an ABI-compatible version
+// of the VCRuntime std::exception and std::bad_exception types in that mode.
+
+struct __std_exception_data {
+ char const* _What;
+ bool _DoFree;
+};
+
+class exception { // base of all library exceptions
+public:
+ exception() _NOEXCEPT : __data_() {}
+
+ explicit exception(char const* __message) _NOEXCEPT : __data_() {
+ __data_._What = __message;
+ __data_._DoFree = true;
+ }
+
+ exception(exception const&) _NOEXCEPT {}
+
+ exception& operator=(exception const&) _NOEXCEPT { return *this; }
+
+ virtual ~exception() _NOEXCEPT {}
+
+ virtual char const* what() const _NOEXCEPT { return __data_._What ? __data_._What : "Unknown exception"; }
+
+private:
+ __std_exception_data __data_;
+};
+
+class bad_exception : public exception {
+public:
+ bad_exception() _NOEXCEPT : exception("bad exception") {}
+};
+
+#else // !defined(_LIBCPP_ABI_VCRUNTIME)
+// On all other platforms, we define our own std::exception and std::bad_exception types
+// regardless of whether exceptions are turned on as a language feature.
+
+class _LIBCPP_EXCEPTION_ABI exception {
+public:
+ _LIBCPP_HIDE_FROM_ABI exception() _NOEXCEPT {}
+ _LIBCPP_HIDE_FROM_ABI exception(const exception&) _NOEXCEPT = default;
+
+ virtual ~exception() _NOEXCEPT;
+ virtual const char* what() const _NOEXCEPT;
+};
+
+class _LIBCPP_EXCEPTION_ABI bad_exception : public exception {
+public:
+ _LIBCPP_HIDE_FROM_ABI bad_exception() _NOEXCEPT {}
+ ~bad_exception() _NOEXCEPT override;
+ const char* what() const _NOEXCEPT override;
+};
+#endif // !_LIBCPP_ABI_VCRUNTIME
+
+} // namespace std
+
+#endif // _LIBCPP___EXCEPTION_EXCEPTION_H
diff --git a/libcxx/include/__exception/exception_ptr.h b/libcxx/include/__exception/exception_ptr.h
new file mode 100644
index 0000000000000..9c77ebf74d515
--- /dev/null
+++ b/libcxx/include/__exception/exception_ptr.h
@@ -0,0 +1,108 @@
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___EXCEPTION_EXCEPTION_PTR_H
+#define _LIBCPP___EXCEPTION_EXCEPTION_PTR_H
+
+#include <__config>
+#include <__exception/operations.h>
+#include <cstddef>
+#include <cstdlib>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+# pragma GCC system_header
+#endif
+
+namespace std { // purposefully not using versioning namespace
+
+#ifndef _LIBCPP_ABI_MICROSOFT
+
+class _LIBCPP_TYPE_VIS exception_ptr {
+ void* __ptr_;
+
+public:
+ _LIBCPP_HIDE_FROM_ABI exception_ptr() _NOEXCEPT : __ptr_() {}
+ _LIBCPP_HIDE_FROM_ABI exception_ptr(nullptr_t) _NOEXCEPT : __ptr_() {}
+
+ exception_ptr(const exception_ptr&) _NOEXCEPT;
+ exception_ptr& operator=(const exception_ptr&) _NOEXCEPT;
+ ~exception_ptr() _NOEXCEPT;
+
+ _LIBCPP_HIDE_FROM_ABI explicit operator bool() const _NOEXCEPT { return __ptr_ != nullptr; }
+
+ friend _LIBCPP_HIDE_FROM_ABI bool operator==(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT {
+ return __x.__ptr_ == __y.__ptr_;
+ }
+
+ friend _LIBCPP_HIDE_FROM_ABI bool operator!=(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT {
+ return !(__x == __y);
+ }
+
+ friend _LIBCPP_FUNC_VIS exception_ptr current_exception() _NOEXCEPT;
+ friend _LIBCPP_FUNC_VIS void rethrow_exception(exception_ptr);
+};
+
+template <class _Ep>
+_LIBCPP_HIDE_FROM_ABI exception_ptr make_exception_ptr(_Ep __e) _NOEXCEPT {
+# ifndef _LIBCPP_HAS_NO_EXCEPTIONS
+ try {
+ throw __e;
+ } catch (...) {
+ return current_exception();
+ }
+# else
+ ((void)__e);
+ std::abort();
+# endif
+}
+
+#else // _LIBCPP_ABI_MICROSOFT
+
+class _LIBCPP_TYPE_VIS exception_ptr {
+ _LIBCPP_DIAGNOSTIC_PUSH
+ _LIBCPP_CLANG_DIAGNOSTIC_IGNORED("-Wunused-private-field")
+ void* __ptr1_;
+ void* __ptr2_;
+ _LIBCPP_DIAGNOSTIC_POP
+
+public:
+ exception_ptr() _NOEXCEPT;
+ exception_ptr(nullptr_t) _NOEXCEPT;
+ exception_ptr(const exception_ptr& __other) _NOEXCEPT;
+ exception_ptr& operator=(const exception_ptr& __other) _NOEXCEPT;
+ exception_ptr& operator=(nullptr_t) _NOEXCEPT;
+ ~exception_ptr() _NOEXCEPT;
+ explicit operator bool() const _NOEXCEPT;
+};
+
+_LIBCPP_FUNC_VIS bool operator==(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT;
+
+inline _LIBCPP_HIDE_FROM_ABI bool operator!=(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT {
+ return !(__x == __y);
+}
+
+_LIBCPP_FUNC_VIS void swap(exception_ptr&, exception_ptr&) _NOEXCEPT;
+
+_LIBCPP_FUNC_VIS exception_ptr __copy_exception_ptr(void* __except, const void* __ptr);
+_LIBCPP_FUNC_VIS exception_ptr current_exception() _NOEXCEPT;
+_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void rethrow_exception(exception_ptr);
+
+// This is a built-in template function which automagically extracts the required
+// information.
+template <class _E>
+void* __GetExceptionInfo(_E);
+
+template <class _Ep>
+_LIBCPP_HIDE_FROM_ABI exception_ptr make_exception_ptr(_Ep __e) _NOEXCEPT {
+ return __copy_exception_ptr(std::addressof(__e), __GetExceptionInfo(__e));
+}
+
+#endif // _LIBCPP_ABI_MICROSOFT
+} // namespace std
+
+#endif // _LIBCPP___EXCEPTION_EXCEPTION_PTR_H
diff --git a/libcxx/include/__exception/nested_exception.h b/libcxx/include/__exception/nested_exception.h
new file mode 100644
index 0000000000000..b842dde03e16a
--- /dev/null
+++ b/libcxx/include/__exception/nested_exception.h
@@ -0,0 +1,101 @@
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___EXCEPTION_NESTED_EXCEPTION_H
+#define _LIBCPP___EXCEPTION_NESTED_EXCEPTION_H
+
+#include <__config>
+#include <__exception/exception_ptr.h>
+#include <__memory/addressof.h>
+#include <__type_traits/decay.h>
+#include <__type_traits/is_base_of.h>
+#include <__type_traits/is_class.h>
+#include <__type_traits/is_convertible.h>
+#include <__type_traits/is_copy_constructible.h>
+#include <__type_traits/is_final.h>
+#include <__type_traits/is_polymorphic.h>
+#include <__utility/forward.h>
+#include <cstddef>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+# pragma GCC system_header
+#endif
+
+namespace std { // purposefully not using versioning namespace
+
+class _LIBCPP_EXCEPTION_ABI nested_exception {
+ exception_ptr __ptr_;
+
+public:
+ nested_exception() _NOEXCEPT;
+ // nested_exception(const nested_exception&) noexcept = default;
+ // nested_exception& operator=(const nested_exception&) noexcept = default;
+ virtual ~nested_exception() _NOEXCEPT;
+
+ // access functions
+ _LIBCPP_NORETURN void rethrow_nested() const;
+ _LIBCPP_HIDE_FROM_ABI exception_ptr nested_ptr() const _NOEXCEPT { return __ptr_; }
+};
+
+template <class _Tp>
+struct __nested : public _Tp, public nested_exception {
+ _LIBCPP_HIDE_FROM_ABI explicit __nested(const _Tp& __t) : _Tp(__t) {}
+};
+
+#ifndef _LIBCPP_HAS_NO_EXCEPTIONS
+template <class _Tp, class _Up, bool>
+struct __throw_with_nested;
+
+template <class _Tp, class _Up>
+struct __throw_with_nested<_Tp, _Up, true> {
+ _LIBCPP_NORETURN static inline _LIBCPP_INLINE_VISIBILITY void __do_throw(_Tp&& __t) {
+ throw __nested<_Up>(std::forward<_Tp>(__t));
+ }
+};
+
+template <class _Tp, class _Up>
+struct __throw_with_nested<_Tp, _Up, false> {
+ _LIBCPP_NORETURN static inline _LIBCPP_INLINE_VISIBILITY void __do_throw(_Tp&& __t) { throw std::forward<_Tp>(__t); }
+};
+#endif
+
+template <class _Tp>
+_LIBCPP_NORETURN _LIBCPP_HIDE_FROM_ABI void throw_with_nested(_Tp&& __t) {
+#ifndef _LIBCPP_HAS_NO_EXCEPTIONS
+ typedef typename decay<_Tp>::type _Up;
+ static_assert(is_copy_constructible<_Up>::value, "type thrown must be CopyConstructible");
+ __throw_with_nested<_Tp,
+ _Up,
+ is_class<_Up>::value && !is_base_of<nested_exception, _Up>::value &&
+ !__libcpp_is_final<_Up>::value>::__do_throw(std::forward<_Tp>(__t));
+#else
+ ((void)__t);
+ // FIXME: Make this abort
+#endif
+}
+
+template <class _From, class _To>
+struct __can_dynamic_cast
+ : _BoolConstant< is_polymorphic<_From>::value &&
+ (!is_base_of<_To, _From>::value || is_convertible<const _From*, const _To*>::value)> {};
+
+template <class _Ep>
+inline _LIBCPP_HIDE_FROM_ABI void
+rethrow_if_nested(const _Ep& __e, __enable_if_t< __can_dynamic_cast<_Ep, nested_exception>::value>* = 0) {
+ const nested_exception* __nep = dynamic_cast<const nested_exception*>(std::addressof(__e));
+ if (__nep)
+ __nep->rethrow_nested();
+}
+
+template <class _Ep>
+inline _LIBCPP_HIDE_FROM_ABI void
+rethrow_if_nested(const _Ep&, __enable_if_t<!__can_dynamic_cast<_Ep, nested_exception>::value>* = 0) {}
+
+} // namespace std
+
+#endif // _LIBCPP___EXCEPTION_NESTED_EXCEPTION_H
diff --git a/libcxx/include/__exception/operations.h b/libcxx/include/__exception/operations.h
new file mode 100644
index 0000000000000..e8c5ba61ee0e2
--- /dev/null
+++ b/libcxx/include/__exception/operations.h
@@ -0,0 +1,42 @@
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___EXCEPTION_OPERATIONS_H
+#define _LIBCPP___EXCEPTION_OPERATIONS_H
+
+#include <__availability>
+#include <__config>
+#include <cstddef>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+# pragma GCC system_header
+#endif
+
+namespace std { // purposefully not using versioning namespace
+#if _LIBCPP_STD_VER <= 14 || defined(_LIBCPP_ENABLE_CXX17_REMOVED_UNEXPECTED_FUNCTIONS) || \
+ defined(_LIBCPP_BUILDING_LIBRARY)
+using unexpected_handler = void (*)();
+_LIBCPP_FUNC_VIS unexpected_handler set_unexpected(unexpected_handler) _NOEXCEPT;
+_LIBCPP_FUNC_VIS unexpected_handler get_unexpected() _NOEXCEPT;
+_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void unexpected();
+#endif
+
+using terminate_handler = void (*)();
+_LIBCPP_FUNC_VIS terminate_handler set_terminate(terminate_handler) _NOEXCEPT;
+_LIBCPP_FUNC_VIS terminate_handler get_terminate() _NOEXCEPT;
+
+_LIBCPP_FUNC_VIS bool uncaught_exception() _NOEXCEPT;
+_LIBCPP_FUNC_VIS _LIBCPP_AVAILABILITY_UNCAUGHT_EXCEPTIONS int uncaught_exceptions() _NOEXCEPT;
+
+class _LIBCPP_TYPE_VIS exception_ptr;
+
+_LIBCPP_FUNC_VIS exception_ptr current_exception() _NOEXCEPT;
+_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void rethrow_exception(exception_ptr);
+} // namespace std
+
+#endif // _LIBCPP___EXCEPTION_OPERATIONS_H
diff --git a/libcxx/include/__exception/terminate.h b/libcxx/include/__exception/terminate.h
new file mode 100644
index 0000000000000..d8dd9642b88d1
--- /dev/null
+++ b/libcxx/include/__exception/terminate.h
@@ -0,0 +1,22 @@
+//===----------------------------------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef _LIBCPP___EXCEPTION_TERMINATE_H
+#define _LIBCPP___EXCEPTION_TERMINATE_H
+
+#include <__config>
+
+#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
+# pragma GCC system_header
+#endif
+
+namespace std { // purposefully not using versioning namespace
+_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void terminate() _NOEXCEPT;
+} // namespace std
+
+#endif // _LIBCPP___EXCEPTION_TERMINATE_H
diff --git a/libcxx/include/__format/formatter_integral.h b/libcxx/include/__format/formatter_integral.h
index 8a18049618846..8cc21e43749db 100644
--- a/libcxx/include/__format/formatter_integral.h
+++ b/libcxx/include/__format/formatter_integral.h
@@ -22,6 +22,7 @@
#include <charconv>
#include <limits>
#include <string>
+#include <string_view>
#ifndef _LIBCPP_HAS_NO_LOCALIZATION
# include <locale>
diff --git a/libcxx/include/__iterator/common_iterator.h b/libcxx/include/__iterator/common_iterator.h
index 3c8eb1c00e11c..aab04ce49717f 100644
--- a/libcxx/include/__iterator/common_iterator.h
+++ b/libcxx/include/__iterator/common_iterator.h
@@ -25,6 +25,7 @@
#include <__iterator/iter_swap.h>
#include <__iterator/iterator_traits.h>
#include <__iterator/readable_traits.h>
+#include <__memory/addressof.h>
#include <__type_traits/is_pointer.h>
#include <__utility/declval.h>
#include <variant>
diff --git a/libcxx/include/__memory/allocator.h b/libcxx/include/__memory/allocator.h
index de94cfb6a2353..244013cef7b64 100644
--- a/libcxx/include/__memory/allocator.h
+++ b/libcxx/include/__memory/allocator.h
@@ -11,6 +11,7 @@
#define _LIBCPP___MEMORY_ALLOCATOR_H
#include <__config>
+#include <__memory/addressof.h>
#include <__memory/allocate_at_least.h>
#include <__memory/allocator_traits.h>
#include <__type_traits/is_constant_evaluated.h>
diff --git a/libcxx/include/__memory/shared_ptr.h b/libcxx/include/__memory/shared_ptr.h
index c5089f3f8686d..c88ced2c5bbe5 100644
--- a/libcxx/include/__memory/shared_ptr.h
+++ b/libcxx/include/__memory/shared_ptr.h
@@ -35,6 +35,7 @@
#include <__type_traits/disjunction.h>
#include <__type_traits/is_array.h>
#include <__type_traits/is_bounded_array.h>
+#include <__type_traits/is_convertible.h>
#include <__type_traits/is_move_constructible.h>
#include <__type_traits/is_reference.h>
#include <__type_traits/is_unbounded_array.h>
diff --git a/libcxx/include/__tree b/libcxx/include/__tree
index 672b92c7796ea..8b2965ae9b51c 100644
--- a/libcxx/include/__tree
+++ b/libcxx/include/__tree
@@ -18,6 +18,7 @@
#include <__iterator/distance.h>
#include <__iterator/iterator_traits.h>
#include <__iterator/next.h>
+#include <__memory/addressof.h>
#include <__memory/allocator_traits.h>
#include <__memory/compressed_pair.h>
#include <__memory/pointer_traits.h>
diff --git a/libcxx/include/any b/libcxx/include/any
index e44ec7a45b2d8..addd6d4285c0b 100644
--- a/libcxx/include/any
+++ b/libcxx/include/any
@@ -92,7 +92,9 @@ namespace std {
#include <__type_traits/aligned_storage.h>
#include <__type_traits/alignment_of.h>
#include <__type_traits/conditional.h>
+#include <__type_traits/decay.h>
#include <__type_traits/is_constructible.h>
+#include <__type_traits/is_copy_constructible.h>
#include <__type_traits/is_function.h>
#include <__type_traits/is_nothrow_move_constructible.h>
#include <__type_traits/is_reference.h>
diff --git a/libcxx/include/deque b/libcxx/include/deque
index 4ce261f2f8aa6..166a75c843fd1 100644
--- a/libcxx/include/deque
+++ b/libcxx/include/deque
@@ -181,6 +181,7 @@ template <class T, class Allocator, class Predicate>
#include <__iterator/prev.h>
#include <__iterator/reverse_iterator.h>
#include <__iterator/segmented_iterator.h>
+#include <__memory/addressof.h>
#include <__memory/allocator_destructor.h>
#include <__memory/pointer_traits.h>
#include <__memory/temp_value.h>
@@ -188,6 +189,7 @@ template <class T, class Allocator, class Predicate>
#include <__memory_resource/polymorphic_allocator.h>
#include <__split_buffer>
#include <__type_traits/is_allocator.h>
+#include <__type_traits/is_convertible.h>
#include <__type_traits/is_same.h>
#include <__type_traits/type_identity.h>
#include <__utility/forward.h>
diff --git a/libcxx/include/exception b/libcxx/include/exception
index 2b5cfd52ae186..97fee977690d0 100644
--- a/libcxx/include/exception
+++ b/libcxx/include/exception
@@ -77,304 +77,20 @@ template <class E> void rethrow_if_nested(const E& e);
*/
#include <__assert> // all public C++ headers provide the assertion handler
-#include <__availability>
#include <__config>
-#include <__memory/addressof.h>
-#include <__type_traits/decay.h>
-#include <__type_traits/is_base_of.h>
-#include <__type_traits/is_class.h>
-#include <__type_traits/is_convertible.h>
-#include <__type_traits/is_copy_constructible.h>
-#include <__type_traits/is_final.h>
-#include <__type_traits/is_polymorphic.h>
-#include <__utility/forward.h>
-#include <cstddef>
-#include <cstdlib>
+#include <__exception/exception.h>
+#include <__exception/exception_ptr.h>
+#include <__exception/nested_exception.h>
+#include <__exception/operations.h>
+#include <__exception/terminate.h>
#include <version>
-// <vcruntime_exception.h> defines its own std::exception and std::bad_exception types,
-// which we use in order to be ABI-compatible with other STLs on Windows.
-#if defined(_LIBCPP_ABI_VCRUNTIME)
-# include <vcruntime_exception.h>
-#endif
-
#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
# pragma GCC system_header
#endif
-namespace std // purposefully not using versioning namespace
-{
-
-#if defined(_LIBCPP_ABI_VCRUNTIME) && (!defined(_HAS_EXCEPTIONS) || _HAS_EXCEPTIONS != 0)
-// The std::exception class was already included above, but we're explicit about this condition here for clarity.
-
-#elif defined(_LIBCPP_ABI_VCRUNTIME) && _HAS_EXCEPTIONS == 0
-// However, <vcruntime_exception.h> does not define std::exception and std::bad_exception
-// when _HAS_EXCEPTIONS == 0.
-//
-// Since libc++ still wants to provide the std::exception hierarchy even when _HAS_EXCEPTIONS == 0
-// (after all those are simply types like any other), we define an ABI-compatible version
-// of the VCRuntime std::exception and std::bad_exception types in that mode.
-
-struct __std_exception_data {
- char const* _What;
- bool _DoFree;
-};
-
-class exception { // base of all library exceptions
-public:
- exception() _NOEXCEPT : __data_() {}
-
- explicit exception(char const* __message) _NOEXCEPT : __data_() {
- __data_._What = __message;
- __data_._DoFree = true;
- }
-
- exception(exception const&) _NOEXCEPT {}
-
- exception& operator=(exception const&) _NOEXCEPT { return *this; }
-
- virtual ~exception() _NOEXCEPT {}
-
- virtual char const* what() const _NOEXCEPT { return __data_._What ? __data_._What : "Unknown exception"; }
-
-private:
- __std_exception_data __data_;
-};
-
-class bad_exception : public exception {
-public:
- bad_exception() _NOEXCEPT : exception("bad exception") {}
-};
-
-#else // !defined(_LIBCPP_ABI_VCRUNTIME)
-// On all other platforms, we define our own std::exception and std::bad_exception types
-// regardless of whether exceptions are turned on as a language feature.
-
-class _LIBCPP_EXCEPTION_ABI exception {
-public:
- _LIBCPP_INLINE_VISIBILITY exception() _NOEXCEPT {}
- _LIBCPP_INLINE_VISIBILITY exception(const exception&) _NOEXCEPT = default;
-
- virtual ~exception() _NOEXCEPT;
- virtual const char* what() const _NOEXCEPT;
-};
-
-class _LIBCPP_EXCEPTION_ABI bad_exception : public exception {
-public:
- _LIBCPP_INLINE_VISIBILITY bad_exception() _NOEXCEPT {}
- ~bad_exception() _NOEXCEPT override;
- const char* what() const _NOEXCEPT override;
-};
-#endif // !_LIBCPP_ABI_VCRUNTIME
-
-#if _LIBCPP_STD_VER <= 14 \
- || defined(_LIBCPP_ENABLE_CXX17_REMOVED_UNEXPECTED_FUNCTIONS) \
- || defined(_LIBCPP_BUILDING_LIBRARY)
-typedef void (*unexpected_handler)();
-_LIBCPP_FUNC_VIS unexpected_handler set_unexpected(unexpected_handler) _NOEXCEPT;
-_LIBCPP_FUNC_VIS unexpected_handler get_unexpected() _NOEXCEPT;
-_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void unexpected();
-#endif
-
-typedef void (*terminate_handler)();
-_LIBCPP_FUNC_VIS terminate_handler set_terminate(terminate_handler) _NOEXCEPT;
-_LIBCPP_FUNC_VIS terminate_handler get_terminate() _NOEXCEPT;
-_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void terminate() _NOEXCEPT;
-
-_LIBCPP_FUNC_VIS bool uncaught_exception() _NOEXCEPT;
-_LIBCPP_FUNC_VIS _LIBCPP_AVAILABILITY_UNCAUGHT_EXCEPTIONS int uncaught_exceptions() _NOEXCEPT;
-
-class _LIBCPP_TYPE_VIS exception_ptr;
-
-_LIBCPP_FUNC_VIS exception_ptr current_exception() _NOEXCEPT;
-_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void rethrow_exception(exception_ptr);
-
-#ifndef _LIBCPP_ABI_MICROSOFT
-
-class _LIBCPP_TYPE_VIS exception_ptr
-{
- void* __ptr_;
-public:
- _LIBCPP_INLINE_VISIBILITY exception_ptr() _NOEXCEPT : __ptr_() {}
- _LIBCPP_INLINE_VISIBILITY exception_ptr(nullptr_t) _NOEXCEPT : __ptr_() {}
-
- exception_ptr(const exception_ptr&) _NOEXCEPT;
- exception_ptr& operator=(const exception_ptr&) _NOEXCEPT;
- ~exception_ptr() _NOEXCEPT;
-
- _LIBCPP_INLINE_VISIBILITY explicit operator bool() const _NOEXCEPT
- {return __ptr_ != nullptr;}
-
- friend _LIBCPP_INLINE_VISIBILITY
- bool operator==(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT
- {return __x.__ptr_ == __y.__ptr_;}
-
- friend _LIBCPP_INLINE_VISIBILITY
- bool operator!=(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT
- {return !(__x == __y);}
-
- friend _LIBCPP_FUNC_VIS exception_ptr current_exception() _NOEXCEPT;
- friend _LIBCPP_FUNC_VIS void rethrow_exception(exception_ptr);
-};
-
-template<class _Ep>
-_LIBCPP_INLINE_VISIBILITY exception_ptr
-make_exception_ptr(_Ep __e) _NOEXCEPT
-{
-#ifndef _LIBCPP_HAS_NO_EXCEPTIONS
- try
- {
- throw __e;
- }
- catch (...)
- {
- return current_exception();
- }
-#else
- ((void)__e);
- _VSTD::abort();
-#endif
-}
-
-#else // _LIBCPP_ABI_MICROSOFT
-
-class _LIBCPP_TYPE_VIS exception_ptr
-{
-_LIBCPP_DIAGNOSTIC_PUSH
-_LIBCPP_CLANG_DIAGNOSTIC_IGNORED("-Wunused-private-field")
- void* __ptr1_;
- void* __ptr2_;
-_LIBCPP_DIAGNOSTIC_POP
-public:
- exception_ptr() _NOEXCEPT;
- exception_ptr(nullptr_t) _NOEXCEPT;
- exception_ptr(const exception_ptr& __other) _NOEXCEPT;
- exception_ptr& operator=(const exception_ptr& __other) _NOEXCEPT;
- exception_ptr& operator=(nullptr_t) _NOEXCEPT;
- ~exception_ptr() _NOEXCEPT;
- explicit operator bool() const _NOEXCEPT;
-};
-
-_LIBCPP_FUNC_VIS
-bool operator==(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT;
-
-inline _LIBCPP_INLINE_VISIBILITY
-bool operator!=(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT
- {return !(__x == __y);}
-
-_LIBCPP_FUNC_VIS void swap(exception_ptr&, exception_ptr&) _NOEXCEPT;
-
-_LIBCPP_FUNC_VIS exception_ptr __copy_exception_ptr(void *__except, const void* __ptr);
-_LIBCPP_FUNC_VIS exception_ptr current_exception() _NOEXCEPT;
-_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void rethrow_exception(exception_ptr);
-
-// This is a built-in template function which automagically extracts the required
-// information.
-template <class _E> void *__GetExceptionInfo(_E);
-
-template<class _Ep>
-_LIBCPP_INLINE_VISIBILITY exception_ptr
-make_exception_ptr(_Ep __e) _NOEXCEPT
-{
- return __copy_exception_ptr(_VSTD::addressof(__e), __GetExceptionInfo(__e));
-}
-
-#endif // _LIBCPP_ABI_MICROSOFT
-// nested_exception
-
-class _LIBCPP_EXCEPTION_ABI nested_exception
-{
- exception_ptr __ptr_;
-public:
- nested_exception() _NOEXCEPT;
-// nested_exception(const nested_exception&) noexcept = default;
-// nested_exception& operator=(const nested_exception&) noexcept = default;
- virtual ~nested_exception() _NOEXCEPT;
-
- // access functions
- _LIBCPP_NORETURN void rethrow_nested() const;
- _LIBCPP_INLINE_VISIBILITY exception_ptr nested_ptr() const _NOEXCEPT {return __ptr_;}
-};
-
-template <class _Tp>
-struct __nested
- : public _Tp,
- public nested_exception
-{
- _LIBCPP_INLINE_VISIBILITY explicit __nested(const _Tp& __t) : _Tp(__t) {}
-};
-
-#ifndef _LIBCPP_HAS_NO_EXCEPTIONS
-template <class _Tp, class _Up, bool>
-struct __throw_with_nested;
-
-template <class _Tp, class _Up>
-struct __throw_with_nested<_Tp, _Up, true> {
- _LIBCPP_NORETURN static inline _LIBCPP_INLINE_VISIBILITY void
- __do_throw(_Tp&& __t)
- {
- throw __nested<_Up>(std::forward<_Tp>(__t));
- }
-};
-
-template <class _Tp, class _Up>
-struct __throw_with_nested<_Tp, _Up, false> {
- _LIBCPP_NORETURN static inline _LIBCPP_INLINE_VISIBILITY void
- __do_throw(_Tp&& __t)
- {
- throw std::forward<_Tp>(__t);
- }
-};
-#endif
-
-template <class _Tp>
-_LIBCPP_NORETURN _LIBCPP_HIDE_FROM_ABI
-void
-throw_with_nested(_Tp&& __t)
-{
-#ifndef _LIBCPP_HAS_NO_EXCEPTIONS
- typedef typename decay<_Tp>::type _Up;
- static_assert( is_copy_constructible<_Up>::value, "type thrown must be CopyConstructible");
- __throw_with_nested<_Tp, _Up,
- is_class<_Up>::value &&
- !is_base_of<nested_exception, _Up>::value &&
- !__libcpp_is_final<_Up>::value>::
- __do_throw(std::forward<_Tp>(__t));
-#else
- ((void)__t);
- // FIXME: Make this abort
-#endif
-}
-
-template <class _From, class _To>
-struct __can_dynamic_cast : _BoolConstant<
- is_polymorphic<_From>::value &&
- (!is_base_of<_To, _From>::value ||
- is_convertible<const _From*, const _To*>::value)> {};
-
-template <class _Ep>
-inline _LIBCPP_INLINE_VISIBILITY
-void
-rethrow_if_nested(const _Ep& __e,
- __enable_if_t< __can_dynamic_cast<_Ep, nested_exception>::value>* = 0)
-{
- const nested_exception* __nep = dynamic_cast<const nested_exception*>(_VSTD::addressof(__e));
- if (__nep)
- __nep->rethrow_nested();
-}
-
-template <class _Ep>
-inline _LIBCPP_INLINE_VISIBILITY
-void
-rethrow_if_nested(const _Ep&,
- __enable_if_t<!__can_dynamic_cast<_Ep, nested_exception>::value>* = 0)
-{
-}
-
-} // namespace std
-
#if !defined(_LIBCPP_REMOVE_TRANSITIVE_INCLUDES) && _LIBCPP_STD_VER <= 20
+# include <cstdlib>
# include <type_traits>
#endif
diff --git a/libcxx/include/istream b/libcxx/include/istream
index 1fb45fadf236a..7350e11fe129d 100644
--- a/libcxx/include/istream
+++ b/libcxx/include/istream
@@ -161,6 +161,9 @@ template <class Stream, class T>
#include <__assert> // all public C++ headers provide the assertion handler
#include <__config>
#include <__iterator/istreambuf_iterator.h>
+#include <__type_traits/conjunction.h>
+#include <__type_traits/enable_if.h>
+#include <__type_traits/is_base_of.h>
#include <__utility/declval.h>
#include <__utility/forward.h>
#include <ostream>
diff --git a/libcxx/include/libcxx.imp b/libcxx/include/libcxx.imp
index 8e897c9bb66e1..d85ae36953a1e 100644
--- a/libcxx/include/libcxx.imp
+++ b/libcxx/include/libcxx.imp
@@ -24,6 +24,7 @@
{ include: [ "@<__concepts/.*>", "private", "<concepts>", "public" ] },
{ include: [ "@<__coroutine/.*>", "private", "<coroutine>", "public" ] },
{ include: [ "@<__debug_utils/.*>", "private", "<debug_utils>", "public" ] },
+ { include: [ "@<__exception/.*>", "private", "<exception>", "public" ] },
{ include: [ "@<__expected/.*>", "private", "<expected>", "public" ] },
{ include: [ "@<__filesystem/.*>", "private", "<filesystem>", "public" ] },
{ include: [ "@<__format/.*>", "private", "<format>", "public" ] },
diff --git a/libcxx/include/module.modulemap.in b/libcxx/include/module.modulemap.in
index 5f874d0d0de0c..4f8159fd07ee2 100644
--- a/libcxx/include/module.modulemap.in
+++ b/libcxx/include/module.modulemap.in
@@ -829,6 +829,14 @@ module std [system] {
module exception {
header "exception"
export *
+
+ module __exception {
+ module exception { private header "__exception/exception.h" }
+ module exception_ptr { private header "__exception/exception_ptr.h" }
+ module nested_exception { private header "__exception/nested_exception.h" }
+ module operations { private header "__exception/operations.h" }
+ module terminate { private header "__exception/terminate.h" }
+ }
}
module execution {
header "execution"
@@ -1623,7 +1631,10 @@ module std [system] {
module __utility {
module as_const { private header "__utility/as_const.h" }
- module auto_cast { private header "__utility/auto_cast.h" }
+ module auto_cast {
+ private header "__utility/auto_cast.h"
+ export type_traits.decay
+ }
module cmp { private header "__utility/cmp.h" }
module convert_to_integral { private header "__utility/convert_to_integral.h" }
module declval { private header "__utility/declval.h" }
diff --git a/libcxx/include/optional b/libcxx/include/optional
index e548c47268611..641745b7bda94 100644
--- a/libcxx/include/optional
+++ b/libcxx/include/optional
@@ -165,6 +165,7 @@ template<class T>
#include <__functional/hash.h>
#include <__functional/invoke.h>
#include <__functional/unary_function.h>
+#include <__memory/addressof.h>
#include <__memory/construct_at.h>
#include <__tuple_dir/sfinae_helpers.h>
#include <__type_traits/conjunction.h>
diff --git a/libcxx/include/ostream b/libcxx/include/ostream
index 6db0e889ce457..60f111ce6aa86 100644
--- a/libcxx/include/ostream
+++ b/libcxx/include/ostream
@@ -168,6 +168,8 @@ basic_ostream<wchar_t, traits>& operator<<(basic_ostream<wchar_t, traits>&, cons
#include <__memory/shared_ptr.h>
#include <__memory/unique_ptr.h>
#include <__type_traits/conjunction.h>
+#include <__type_traits/enable_if.h>
+#include <__type_traits/is_base_of.h>
#include <__type_traits/void_t.h>
#include <__utility/declval.h>
#include <bitset>
diff --git a/libcxx/include/span b/libcxx/include/span
index 661ae0dbec20a..2ef1ea69d9587 100644
--- a/libcxx/include/span
+++ b/libcxx/include/span
@@ -141,6 +141,7 @@ template<class R>
#include <__ranges/enable_borrowed_range.h>
#include <__ranges/enable_view.h>
#include <__ranges/size.h>
+#include <__type_traits/is_convertible.h>
#include <__type_traits/remove_cvref.h>
#include <__type_traits/remove_reference.h>
#include <__type_traits/type_identity.h>
diff --git a/libcxx/include/string b/libcxx/include/string
index 3217361d00f6a..9a84440555aa8 100644
--- a/libcxx/include/string
+++ b/libcxx/include/string
@@ -550,6 +550,7 @@ basic_string<char32_t> operator "" s( const char32_t *str, size_t len );
#include <__iterator/iterator_traits.h>
#include <__iterator/reverse_iterator.h>
#include <__iterator/wrap_iter.h>
+#include <__memory/addressof.h>
#include <__memory/allocate_at_least.h>
#include <__memory/allocator.h>
#include <__memory/allocator_traits.h>
@@ -562,6 +563,7 @@ basic_string<char32_t> operator "" s( const char32_t *str, size_t len );
#include <__string/extern_template_lists.h>
#include <__type_traits/is_allocator.h>
#include <__type_traits/is_array.h>
+#include <__type_traits/is_convertible.h>
#include <__type_traits/is_nothrow_default_constructible.h>
#include <__type_traits/is_nothrow_move_assignable.h>
#include <__type_traits/is_same.h>
diff --git a/libcxx/include/string_view b/libcxx/include/string_view
index d5629b706d839..b61ca9e9d5363 100644
--- a/libcxx/include/string_view
+++ b/libcxx/include/string_view
@@ -220,6 +220,7 @@ namespace std {
#include <__ranges/size.h>
#include <__string/char_traits.h>
#include <__type_traits/is_array.h>
+#include <__type_traits/is_convertible.h>
#include <__type_traits/is_same.h>
#include <__type_traits/is_standard_layout.h>
#include <__type_traits/is_trivial.h>
diff --git a/libcxx/include/valarray b/libcxx/include/valarray
index a52fc1088e467..f305bac8bc764 100644
--- a/libcxx/include/valarray
+++ b/libcxx/include/valarray
@@ -351,8 +351,10 @@ template <class T> unspecified2 end(const valarray<T>& v);
#include <__assert> // all public C++ headers provide the assertion handler
#include <__config>
#include <__functional/operations.h>
+#include <__memory/addressof.h>
#include <__memory/allocator.h>
#include <__memory/uninitialized_algorithms.h>
+#include <__type_traits/decay.h>
#include <__type_traits/remove_reference.h>
#include <__utility/move.h>
#include <__utility/swap.h>
diff --git a/libcxx/include/variant b/libcxx/include/variant
index 0f4600eea49b1..88f63dd5610ab 100644
--- a/libcxx/include/variant
+++ b/libcxx/include/variant
@@ -214,6 +214,7 @@ namespace std {
#include <__functional/invoke.h>
#include <__functional/operations.h>
#include <__functional/unary_function.h>
+#include <__memory/addressof.h>
#include <__type_traits/add_const.h>
#include <__type_traits/add_cv.h>
#include <__type_traits/add_pointer.h>
diff --git a/libcxx/include/vector b/libcxx/include/vector
index 6c25e5de718a0..980af582558be 100644
--- a/libcxx/include/vector
+++ b/libcxx/include/vector
@@ -299,6 +299,7 @@ template<class T, class charT> requires is-vector-bool-reference<T> // Since C++
#include <__iterator/iterator_traits.h>
#include <__iterator/reverse_iterator.h>
#include <__iterator/wrap_iter.h>
+#include <__memory/addressof.h>
#include <__memory/allocate_at_least.h>
#include <__memory/pointer_traits.h>
#include <__memory/swap_allocator.h>
diff --git a/libcxx/test/libcxx/private_headers.verify.cpp b/libcxx/test/libcxx/private_headers.verify.cpp
index 0f611ce5eec75..7ec1762874625 100644
--- a/libcxx/test/libcxx/private_headers.verify.cpp
+++ b/libcxx/test/libcxx/private_headers.verify.cpp
@@ -329,6 +329,11 @@ END-SCRIPT
#include <__coroutine/trivial_awaitables.h> // expected-error@*:* {{use of private header from outside its module: '__coroutine/trivial_awaitables.h'}}
#include <__debug_utils/randomize_range.h> // expected-error@*:* {{use of private header from outside its module: '__debug_utils/randomize_range.h'}}
#include <__errc> // expected-error@*:* {{use of private header from outside its module: '__errc'}}
+#include <__exception/exception.h> // expected-error@*:* {{use of private header from outside its module: '__exception/exception.h'}}
+#include <__exception/exception_ptr.h> // expected-error@*:* {{use of private header from outside its module: '__exception/exception_ptr.h'}}
+#include <__exception/nested_exception.h> // expected-error@*:* {{use of private header from outside its module: '__exception/nested_exception.h'}}
+#include <__exception/operations.h> // expected-error@*:* {{use of private header from outside its module: '__exception/operations.h'}}
+#include <__exception/terminate.h> // expected-error@*:* {{use of private header from outside its module: '__exception/terminate.h'}}
#include <__expected/bad_expected_access.h> // expected-error@*:* {{use of private header from outside its module: '__expected/bad_expected_access.h'}}
#include <__expected/expected.h> // expected-error@*:* {{use of private header from outside its module: '__expected/expected.h'}}
#include <__expected/unexpect.h> // expected-error@*:* {{use of private header from outside its module: '__expected/unexpect.h'}}
diff --git a/libcxx/test/std/containers/sequences/array/contiguous.pass.cpp b/libcxx/test/std/containers/sequences/array/contiguous.pass.cpp
index 9589e63643941..fec48b325e90e 100644
--- a/libcxx/test/std/containers/sequences/array/contiguous.pass.cpp
+++ b/libcxx/test/std/containers/sequences/array/contiguous.pass.cpp
@@ -12,6 +12,7 @@
#include <array>
#include <cassert>
+#include <memory>
#include "test_macros.h"
diff --git a/libcxx/test/std/utilities/memory/allocator.uses/allocator.uses.trait/uses_allocator.pass.cpp b/libcxx/test/std/utilities/memory/allocator.uses/allocator.uses.trait/uses_allocator.pass.cpp
index dc52cb8635937..5d200a4bf808f 100644
--- a/libcxx/test/std/utilities/memory/allocator.uses/allocator.uses.trait/uses_allocator.pass.cpp
+++ b/libcxx/test/std/utilities/memory/allocator.uses/allocator.uses.trait/uses_allocator.pass.cpp
@@ -12,6 +12,7 @@
#include <memory>
#include <vector>
+#include <type_traits>
#include "test_macros.h"
diff --git a/libcxx/utils/data/ignore_format.txt b/libcxx/utils/data/ignore_format.txt
index 387f4c5f36d49..945af7ebd1fc8 100644
--- a/libcxx/utils/data/ignore_format.txt
+++ b/libcxx/utils/data/ignore_format.txt
@@ -317,7 +317,6 @@ libcxx/include/__debug_utils/randomize_range.h
libcxx/include/deque
libcxx/include/__errc
libcxx/include/errno.h
-libcxx/include/exception
libcxx/include/execution
libcxx/include/expected
libcxx/include/__expected/expected.h
More information about the libcxx-commits
mailing list