[libcxx] r294707 - Split exception.cpp and new.cpp implementation into different files for different runtimes.
Vitaly Buka via cfe-commits
cfe-commits at lists.llvm.org
Thu Feb 9 23:56:00 PST 2017
Thanks!
On Thu, Feb 9, 2017 at 11:50 PM Eric Fiselier <eric at efcs.ca> wrote:
> Alright. Reverting...
>
> On Fri, Feb 10, 2017 at 12:48 AM, Vitaly Buka <vitalybuka at google.com>
> wrote:
>
> As I understand it's not the builder but cmake files of compiler-rt need
> to be fixed, somewhere near add_custom_libcxx in tsan and msan.
> Something just like this should work, but it's broken after the patch.
> cmake -GNinja -DCMAKE_C_COMPILER=clang -DCMAKE_CXX_COMPILER=clang++
> ../../llvm && ninja check-tsan check-msan
>
> Seems reasonable thing to do is to revert and resubmit together with fixed
> compiler-rt.
>
> On Thu, Feb 9, 2017 at 10:04 PM Vitaly Buka <vitalybuka at google.com> wrote:
>
> Thanks.
> looking...
>
> On Thu, Feb 9, 2017 at 9:51 PM Eric Fiselier <eric at efcs.ca> wrote:
>
> To all those who wander here from the sanitizer autoconf buildbot failures
> <http://lab.llvm.org:8011/builders/sanitizer-x86_64-linux-autoconf>.
>
> Yes, this commit is responsible for that breakage. The buildbot in question
> attempts to compile libc++ in-tree w/o libc++abi. Previously libc++
> silently defaulted
> to using w/e <cxxabi.h> header it found on the system. However it no
> longer does this
> on Linux, since the <cxxabi.h> header it finds could incorrectly belong to
> libstdc++ or libcxxrt.
>
> Instead this builder should be changed to either:
>
> (A) build libc++abi in-tree as well.
> (B) explicitly specify -DLIBCXX_CXX_ABI=libcxxabi
> -DLIBCXX_CXX_ABI_INCLUDE_PATHS="<path-to-installed-headers>".
>
> If these changes cannot be made easily and quickly then please let me
> know, and I'll implement a temporary workaround in
> libc++.
>
>
> /Eric
>
>
> On Thu, Feb 9, 2017 at 9:25 PM, Eric Fiselier via cfe-commits <
> cfe-commits at lists.llvm.org> wrote:
>
> Author: ericwf
> Date: Thu Feb 9 22:25:33 2017
> New Revision: 294707
>
> URL: http://llvm.org/viewvc/llvm-project?rev=294707&view=rev
> Log:
> Split exception.cpp and new.cpp implementation into different files for
> different runtimes.
>
> exception.cpp is a bloody mess. It's full of confusing #ifdef branches for
> each different ABI library we support, and it's getting unmaintainable.
>
> This patch breaks down exception.cpp into multiple different header files,
> roughly one per implementation. Additionally it moves the definitions of
> exceptions in new.cpp into the correct implementation header.
>
> This patch also removes an unmaintained libc++abi configuration.
> This configuration may still be used by Apple internally but there
> are no other possible users. If it turns out that Apple still uses
> this configuration internally I will re-add it in a later commit.
> See http://llvm.org/PR31904.
>
> Added:
> libcxx/trunk/src/support/runtime/
> libcxx/trunk/src/support/runtime/exception_fallback.ipp
> libcxx/trunk/src/support/runtime/exception_glibcxx.ipp
> libcxx/trunk/src/support/runtime/exception_libcxxabi.ipp
> libcxx/trunk/src/support/runtime/exception_libcxxrt.ipp
> libcxx/trunk/src/support/runtime/exception_msvc.ipp
> libcxx/trunk/src/support/runtime/exception_pointer_cxxabi.ipp
> libcxx/trunk/src/support/runtime/exception_pointer_glibcxx.ipp
> libcxx/trunk/src/support/runtime/exception_pointer_unimplemented.ipp
> libcxx/trunk/src/support/runtime/new_handler_fallback.ipp
> Modified:
> libcxx/trunk/CMakeLists.txt
> libcxx/trunk/include/exception
> libcxx/trunk/include/new
> libcxx/trunk/include/typeinfo
> libcxx/trunk/src/exception.cpp
> libcxx/trunk/src/new.cpp
> libcxx/trunk/src/typeinfo.cpp
>
> Modified: libcxx/trunk/CMakeLists.txt
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/CMakeLists.txt?rev=294707&r1=294706&r2=294707&view=diff
>
> ==============================================================================
> --- libcxx/trunk/CMakeLists.txt (original)
> +++ libcxx/trunk/CMakeLists.txt Thu Feb 9 22:25:33 2017
> @@ -116,11 +116,19 @@ if (LIBCXX_CXX_ABI STREQUAL "default")
> ${LLVM_MAIN_SRC_DIR}/runtimes/libcxxabi/include
> NO_DEFAULT_PATH
> )
> + find_path(
> + LIBCXX_LIBCXXABI_INCLUDES_EXTERNAL
> + cxxabi.h
> + PATHS /usr/include
> + )
> if ((NOT LIBCXX_STANDALONE_BUILD OR HAVE_LIBCXXABI) AND
> IS_DIRECTORY "${LIBCXX_LIBCXXABI_INCLUDES_INTERNAL}")
> set(LIBCXX_CXX_ABI_LIBNAME "libcxxabi")
> set(LIBCXX_CXX_ABI_INCLUDE_PATHS
> "${LIBCXX_LIBCXXABI_INCLUDES_INTERNAL}")
> set(LIBCXX_CXX_ABI_INTREE 1)
> + elseif(APPLE AND IS_DIRECTORY "${LIBCXX_LIBCXXABI_INCLUDES_INTERNAL}")
> + set(LIBCXX_CXX_ABI_LIBNAME "libcxxabi")
> + set(LIBCXX_CXX_ABI_INCLUDE_PATHS
> "${LIBCXX_LIBCXXABI_INCLUDES_INTERNAL}")
> else()
> if (LIBCXX_TARGETING_MSVC)
> # FIXME: Figure out how to configure the ABI library on Windows.
>
> Modified: libcxx/trunk/include/exception
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/include/exception?rev=294707&r1=294706&r2=294707&view=diff
>
> ==============================================================================
> --- libcxx/trunk/include/exception (original)
> +++ libcxx/trunk/include/exception Thu Feb 9 22:25:33 2017
> @@ -82,6 +82,10 @@ template <class E> void rethrow_if_neste
> #include <cstdlib>
> #include <type_traits>
>
> +#if defined(_LIBCPP_ABI_MICROSOFT)
> +#include <vcruntime_exception.h>
> +#endif
> +
> #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
> #pragma GCC system_header
> #endif
> @@ -89,6 +93,7 @@ template <class E> void rethrow_if_neste
> namespace std // purposefully not using versioning namespace
> {
>
> +#if !defined(_LIBCPP_ABI_MICROSOFT)
> class _LIBCPP_EXCEPTION_ABI exception
> {
> public:
> @@ -105,6 +110,7 @@ public:
> virtual ~bad_exception() _NOEXCEPT;
> virtual const char* what() const _NOEXCEPT;
> };
> +#endif // !_LIBCPP_ABI_MICROSOFT
>
> typedef void (*unexpected_handler)();
> _LIBCPP_FUNC_VIS unexpected_handler set_unexpected(unexpected_handler)
> _NOEXCEPT;
>
> Modified: libcxx/trunk/include/new
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/include/new?rev=294707&r1=294706&r2=294707&view=diff
>
> ==============================================================================
> --- libcxx/trunk/include/new (original)
> +++ libcxx/trunk/include/new Thu Feb 9 22:25:33 2017
> @@ -92,6 +92,10 @@ void operator delete[](void* ptr, void*
> #include <cstdlib>
> #endif
>
> +#if defined(_LIBCPP_ABI_MICROSOFT)
> +#include <new.h>
> +#endif
> +
> #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
> #pragma GCC system_header
> #endif
> @@ -110,6 +114,10 @@ void operator delete[](void* ptr, void*
> namespace std // purposefully not using versioning namespace
> {
>
> +#if !defined(_LIBCPP_ABI_MICROSOFT)
> +struct _LIBCPP_TYPE_VIS nothrow_t {};
> +extern _LIBCPP_FUNC_VIS const nothrow_t nothrow;
> +
> class _LIBCPP_EXCEPTION_ABI bad_alloc
> : public exception
> {
> @@ -128,6 +136,12 @@ public:
> virtual const char* what() const _NOEXCEPT;
> };
>
> +typedef void (*new_handler)();
> +_LIBCPP_FUNC_VIS new_handler set_new_handler(new_handler) _NOEXCEPT;
> +_LIBCPP_FUNC_VIS new_handler get_new_handler() _NOEXCEPT;
> +
> +#endif // !_LIBCPP_ABI_MICROSOFT
> +
> _LIBCPP_NORETURN _LIBCPP_FUNC_VIS void __throw_bad_alloc(); // not in
> C++ spec
>
> #if defined(_LIBCPP_BUILDING_NEW) || (_LIBCPP_STD_VER > 11)
> @@ -153,12 +167,6 @@ enum align_val_t { __zero = 0, __max = (
> #endif
> #endif
>
> -struct _LIBCPP_TYPE_VIS nothrow_t {};
> -extern _LIBCPP_FUNC_VIS const nothrow_t nothrow;
> -typedef void (*new_handler)();
> -_LIBCPP_FUNC_VIS new_handler set_new_handler(new_handler) _NOEXCEPT;
> -_LIBCPP_FUNC_VIS new_handler get_new_handler() _NOEXCEPT;
> -
> } // std
>
> #if defined(_LIBCPP_CXX03_LANG)
> @@ -167,6 +175,8 @@ _LIBCPP_FUNC_VIS new_handler get_new_han
> #define _THROW_BAD_ALLOC
> #endif
>
> +#if !defined(_LIBCPP_ABI_MICROSOFT)
> +
> _LIBCPP_OVERRIDABLE_FUNC_VIS void* operator new(std::size_t __sz)
> _THROW_BAD_ALLOC;
> _LIBCPP_OVERRIDABLE_FUNC_VIS void* operator new(std::size_t __sz, const
> std::nothrow_t&) _NOEXCEPT _NOALIAS;
> _LIBCPP_OVERRIDABLE_FUNC_VIS void operator delete(void* __p) _NOEXCEPT;
> @@ -206,6 +216,8 @@ inline _LIBCPP_INLINE_VISIBILITY void* o
> inline _LIBCPP_INLINE_VISIBILITY void operator delete (void*, void*)
> _NOEXCEPT {}
> inline _LIBCPP_INLINE_VISIBILITY void operator delete[](void*, void*)
> _NOEXCEPT {}
>
> +#endif // !_LIBCPP_ABI_MICROSOFT
> +
> _LIBCPP_BEGIN_NAMESPACE_STD
>
> inline _LIBCPP_INLINE_VISIBILITY void *__allocate(size_t __size) {
>
> Modified: libcxx/trunk/include/typeinfo
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/include/typeinfo?rev=294707&r1=294706&r2=294707&view=diff
>
> ==============================================================================
> --- libcxx/trunk/include/typeinfo (original)
> +++ libcxx/trunk/include/typeinfo Thu Feb 9 22:25:33 2017
> @@ -69,7 +69,9 @@ public:
> #pragma GCC system_header
> #endif
>
> -#if defined(_LIBCPP_NONUNIQUE_RTTI_BIT)
> +#if defined(_LIBCPP_ABI_MICROSOFT)
> +#include <vcruntime_typeinfo.h>
> +#elif defined(_LIBCPP_NONUNIQUE_RTTI_BIT)
> #define _LIBCPP_HAS_NONUNIQUE_TYPEINFO
> #else
> #define _LIBCPP_HAS_UNIQUE_TYPEINFO
> @@ -78,6 +80,7 @@ public:
> namespace std // purposefully not using versioning namespace
> {
>
> +#if !defined(_LIBCPP_ABI_MICROSOFT)
> class _LIBCPP_EXCEPTION_ABI type_info
> {
> type_info& operator=(const type_info&);
> @@ -187,6 +190,8 @@ public:
> virtual const char* what() const _NOEXCEPT;
> };
>
> +#endif // !_LIBCPP_ABI_MICROSOFT
> +
> } // std
>
> _LIBCPP_BEGIN_NAMESPACE_STD
>
> Modified: libcxx/trunk/src/exception.cpp
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/src/exception.cpp?rev=294707&r1=294706&r2=294707&view=diff
>
> ==============================================================================
> --- libcxx/trunk/src/exception.cpp (original)
> +++ libcxx/trunk/src/exception.cpp Thu Feb 9 22:25:33 2017
> @@ -6,328 +6,30 @@
> // Source Licenses. See LICENSE.TXT for details.
> //
>
> //===----------------------------------------------------------------------===//
> -#include <stdlib.h>
> -#include <stdio.h>
>
> #include "exception"
> #include "new"
>
> -#if defined(_LIBCPP_ABI_MICROSOFT)
> -#include <eh.h>
> -#include <corecrt_terminate.h>
> -#elif defined(__APPLE__) && !defined(LIBCXXRT) && \
> - !defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY)
> +#if defined(LIBCXXRT) || defined(LIBCXX_BUILDING_LIBCXXABI) || \
> + (defined(__APPLE__) && !defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY))
> #include <cxxabi.h>
> -
> using namespace __cxxabiv1;
> #define HAVE_DEPENDENT_EH_ABI 1
> - #ifndef _LIBCPPABI_VERSION
> - using namespace __cxxabiapple;
> - // On Darwin, there are two STL shared libraries and a lower level ABI
> - // shared library. The globals holding the current terminate handler
> and
> - // current unexpected handler are in the ABI library.
> - #define __terminate_handler __cxxabiapple::__cxa_terminate_handler
> - #define __unexpected_handler __cxxabiapple::__cxa_unexpected_handler
> - #endif // _LIBCPPABI_VERSION
> -#elif defined(LIBCXXRT) || defined(LIBCXX_BUILDING_LIBCXXABI)
> - #include <cxxabi.h>
> - using namespace __cxxabiv1;
> - #if defined(LIBCXXRT) || defined(_LIBCPPABI_VERSION)
> - #define HAVE_DEPENDENT_EH_ABI 1
> - #endif
> -#elif !defined(__GLIBCXX__) // defined(LIBCXX_BUILDING_LIBCXXABI)
> - _LIBCPP_SAFE_STATIC static std::terminate_handler __terminate_handler;
> - _LIBCPP_SAFE_STATIC static std::unexpected_handler __unexpected_handler;
> -#endif // defined(LIBCXX_BUILDING_LIBCXXABI)
> -
> -namespace std
> -{
> -
> -#if !defined(LIBCXXRT) && !defined(_LIBCPPABI_VERSION) &&
> !defined(__GLIBCXX__)
> -
> -// libcxxrt provides implementations of these functions itself.
> -unexpected_handler
> -set_unexpected(unexpected_handler func) _NOEXCEPT
> -{
> -#if defined(_LIBCPP_ABI_MICROSOFT)
> - return ::set_unexpected(func);
> -#else
> - return __sync_lock_test_and_set(&__unexpected_handler, func);
> -#endif
> -}
> -
> -unexpected_handler
> -get_unexpected() _NOEXCEPT
> -{
> -#if defined(_LIBCPP_ABI_MICROSOFT)
> - return ::_get_unexpected();
> -#else
> - return __sync_fetch_and_add(&__unexpected_handler,
> (unexpected_handler)0);
> -#endif
> -}
> -
> -_LIBCPP_NORETURN
> -void
> -unexpected()
> -{
> - (*get_unexpected())();
> - // unexpected handler should not return
> - terminate();
> -}
> -
> -terminate_handler
> -set_terminate(terminate_handler func) _NOEXCEPT
> -{
> -#if defined(_LIBCPP_ABI_MICROSOFT)
> - return ::set_terminate(func);
> -#else
> - return __sync_lock_test_and_set(&__terminate_handler, func);
> #endif
> -}
>
> -terminate_handler
> -get_terminate() _NOEXCEPT
> -{
> #if defined(_LIBCPP_ABI_MICROSOFT)
> - return ::_get_terminate();
> -#else
> - return __sync_fetch_and_add(&__terminate_handler, (terminate_handler)0);
> -#endif
> -}
> -
> -#ifndef __EMSCRIPTEN__ // We provide this in JS
> -_LIBCPP_NORETURN
> -void
> -terminate() _NOEXCEPT
> -{
> -#ifndef _LIBCPP_NO_EXCEPTIONS
> - try
> - {
> -#endif // _LIBCPP_NO_EXCEPTIONS
> - (*get_terminate())();
> - // handler should not return
> - fprintf(stderr, "terminate_handler unexpectedly returned\n");
> - ::abort();
> -#ifndef _LIBCPP_NO_EXCEPTIONS
> - }
> - catch (...)
> - {
> - // handler should not throw exception
> - fprintf(stderr, "terminate_handler unexpectedly threw an
> exception\n");
> - ::abort();
> - }
> -#endif // _LIBCPP_NO_EXCEPTIONS
> -}
> -#endif // !__EMSCRIPTEN__
> -#endif // !defined(LIBCXXRT) && !defined(_LIBCPPABI_VERSION)
> -
> -#if !defined(LIBCXXRT) && !defined(__GLIBCXX__) &&
> !defined(__EMSCRIPTEN__)
> -
> -bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; }
> -
> -int uncaught_exceptions() _NOEXCEPT
> -{
> -#if !defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY) && \
> - (defined(__APPLE__) || defined(_LIBCPPABI_VERSION))
> - // on Darwin, there is a helper function so __cxa_get_globals is
> private
> -# if _LIBCPPABI_VERSION > 1101
> - return __cxa_uncaught_exceptions();
> -# else
> - return __cxa_uncaught_exception() ? 1 : 0;
> -# endif
> -#elif defined(_LIBCPP_ABI_MICROSOFT)
> - return __uncaught_exceptions();
> -#else
> -# if defined(_LIBCPP_MSVC)
> - _LIBCPP_WARNING("uncaught_exceptions not yet implemented")
> -# else
> -# warning uncaught_exception not yet implemented
> -# endif
> - fprintf(stderr, "uncaught_exceptions not yet implemented\n");
> - ::abort();
> -#endif // __APPLE__
> -}
> -
> -
> -#ifndef _LIBCPPABI_VERSION
> -
> -exception::~exception() _NOEXCEPT
> -{
> -}
> -
> -const char* exception::what() const _NOEXCEPT
> -{
> - return "std::exception";
> -}
> -
> -#endif // _LIBCPPABI_VERSION
> -#endif //LIBCXXRT
> -#if !defined(_LIBCPPABI_VERSION) && !defined(__GLIBCXX__)
> -
> -bad_exception::~bad_exception() _NOEXCEPT
> -{
> -}
> -
> -const char* bad_exception::what() const _NOEXCEPT
> -{
> - return "std::bad_exception";
> -}
> -
> -#endif
> -
> -#if defined(__GLIBCXX__)
> -
> -// libsupc++ does not implement the dependent EH ABI and the functionality
> -// it uses to implement std::exception_ptr (which it declares as an alias
> of
> -// std::__exception_ptr::exception_ptr) is not directly exported to
> clients. So
> -// we have little choice but to hijack
> std::__exception_ptr::exception_ptr's
> -// (which fortunately has the same layout as our std::exception_ptr) copy
> -// constructor, assignment operator and destructor (which are part of its
> -// stable ABI), and its
> rethrow_exception(std::__exception_ptr::exception_ptr)
> -// function.
> -
> -namespace __exception_ptr
> -{
> -
> -struct exception_ptr
> -{
> - void* __ptr_;
> -
> - exception_ptr(const exception_ptr&) _NOEXCEPT;
> - exception_ptr& operator=(const exception_ptr&) _NOEXCEPT;
> - ~exception_ptr() _NOEXCEPT;
> -};
> -
> -}
> -
> -_LIBCPP_NORETURN void rethrow_exception(__exception_ptr::exception_ptr);
> -
> -#endif
> -
> -exception_ptr::~exception_ptr() _NOEXCEPT
> -{
> -#if HAVE_DEPENDENT_EH_ABI
> - __cxa_decrement_exception_refcount(__ptr_);
> -#elif defined(__GLIBCXX__)
> -
> reinterpret_cast<__exception_ptr::exception_ptr*>(this)->~exception_ptr();
> -#else
> -# if defined(_LIBCPP_MSVC)
> - _LIBCPP_WARNING("exception_ptr not yet implemented")
> -# else
> -# warning exception_ptr not yet implemented
> -# endif
> - fprintf(stderr, "exception_ptr not yet implemented\n");
> - ::abort();
> -#endif
> -}
> -
> -exception_ptr::exception_ptr(const exception_ptr& other) _NOEXCEPT
> - : __ptr_(other.__ptr_)
> -{
> -#if HAVE_DEPENDENT_EH_ABI
> - __cxa_increment_exception_refcount(__ptr_);
> -#elif defined(__GLIBCXX__)
> - new (reinterpret_cast<void*>(this)) __exception_ptr::exception_ptr(
> - reinterpret_cast<const __exception_ptr::exception_ptr&>(other));
> -#else
> -# if defined(_LIBCPP_MSVC)
> - _LIBCPP_WARNING("exception_ptr not yet implemented")
> -# else
> -# warning exception_ptr not yet implemented
> -# endif
> - fprintf(stderr, "exception_ptr not yet implemented\n");
> - ::abort();
> -#endif
> -}
> -
> -exception_ptr& exception_ptr::operator=(const exception_ptr& other)
> _NOEXCEPT
> -{
> -#if HAVE_DEPENDENT_EH_ABI
> - if (__ptr_ != other.__ptr_)
> - {
> - __cxa_increment_exception_refcount(other.__ptr_);
> - __cxa_decrement_exception_refcount(__ptr_);
> - __ptr_ = other.__ptr_;
> - }
> - return *this;
> -#elif defined(__GLIBCXX__)
> - *reinterpret_cast<__exception_ptr::exception_ptr*>(this) =
> - reinterpret_cast<const __exception_ptr::exception_ptr&>(other);
> - return *this;
> -#else
> -# if defined(_LIBCPP_MSVC)
> - _LIBCPP_WARNING("exception_ptr not yet implemented")
> -# else
> -# warning exception_ptr not yet implemented
> -# endif
> - fprintf(stderr, "exception_ptr not yet implemented\n");
> - ::abort();
> -#endif
> -}
> -
> -nested_exception::nested_exception() _NOEXCEPT
> - : __ptr_(current_exception())
> -{
> -}
> -
> -#if !defined(__GLIBCXX__)
> -
> -nested_exception::~nested_exception() _NOEXCEPT
> -{
> -}
> -
> -#endif
> -
> -_LIBCPP_NORETURN
> -void
> -nested_exception::rethrow_nested() const
> -{
> - if (__ptr_ == nullptr)
> - terminate();
> - rethrow_exception(__ptr_);
> -}
> -
> -#if !defined(__GLIBCXX__)
> -
> -exception_ptr current_exception() _NOEXCEPT
> -{
> -#if HAVE_DEPENDENT_EH_ABI
> - // be nicer if there was a constructor that took a ptr, then
> - // this whole function would be just:
> - // return exception_ptr(__cxa_current_primary_exception());
> - exception_ptr ptr;
> - ptr.__ptr_ = __cxa_current_primary_exception();
> - return ptr;
> -#else
> -# if defined(_LIBCPP_MSVC)
> - _LIBCPP_WARNING( "exception_ptr not yet implemented" )
> -# else
> -# warning exception_ptr not yet implemented
> -# endif
> - fprintf(stderr, "exception_ptr not yet implemented\n");
> - ::abort();
> -#endif
> -}
> -
> -#endif // !__GLIBCXX__
> -
> -_LIBCPP_NORETURN
> -void rethrow_exception(exception_ptr p)
> -{
> -#if HAVE_DEPENDENT_EH_ABI
> - __cxa_rethrow_primary_exception(p.__ptr_);
> - // if p.__ptr_ is NULL, above returns so we terminate
> - terminate();
> +#include "support/runtime/exception_msvc.ipp"
> +#include "support/runtime/exception_pointer_unimplemented.ipp"
> +#elif defined(_LIBCPPABI_VERSION)
> +#include "support/runtime/exception_libcxxabi.ipp"
> +#include "support/runtime/exception_pointer_cxxabi.ipp"
> +#elif defined(LIBCXXRT)
> +#include "support/runtime/exception_libcxxrt.ipp"
> +#include "support/runtime/exception_pointer_cxxabi.ipp"
> #elif defined(__GLIBCXX__)
> -
> rethrow_exception(reinterpret_cast<__exception_ptr::exception_ptr&>(p));
> +#include "support/runtime/exception_glibcxx.ipp"
> +#include "support/runtime/exception_pointer_glibcxx.ipp"
> #else
> -# if defined(_LIBCPP_MSVC)
> - _LIBCPP_WARNING("exception_ptr not yet implemented")
> -# else
> -# warning exception_ptr not yet implemented
> -# endif
> - fprintf(stderr, "exception_ptr not yet implemented\n");
> - ::abort();
> +#include "support/runtime/exception_fallback.ipp"
> +#include "support/runtime/exception_pointer_unimplemented.ipp"
> #endif
> -}
> -} // std
>
> Modified: libcxx/trunk/src/new.cpp
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/src/new.cpp?rev=294707&r1=294706&r2=294707&view=diff
>
> ==============================================================================
> --- libcxx/trunk/src/new.cpp (original)
> +++ libcxx/trunk/src/new.cpp Thu Feb 9 22:25:33 2017
> @@ -13,27 +13,45 @@
>
> #include "new"
>
> -#if defined(__APPLE__) && !defined(LIBCXXRT) && \
> - !defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY)
> - #include <cxxabi.h>
> -
> - #ifndef _LIBCPPABI_VERSION
> - // On Darwin, there are two STL shared libraries and a lower
> level ABI
> - // shared library. The global holding the current new handler is
> - // in the ABI library and named __cxa_new_handler.
> - #define __new_handler __cxxabiapple::__cxa_new_handler
> - #endif
> -#else // __APPLE__
> - #if defined(LIBCXXRT) || defined(LIBCXX_BUILDING_LIBCXXABI)
> - #include <cxxabi.h>
> - #endif // defined(LIBCXX_BUILDING_LIBCXXABI)
> - #if defined(_LIBCPP_BUILDING_HAS_NO_ABI_LIBRARY) || \
> - (!defined(_LIBCPPABI_VERSION) && !defined(__GLIBCXX__))
> - static std::new_handler __new_handler;
> - #endif // _LIBCPPABI_VERSION
> +#if defined(_LIBCPP_ABI_MICROSOFT)
> +// nothing todo
> +#elif defined(LIBCXX_BUILDING_LIBCXXABI)
> +#include <cxxabi.h>
> +#elif defined(LIBCXXRT)
> +#include <cxxabi.h>
> +#include "new_handler_fallback.ipp"
> +#elif defined(__GLIBCXX__)
> +// nothing todo
> +#elif defined(_LIBCPP_BUILDING_NO_ABI_LIBRARY)
> +// nothing todo
> +#else
> +#error UNSUPPORTED configuration
> #endif
>
> +namespace std
> +{
> +
> #ifndef __GLIBCXX__
> +const nothrow_t nothrow = {};
> +#endif
> +
> +#ifndef LIBSTDCXX
> +
> +void
> +__throw_bad_alloc()
> +{
> +#ifndef _LIBCPP_NO_EXCEPTIONS
> + throw bad_alloc();
> +#else
> + _VSTD::abort();
> +#endif
> +}
> +
> +#endif // !LIBSTDCXX
> +
> +} // std
> +
> +#if !defined(__GLIBCXX__) && !defined(_LIBCPP_ABI_MICROSOFT)
>
> // Implement all new and delete operators as weak definitions
> // in this shared library, so that they can be overridden by programs
> @@ -277,107 +295,5 @@ operator delete[] (void* ptr, size_t, st
> ::operator delete[](ptr, alignment);
> }
>
> -#endif // !defined(_LIBCPP_HAS_NO_ALIGNED_ALLOCATION)
> -
> -#endif // !__GLIBCXX__
> -
> -namespace std
> -{
> -
> -#ifndef __GLIBCXX__
> -const nothrow_t nothrow = {};
> -#endif
> -
> -#ifndef _LIBCPPABI_VERSION
> -
> -#ifndef __GLIBCXX__
> -
> -new_handler
> -set_new_handler(new_handler handler) _NOEXCEPT
> -{
> - return __sync_lock_test_and_set(&__new_handler, handler);
> -}
> -
> -new_handler
> -get_new_handler() _NOEXCEPT
> -{
> - return __sync_fetch_and_add(&__new_handler, nullptr);
> -}
> -
> -#endif // !__GLIBCXX__
> -
> -#ifndef LIBCXXRT
> -
> -bad_alloc::bad_alloc() _NOEXCEPT
> -{
> -}
> -
> -#ifndef __GLIBCXX__
> -
> -bad_alloc::~bad_alloc() _NOEXCEPT
> -{
> -}
> -
> -const char*
> -bad_alloc::what() const _NOEXCEPT
> -{
> - return "std::bad_alloc";
> -}
> -
> -#endif // !__GLIBCXX__
> -
> -bad_array_new_length::bad_array_new_length() _NOEXCEPT
> -{
> -}
> -
> -#ifndef __GLIBCXX__
> -
> -bad_array_new_length::~bad_array_new_length() _NOEXCEPT
> -{
> -}
> -
> -const char*
> -bad_array_new_length::what() const _NOEXCEPT
> -{
> - return "bad_array_new_length";
> -}
> -
> -#endif // !__GLIBCXX__
> -
> -#endif //LIBCXXRT
> -
> -bad_array_length::bad_array_length() _NOEXCEPT
> -{
> -}
> -
> -#ifndef __GLIBCXX__
> -
> -bad_array_length::~bad_array_length() _NOEXCEPT
> -{
> -}
> -
> -const char*
> -bad_array_length::what() const _NOEXCEPT
> -{
> - return "bad_array_length";
> -}
> -
> -#endif // !__GLIBCXX__
> -
> -#endif // _LIBCPPABI_VERSION
> -
> -#ifndef LIBSTDCXX
> -
> -void
> -__throw_bad_alloc()
> -{
> -#ifndef _LIBCPP_NO_EXCEPTIONS
> - throw bad_alloc();
> -#else
> - _VSTD::abort();
> -#endif
> -}
> -
> -#endif // !LIBSTDCXX
> -
> -} // std
> +#endif // !_LIBCPP_HAS_NO_ALIGNED_ALLOCATION
> +#endif // !__GLIBCXX__ && !_LIBCPP_ABI_MICROSOFT
>
> Added: libcxx/trunk/src/support/runtime/exception_fallback.ipp
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/src/support/runtime/exception_fallback.ipp?rev=294707&view=auto
>
> ==============================================================================
> --- libcxx/trunk/src/support/runtime/exception_fallback.ipp (added)
> +++ libcxx/trunk/src/support/runtime/exception_fallback.ipp Thu Feb 9
> 22:25:33 2017
> @@ -0,0 +1,182 @@
> +// -*- C++ -*-
>
> +//===----------------------------------------------------------------------===//
> +//
> +// The LLVM Compiler Infrastructure
> +//
> +// This file is dual licensed under the MIT and the University of
> Illinois Open
> +// Source Licenses. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +namespace std {
> +
> +_LIBCPP_SAFE_STATIC static std::terminate_handler __terminate_handler;
> +_LIBCPP_SAFE_STATIC static std::unexpected_handler __unexpected_handler;
> +
> +
> +// libcxxrt provides implementations of these functions itself.
> +unexpected_handler
> +set_unexpected(unexpected_handler func) _NOEXCEPT
> +{
> + return __sync_lock_test_and_set(&__unexpected_handler, func);
> +}
> +
> +unexpected_handler
> +get_unexpected() _NOEXCEPT
> +{
> + return __sync_fetch_and_add(&__unexpected_handler,
> (unexpected_handler)0);
> +
> +}
> +
> +_LIBCPP_NORETURN
> +void unexpected()
> +{
> + (*get_unexpected())();
> + // unexpected handler should not return
> + terminate();
> +}
> +
> +terminate_handler
> +set_terminate(terminate_handler func) _NOEXCEPT
> +{
> + return __sync_lock_test_and_set(&__terminate_handler, func);
> +}
> +
> +terminate_handler
> +get_terminate() _NOEXCEPT
> +{
> + return __sync_fetch_and_add(&__terminate_handler, (terminate_handler)0);
> +
> +}
> +
> +#ifndef __EMSCRIPTEN__ // We provide this in JS
> +_LIBCPP_NORETURN
> +void
> +terminate() _NOEXCEPT
> +{
> +#ifndef _LIBCPP_NO_EXCEPTIONS
> + try
> + {
> +#endif // _LIBCPP_NO_EXCEPTIONS
> + (*get_terminate())();
> + // handler should not return
> + fprintf(stderr, "terminate_handler unexpectedly returned\n");
> + ::abort();
> +#ifndef _LIBCPP_NO_EXCEPTIONS
> + }
> + catch (...)
> + {
> + // handler should not throw exception
> + fprintf(stderr, "terminate_handler unexpectedly threw an
> exception\n");
> + ::abort();
> + }
> +#endif // _LIBCPP_NO_EXCEPTIONS
> +}
> +#endif // !__EMSCRIPTEN__
> +
> +#if !defined(__EMSCRIPTEN__)
> +bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; }
> +
> +int uncaught_exceptions() _NOEXCEPT
> +{
> +#warning uncaught_exception not yet implemented
> + fprintf(stderr, "uncaught_exceptions not yet implemented\n");
> + ::abort();
> +}
> +#endif // !__EMSCRIPTEN__
> +
> +
> +exception::~exception() _NOEXCEPT
> +{
> +}
> +
> +const char* exception::what() const _NOEXCEPT
> +{
> + return "std::exception";
> +}
> +
> +bad_exception::~bad_exception() _NOEXCEPT
> +{
> +}
> +
> +const char* bad_exception::what() const _NOEXCEPT
> +{
> + return "std::bad_exception";
> +}
> +
> +
> +bad_alloc::bad_alloc() _NOEXCEPT
> +{
> +}
> +
> +bad_alloc::~bad_alloc() _NOEXCEPT
> +{
> +}
> +
> +const char*
> +bad_alloc::what() const _NOEXCEPT
> +{
> + return "std::bad_alloc";
> +}
> +
> +bad_array_new_length::bad_array_new_length() _NOEXCEPT
> +{
> +}
> +
> +bad_array_new_length::~bad_array_new_length() _NOEXCEPT
> +{
> +}
> +
> +const char*
> +bad_array_new_length::what() const _NOEXCEPT
> +{
> + return "bad_array_new_length";
> +}
> +
> +
> +bad_array_length::bad_array_length() _NOEXCEPT
> +{
> +}
> +
> +bad_array_length::~bad_array_length() _NOEXCEPT
> +{
> +}
> +
> +const char*
> +bad_array_length::what() const _NOEXCEPT
> +{
> + return "bad_array_length";
> +}
> +
> +
> +bad_cast::bad_cast() _NOEXCEPT
> +{
> +}
> +
> +bad_typeid::bad_typeid() _NOEXCEPT
> +{
> +}
> +
> +#ifndef __GLIBCXX__
> +
> +bad_cast::~bad_cast() _NOEXCEPT
> +{
> +}
> +
> +const char*
> +bad_cast::what() const _NOEXCEPT
> +{
> + return "std::bad_cast";
> +}
> +
> +bad_typeid::~bad_typeid() _NOEXCEPT
> +{
> +}
> +
> +const char*
> +bad_typeid::what() const _NOEXCEPT
> +{
> + return "std::bad_typeid";
> +}
> +
> +} // namespace std
>
> Added: libcxx/trunk/src/support/runtime/exception_glibcxx.ipp
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/src/support/runtime/exception_glibcxx.ipp?rev=294707&view=auto
>
> ==============================================================================
> --- libcxx/trunk/src/support/runtime/exception_glibcxx.ipp (added)
> +++ libcxx/trunk/src/support/runtime/exception_glibcxx.ipp Thu Feb 9
> 22:25:33 2017
> @@ -0,0 +1,38 @@
> +// -*- C++ -*-
>
> +//===----------------------------------------------------------------------===//
> +//
> +// The LLVM Compiler Infrastructure
> +//
> +// This file is dual licensed under the MIT and the University of
> Illinois Open
> +// Source Licenses. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +#ifndef __GLIBCXX__
> +#error header can only be used when targeting libstdc++ or libsupc++
> +#endif
> +
> +namespace std {
> +
> +bad_alloc::bad_alloc() _NOEXCEPT
> +{
> +}
> +
> +bad_array_new_length::bad_array_new_length() _NOEXCEPT
> +{
> +}
> +
> +bad_array_length::bad_array_length() _NOEXCEPT
> +{
> +}
> +
> +
> +bad_cast::bad_cast() _NOEXCEPT
> +{
> +}
> +
> +bad_typeid::bad_typeid() _NOEXCEPT
> +{
> +}
> +
> +} // namespace
>
> Added: libcxx/trunk/src/support/runtime/exception_libcxxabi.ipp
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/src/support/runtime/exception_libcxxabi.ipp?rev=294707&view=auto
>
> ==============================================================================
> --- libcxx/trunk/src/support/runtime/exception_libcxxabi.ipp (added)
> +++ libcxx/trunk/src/support/runtime/exception_libcxxabi.ipp Thu Feb 9
> 22:25:33 2017
> @@ -0,0 +1,28 @@
> +// -*- C++ -*-
>
> +//===----------------------------------------------------------------------===//
> +//
> +// The LLVM Compiler Infrastructure
> +//
> +// This file is dual licensed under the MIT and the University of
> Illinois Open
> +// Source Licenses. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +#ifndef _LIBCPPABI_VERSION
> +#error this header can only be used with libc++abi
> +#endif
> +
> +namespace std {
> +
> +bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; }
> +
> +int uncaught_exceptions() _NOEXCEPT
> +{
> +# if _LIBCPPABI_VERSION > 1101
> + return __cxa_uncaught_exceptions();
> +# else
> + return __cxa_uncaught_exception() ? 1 : 0;
> +# endif
> +}
> +
> +} // namespace std
>
> Added: libcxx/trunk/src/support/runtime/exception_libcxxrt.ipp
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/src/support/runtime/exception_libcxxrt.ipp?rev=294707&view=auto
>
> ==============================================================================
> --- libcxx/trunk/src/support/runtime/exception_libcxxrt.ipp (added)
> +++ libcxx/trunk/src/support/runtime/exception_libcxxrt.ipp Thu Feb 9
> 22:25:33 2017
> @@ -0,0 +1,41 @@
> +// -*- C++ -*-
>
> +//===----------------------------------------------------------------------===//
> +//
> +// The LLVM Compiler Infrastructure
> +//
> +// This file is dual licensed under the MIT and the University of
> Illinois Open
> +// Source Licenses. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +#ifndef LIBCXXRT
> +#error this header may only be used when targeting libcxxrt
> +#endif
> +
> +namespace std {
> +
> +bad_exception::~bad_exception() _NOEXCEPT
> +{
> +}
> +
> +const char* bad_exception::what() const _NOEXCEPT
> +{
> + return "std::bad_exception";
> +}
> +
> +
> +bad_array_length::bad_array_length() _NOEXCEPT
> +{
> +}
> +
> +bad_array_length::~bad_array_length() _NOEXCEPT
> +{
> +}
> +
> +const char*
> +bad_array_length::what() const _NOEXCEPT
> +{
> + return "bad_array_length";
> +}
> +
> +} // namespace std
>
> Added: libcxx/trunk/src/support/runtime/exception_msvc.ipp
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/src/support/runtime/exception_msvc.ipp?rev=294707&view=auto
>
> ==============================================================================
> --- libcxx/trunk/src/support/runtime/exception_msvc.ipp (added)
> +++ libcxx/trunk/src/support/runtime/exception_msvc.ipp Thu Feb 9
> 22:25:33 2017
> @@ -0,0 +1,89 @@
> +// -*- C++ -*-
>
> +//===----------------------------------------------------------------------===//
> +//
> +// The LLVM Compiler Infrastructure
> +//
> +// This file is dual licensed under the MIT and the University of
> Illinois Open
> +// Source Licenses. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +#ifndef _LIBCPP_ABI_MICROSOFT
> +#error this header can only be used when targeting the MSVC ABI
> +#endif
> +
> +#include <stdio.h>
> +#include <stdlib.h>
> +#include <eh.h>
> +#include <corecrt_terminate.h>
> +
> +namespace std {
> +
> +// libcxxrt provides implementations of these functions itself.
> +unexpected_handler
> +set_unexpected(unexpected_handler func) _NOEXCEPT {
> + return ::set_unexpected(func);
> +}
> +
> +unexpected_handler get_unexpected() _NOEXCEPT {
> + return ::_get_unexpected();
> +}
> +
> +_LIBCPP_NORETURN
> +void unexpected() {
> + (*get_unexpected())();
> + // unexpected handler should not return
> + terminate();
> +}
> +
> +terminate_handler set_terminate(terminate_handler func) _NOEXCEPT {
> + return ::set_terminate(func);
> +}
> +
> +terminate_handler get_terminate() _NOEXCEPT {
> + return ::_get_terminate();
> +}
> +
> +_LIBCPP_NORETURN
> +void terminate() _NOEXCEPT
> +{
> +#ifndef _LIBCPP_NO_EXCEPTIONS
> + try
> + {
> +#endif // _LIBCPP_NO_EXCEPTIONS
> + (*get_terminate())();
> + // handler should not return
> + fprintf(stderr, "terminate_handler unexpectedly returned\n");
> + ::abort();
> +#ifndef _LIBCPP_NO_EXCEPTIONS
> + }
> + catch (...)
> + {
> + // handler should not throw exception
> + fprintf(stderr, "terminate_handler unexpectedly threw an
> exception\n");
> + ::abort();
> + }
> +#endif // _LIBCPP_NO_EXCEPTIONS
> +}
> +
> +bool uncaught_exception() _NOEXCEPT { return uncaught_exceptions() > 0; }
> +
> +int uncaught_exceptions() _NOEXCEPT {
> + return __uncaught_exceptions();
> +}
> +
> +bad_array_length::bad_array_length() _NOEXCEPT
> +{
> +}
> +
> +bad_array_length::~bad_array_length() _NOEXCEPT
> +{
> +}
> +
> +const char*
> +bad_array_length::what() const _NOEXCEPT
> +{
> + return "bad_array_length";
> +}
> +
> +} // namespace std
>
> Added: libcxx/trunk/src/support/runtime/exception_pointer_cxxabi.ipp
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/src/support/runtime/exception_pointer_cxxabi.ipp?rev=294707&view=auto
>
> ==============================================================================
> --- libcxx/trunk/src/support/runtime/exception_pointer_cxxabi.ipp (added)
> +++ libcxx/trunk/src/support/runtime/exception_pointer_cxxabi.ipp Thu Feb
> 9 22:25:33 2017
> @@ -0,0 +1,74 @@
> +// -*- C++ -*-
>
> +//===----------------------------------------------------------------------===//
> +//
> +// The LLVM Compiler Infrastructure
> +//
> +// This file is dual licensed under the MIT and the University of
> Illinois Open
> +// Source Licenses. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +#ifndef HAVE_DEPENDENT_EH_ABI
> +#error this header may only be used with libc++abi or libcxxrt
> +#endif
> +
> +namespace std {
> +
> +exception_ptr::~exception_ptr() _NOEXCEPT {
> + __cxa_decrement_exception_refcount(__ptr_);
> +}
> +
> +exception_ptr::exception_ptr(const exception_ptr& other) _NOEXCEPT
> + : __ptr_(other.__ptr_)
> +{
> + __cxa_increment_exception_refcount(__ptr_);
> +}
> +
> +exception_ptr& exception_ptr::operator=(const exception_ptr& other)
> _NOEXCEPT
> +{
> + if (__ptr_ != other.__ptr_)
> + {
> + __cxa_increment_exception_refcount(other.__ptr_);
> + __cxa_decrement_exception_refcount(__ptr_);
> + __ptr_ = other.__ptr_;
> + }
> + return *this;
> +}
> +
> +nested_exception::nested_exception() _NOEXCEPT
> + : __ptr_(current_exception())
> +{
> +}
> +
> +nested_exception::~nested_exception() _NOEXCEPT
> +{
> +}
> +
> +_LIBCPP_NORETURN
> +void
> +nested_exception::rethrow_nested() const
> +{
> + if (__ptr_ == nullptr)
> + terminate();
> + rethrow_exception(__ptr_);
> +}
> +
> +exception_ptr current_exception() _NOEXCEPT
> +{
> + // be nicer if there was a constructor that took a ptr, then
> + // this whole function would be just:
> + // return exception_ptr(__cxa_current_primary_exception());
> + exception_ptr ptr;
> + ptr.__ptr_ = __cxa_current_primary_exception();
> + return ptr;
> +}
> +
> +_LIBCPP_NORETURN
> +void rethrow_exception(exception_ptr p)
> +{
> + __cxa_rethrow_primary_exception(p.__ptr_);
> + // if p.__ptr_ is NULL, above returns so we terminate
> + terminate();
> +}
> +
> +} // namespace std
>
> Added: libcxx/trunk/src/support/runtime/exception_pointer_glibcxx.ipp
> URL:
> http://llvm.org/viewvc/llvm-project/libcxx/trunk/src/support/runtime/exception_pointer_glibcxx.ipp?rev=294707&view=auto
>
> ==============================================================================
> --- libcxx/trunk/src/support/runtime/exception_pointer_glibcxx.ipp (added)
> +++ libcxx/trunk/src/support/runtime/exception_pointer_glibcxx.ipp Thu
> Feb 9 22:25:33 2017
> @@ -0,0 +1,74 @@
> +// -*- C++ -*-
>
> +//===----------------------------------------------------------------------===//
> +//
> +// The LLVM Compiler Infrastructure
> +//
> +// This file is dual licensed under the MIT and the University of
> Illinois Open
> +// Source Licenses. See LICENSE.TXT for details.
> +//
>
> +//===----------------------------------------------------------------------===//
> +
> +// libsupc++ does not implement the dependent EH ABI and the functionality
> +// it uses to implement std::exception_ptr (which it declares as an alias
> of
> +// std::__exception_ptr::exception_ptr) is not directly exported to
> clients. So
> +// we have little choice but to hijack
> std::__exception_ptr::exception_ptr's
> +// (which fortunately has the same layout as our std::exception_ptr) copy
> +// constructor, assignment operator and destructor (which are part of its
> +// stable ABI), and its
> rethrow_exception(std::__exception_ptr::exception_ptr)
> +// function.
> +
> +namespace __exception_ptr
> +{
> +
> +struct exception_ptr
> +{
> + void* __ptr_;
> +
> + exception_ptr(const exception_ptr&) _NOEXCEPT;
> + exception_ptr& operator=(const exception_ptr&) _NOEXCEPT;
> + ~exception_ptr() _NOEXCEPT;
> +};
> +
> +}
> +
> +_LIBCPP_NORETURN void rethrow_exception(__exception_ptr::exception_ptr);
> +
> +exception_ptr::~exception_ptr() _NOEXCEPT
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-commits/attachments/20170210/19f0b341/attachment-0001.html>
More information about the cfe-commits
mailing list