// -*- C++ -*- //===-------------------------- exception ---------------------------------===// // // The LLVM Compiler Infrastructure // // This file is distributed under the University of Illinois Open Source // License. See LICENSE.TXT for details. // //===----------------------------------------------------------------------===// #ifndef _LIBCPP_EXCEPTION #define _LIBCPP_EXCEPTION /* exception synopsis namespace std { class exception { public: exception() throw(); exception(const exception&) throw(); exception& operator=(const exception&) throw(); virtual ~exception() throw(); virtual const char* what() const throw(); }; class bad_exception : public exception { public: bad_exception() throw(); bad_exception(const bad_exception&) throw(); bad_exception& operator=(const bad_exception&) throw(); virtual ~bad_exception() throw(); virtual const char* what() const throw(); }; typedef void (*unexpected_handler)(); unexpected_handler set_unexpected(unexpected_handler f ) throw(); void unexpected [[noreturn]] (); typedef void (*terminate_handler)(); terminate_handler set_terminate(terminate_handler f ) throw(); void terminate [[noreturn]] (); bool uncaught_exception() throw(); typedef unspecified exception_ptr; exception_ptr current_exception(); void rethrow_exception [[noreturn]] (exception_ptr p); template exception_ptr make_exception_ptr(E e); class nested_exception { public: nested_exception() throw(); nested_exception(const nested_exception&) throw() = default; nested_exception& operator=(const nested_exception&) throw() = default; virtual ~nested_exception() = default; // access functions void rethrow_nested [[noreturn]] () const; exception_ptr nested_ptr() const; }; template void throw_with_nested [[noreturn]] (T&& t); template void rethrow_if_nested(const E& e); } // std */ #include <__config> #include #include #pragma GCC system_header namespace std // purposefully not using versioning namespace { class _LIBCPP_EXCEPTION_ABI exception { public: _LIBCPP_INLINE_VISIBILITY exception() throw() {} virtual ~exception() throw(); virtual const char* what() const throw(); }; class _LIBCPP_EXCEPTION_ABI bad_exception : public exception { public: _LIBCPP_INLINE_VISIBILITY bad_exception() throw() {} virtual ~bad_exception() throw(); virtual const char* what() const throw(); }; typedef void (*unexpected_handler)(); _LIBCPP_VISIBLE unexpected_handler set_unexpected(unexpected_handler) throw(); _LIBCPP_VISIBLE void unexpected(); typedef void (*terminate_handler)(); _LIBCPP_VISIBLE terminate_handler set_terminate(terminate_handler) throw(); _LIBCPP_VISIBLE void terminate() __attribute__((__noreturn__)); _LIBCPP_VISIBLE bool uncaught_exception() throw(); class exception_ptr; exception_ptr current_exception(); void rethrow_exception(exception_ptr); // noreturn class exception_ptr { void* __ptr_; public: exception_ptr() : __ptr_() {} exception_ptr(nullptr_t) : __ptr_() {} exception_ptr(const exception_ptr&); exception_ptr& operator=(const exception_ptr&); ~exception_ptr(); // explicit operator bool() const {return __ptr_ != nullptr;} friend bool operator==(const exception_ptr& __x, const exception_ptr& __y) {return __x.__ptr_ == __y.__ptr_;} friend bool operator!=(const exception_ptr& __x, const exception_ptr& __y) {return !(__x == __y);} friend exception_ptr current_exception(); friend void rethrow_exception(exception_ptr); // noreturn }; template exception_ptr make_exception_ptr(_E __e) { #ifndef _LIBCPP_NO_EXCEPTIONS try { throw __e; } catch (...) { return current_exception(); } #endif } // nested_exception class _LIBCPP_EXCEPTION_ABI nested_exception { exception_ptr __ptr_; public: nested_exception(); // nested_exception(const nested_exception&) throw() = default; // nested_exception& operator=(const nested_exception&) throw() = default; virtual ~nested_exception(); // access functions void rethrow_nested /*[[noreturn]]*/ () const; exception_ptr nested_ptr() const {return __ptr_;} }; template struct __nested : public _Tp, public nested_exception { explicit __nested(const _Tp& __t) : _Tp(__t) {} }; template void #ifdef _LIBCPP_MOVE throw_with_nested /*[[noreturn]]*/ (_Tp&& __t, typename enable_if< is_class::type>::value && !is_base_of::type>::value >::type* = 0) #else throw_with_nested (_Tp& __t, typename enable_if< is_class<_Tp>::value && !is_base_of::value >::type* = 0) #endif { #ifndef _LIBCPP_NO_EXCEPTIONS throw __nested::type>(_STD::forward<_Tp>(__t)); #endif } template void #ifdef _LIBCPP_MOVE throw_with_nested /*[[noreturn]]*/ (_Tp&& __t, typename enable_if< !is_class::type>::value || is_base_of::type>::value >::type* = 0) #else throw_with_nested (_Tp& __t, typename enable_if< !is_class<_Tp>::value || is_base_of::value >::type* = 0) #endif { #ifndef _LIBCPP_NO_EXCEPTIONS throw _STD::forward<_Tp>(__t); #endif } template inline void rethrow_if_nested(const _E& __e, typename enable_if< is_polymorphic<_E>::value >::type* = 0) { const nested_exception* __nep = dynamic_cast(&__e); if (__nep) __nep->rethrow_nested(); } template inline void rethrow_if_nested(const _E& __e, typename enable_if< !is_polymorphic<_E>::value >::type* = 0) { } } // std #endif // _LIBCPP_EXCEPTION