exception revision 261272
1227825Stheraven// -*- C++ -*- 2227825Stheraven//===-------------------------- exception ---------------------------------===// 3227825Stheraven// 4227825Stheraven// The LLVM Compiler Infrastructure 5227825Stheraven// 6227825Stheraven// This file is dual licensed under the MIT and the University of Illinois Open 7227825Stheraven// Source Licenses. See LICENSE.TXT for details. 8227825Stheraven// 9227825Stheraven//===----------------------------------------------------------------------===// 10227825Stheraven 11227825Stheraven#ifndef _LIBCPP_EXCEPTION 12227825Stheraven#define _LIBCPP_EXCEPTION 13227825Stheraven 14227825Stheraven/* 15227825Stheraven exception synopsis 16227825Stheraven 17227825Stheravennamespace std 18227825Stheraven{ 19227825Stheraven 20227825Stheravenclass exception 21227825Stheraven{ 22227825Stheravenpublic: 23227825Stheraven exception() noexcept; 24227825Stheraven exception(const exception&) noexcept; 25227825Stheraven exception& operator=(const exception&) noexcept; 26227825Stheraven virtual ~exception() noexcept; 27227825Stheraven virtual const char* what() const noexcept; 28227825Stheraven}; 29227825Stheraven 30227825Stheravenclass bad_exception 31227825Stheraven : public exception 32227825Stheraven{ 33227825Stheravenpublic: 34227825Stheraven bad_exception() noexcept; 35227825Stheraven bad_exception(const bad_exception&) noexcept; 36227825Stheraven bad_exception& operator=(const bad_exception&) noexcept; 37227825Stheraven virtual ~bad_exception() noexcept; 38227825Stheraven virtual const char* what() const noexcept; 39227825Stheraven}; 40227825Stheraven 41227825Stheraventypedef void (*unexpected_handler)(); 42227825Stheravenunexpected_handler set_unexpected(unexpected_handler f ) noexcept; 43227825Stheravenunexpected_handler get_unexpected() noexcept; 44227825Stheraven[[noreturn]] void unexpected(); 45227825Stheraven 46227825Stheraventypedef void (*terminate_handler)(); 47227825Stheraventerminate_handler set_terminate(terminate_handler f ) noexcept; 48227825Stheraventerminate_handler get_terminate() noexcept; 49227825Stheraven[[noreturn]] void terminate() noexcept; 50227825Stheraven 51227825Stheravenbool uncaught_exception() noexcept; 52227825Stheraven 53227825Stheraventypedef unspecified exception_ptr; 54227825Stheraven 55227825Stheravenexception_ptr current_exception() noexcept; 56227825Stheravenvoid rethrow_exception [[noreturn]] (exception_ptr p); 57227825Stheraventemplate<class E> exception_ptr make_exception_ptr(E e) noexcept; 58227825Stheraven 59227825Stheravenclass nested_exception 60227825Stheraven{ 61227825Stheravenpublic: 62227825Stheraven nested_exception() noexcept; 63227825Stheraven nested_exception(const nested_exception&) noexcept = default; 64227825Stheraven nested_exception& operator=(const nested_exception&) noexcept = default; 65227825Stheraven virtual ~nested_exception() = default; 66227825Stheraven 67227825Stheraven // access functions 68227825Stheraven [[noreturn]] void rethrow_nested() const; 69227825Stheraven exception_ptr nested_ptr() const noexcept; 70227825Stheraven}; 71227825Stheraven 72227825Stheraventemplate <class T> [[noreturn]] void throw_with_nested(T&& t); 73227825Stheraventemplate <class E> void rethrow_if_nested(const E& e); 74227825Stheraven 75227825Stheraven} // std 76227825Stheraven 77227825Stheraven*/ 78227825Stheraven 79227825Stheraven#include <__config> 80227825Stheraven#include <cstddef> 81227825Stheraven#include <type_traits> 82227825Stheraven 83227825Stheraven#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) 84227825Stheraven#pragma GCC system_header 85227825Stheraven#endif 86227825Stheraven 87227825Stheravennamespace std // purposefully not using versioning namespace 88227825Stheraven{ 89227825Stheraven 90227825Stheravenclass _LIBCPP_EXCEPTION_ABI exception 91227825Stheraven{ 92227825Stheravenpublic: 93227825Stheraven _LIBCPP_INLINE_VISIBILITY exception() _NOEXCEPT {} 94227825Stheraven virtual ~exception() _NOEXCEPT; 95227825Stheraven virtual const char* what() const _NOEXCEPT; 96227825Stheraven}; 97227825Stheraven 98227825Stheravenclass _LIBCPP_EXCEPTION_ABI bad_exception 99227825Stheraven : public exception 100227825Stheraven{ 101227825Stheravenpublic: 102227825Stheraven _LIBCPP_INLINE_VISIBILITY bad_exception() _NOEXCEPT {} 103227825Stheraven virtual ~bad_exception() _NOEXCEPT; 104227825Stheraven virtual const char* what() const _NOEXCEPT; 105227825Stheraven}; 106227825Stheraven 107227825Stheraventypedef void (*unexpected_handler)(); 108249989Sdim_LIBCPP_FUNC_VIS unexpected_handler set_unexpected(unexpected_handler) _NOEXCEPT; 109249989Sdim_LIBCPP_FUNC_VIS unexpected_handler get_unexpected() _NOEXCEPT; 110249989Sdim_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void unexpected(); 111227825Stheraven 112227825Stheraventypedef void (*terminate_handler)(); 113249989Sdim_LIBCPP_FUNC_VIS terminate_handler set_terminate(terminate_handler) _NOEXCEPT; 114249989Sdim_LIBCPP_FUNC_VIS terminate_handler get_terminate() _NOEXCEPT; 115249989Sdim_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void terminate() _NOEXCEPT; 116227825Stheraven 117249989Sdim_LIBCPP_FUNC_VIS bool uncaught_exception() _NOEXCEPT; 118227825Stheraven 119249989Sdimclass _LIBCPP_TYPE_VIS exception_ptr; 120227825Stheraven 121261272Sdim_LIBCPP_FUNC_VIS exception_ptr current_exception() _NOEXCEPT; 122261272Sdim_LIBCPP_NORETURN _LIBCPP_FUNC_VIS void rethrow_exception(exception_ptr); 123227825Stheraven 124249989Sdimclass _LIBCPP_TYPE_VIS exception_ptr 125227825Stheraven{ 126227825Stheraven void* __ptr_; 127227825Stheravenpublic: 128227825Stheraven _LIBCPP_INLINE_VISIBILITY exception_ptr() _NOEXCEPT : __ptr_() {} 129227825Stheraven _LIBCPP_INLINE_VISIBILITY exception_ptr(nullptr_t) _NOEXCEPT : __ptr_() {} 130227825Stheraven exception_ptr(const exception_ptr&) _NOEXCEPT; 131227825Stheraven exception_ptr& operator=(const exception_ptr&) _NOEXCEPT; 132227825Stheraven ~exception_ptr() _NOEXCEPT; 133227825Stheraven 134227825Stheraven _LIBCPP_INLINE_VISIBILITY 135232924Stheraven _LIBCPP_EXPLICIT 136227825Stheraven operator bool() const _NOEXCEPT {return __ptr_ != nullptr;} 137227825Stheraven 138227825Stheraven friend _LIBCPP_INLINE_VISIBILITY 139227825Stheraven bool operator==(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT 140227825Stheraven {return __x.__ptr_ == __y.__ptr_;} 141227825Stheraven friend _LIBCPP_INLINE_VISIBILITY 142227825Stheraven bool operator!=(const exception_ptr& __x, const exception_ptr& __y) _NOEXCEPT 143227825Stheraven {return !(__x == __y);} 144227825Stheraven 145261272Sdim friend _LIBCPP_FUNC_VIS exception_ptr current_exception() _NOEXCEPT; 146261272Sdim friend _LIBCPP_FUNC_VIS void rethrow_exception(exception_ptr); 147227825Stheraven}; 148227825Stheraven 149232924Stheraventemplate<class _Ep> 150227825Stheravenexception_ptr 151232924Stheravenmake_exception_ptr(_Ep __e) _NOEXCEPT 152227825Stheraven{ 153227825Stheraven#ifndef _LIBCPP_NO_EXCEPTIONS 154227825Stheraven try 155227825Stheraven { 156227825Stheraven throw __e; 157227825Stheraven } 158227825Stheraven catch (...) 159227825Stheraven { 160227825Stheraven return current_exception(); 161227825Stheraven } 162227825Stheraven#endif // _LIBCPP_NO_EXCEPTIONS 163227825Stheraven} 164227825Stheraven 165227825Stheraven// nested_exception 166227825Stheraven 167227825Stheravenclass _LIBCPP_EXCEPTION_ABI nested_exception 168227825Stheraven{ 169227825Stheraven exception_ptr __ptr_; 170227825Stheravenpublic: 171227825Stheraven nested_exception() _NOEXCEPT; 172227825Stheraven// nested_exception(const nested_exception&) noexcept = default; 173227825Stheraven// nested_exception& operator=(const nested_exception&) noexcept = default; 174227825Stheraven virtual ~nested_exception() _NOEXCEPT; 175227825Stheraven 176227825Stheraven // access functions 177241900Sdim _LIBCPP_NORETURN void rethrow_nested() const; 178227825Stheraven _LIBCPP_INLINE_VISIBILITY exception_ptr nested_ptr() const _NOEXCEPT {return __ptr_;} 179227825Stheraven}; 180227825Stheraven 181227825Stheraventemplate <class _Tp> 182227825Stheravenstruct __nested 183227825Stheraven : public _Tp, 184227825Stheraven public nested_exception 185227825Stheraven{ 186227825Stheraven _LIBCPP_INLINE_VISIBILITY explicit __nested(const _Tp& __t) : _Tp(__t) {} 187227825Stheraven}; 188227825Stheraven 189227825Stheraventemplate <class _Tp> 190241900Sdim_LIBCPP_NORETURN 191227825Stheravenvoid 192227825Stheraven#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES 193227825Stheraventhrow_with_nested(_Tp&& __t, typename enable_if< 194227825Stheraven is_class<typename remove_reference<_Tp>::type>::value && 195227825Stheraven !is_base_of<nested_exception, typename remove_reference<_Tp>::type>::value 196227825Stheraven >::type* = 0) 197227825Stheraven#else // _LIBCPP_HAS_NO_RVALUE_REFERENCES 198227825Stheraventhrow_with_nested (_Tp& __t, typename enable_if< 199227825Stheraven is_class<_Tp>::value && !is_base_of<nested_exception, _Tp>::value 200227825Stheraven >::type* = 0) 201227825Stheraven#endif // _LIBCPP_HAS_NO_RVALUE_REFERENCES 202227825Stheraven{ 203227825Stheraven#ifndef _LIBCPP_NO_EXCEPTIONS 204227825Stheraven throw __nested<typename remove_reference<_Tp>::type>(_VSTD::forward<_Tp>(__t)); 205227825Stheraven#endif 206227825Stheraven} 207227825Stheraven 208227825Stheraventemplate <class _Tp> 209241900Sdim_LIBCPP_NORETURN 210227825Stheravenvoid 211227825Stheraven#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES 212227825Stheraventhrow_with_nested(_Tp&& __t, typename enable_if< 213227825Stheraven !is_class<typename remove_reference<_Tp>::type>::value || 214227825Stheraven is_base_of<nested_exception, typename remove_reference<_Tp>::type>::value 215227825Stheraven >::type* = 0) 216227825Stheraven#else // _LIBCPP_HAS_NO_RVALUE_REFERENCES 217227825Stheraventhrow_with_nested (_Tp& __t, typename enable_if< 218227825Stheraven !is_class<_Tp>::value || is_base_of<nested_exception, _Tp>::value 219227825Stheraven >::type* = 0) 220227825Stheraven#endif // _LIBCPP_HAS_NO_RVALUE_REFERENCES 221227825Stheraven{ 222227825Stheraven#ifndef _LIBCPP_NO_EXCEPTIONS 223227825Stheraven throw _VSTD::forward<_Tp>(__t); 224227825Stheraven#endif 225227825Stheraven} 226227825Stheraven 227232924Stheraventemplate <class _Ep> 228227825Stheraveninline _LIBCPP_INLINE_VISIBILITY 229227825Stheravenvoid 230232924Stheravenrethrow_if_nested(const _Ep& __e, typename enable_if< 231232924Stheraven is_polymorphic<_Ep>::value 232227825Stheraven >::type* = 0) 233227825Stheraven{ 234227825Stheraven const nested_exception* __nep = dynamic_cast<const nested_exception*>(&__e); 235227825Stheraven if (__nep) 236227825Stheraven __nep->rethrow_nested(); 237227825Stheraven} 238227825Stheraven 239232924Stheraventemplate <class _Ep> 240227825Stheraveninline _LIBCPP_INLINE_VISIBILITY 241227825Stheravenvoid 242232924Stheravenrethrow_if_nested(const _Ep&, typename enable_if< 243232924Stheraven !is_polymorphic<_Ep>::value 244227825Stheraven >::type* = 0) 245227825Stheraven{ 246227825Stheraven} 247227825Stheraven 248227825Stheraven} // std 249227825Stheraven 250227825Stheraven#endif // _LIBCPP_EXCEPTION 251