21 Language support library [language.support]

21.8 Exception handling [support.exception]

21.8.7 nested_­exception [except.nested]

namespace std {
  class nested_exception {
  public:
    nested_exception() noexcept;
    nested_exception(const nested_exception&) noexcept = default;
    nested_exception& operator=(const nested_exception&) noexcept = default;
    virtual ~nested_exception() = default;

    // access functions
    [[noreturn]] void rethrow_nested() const;
    exception_ptr nested_ptr() const noexcept;
  };

  template<class T> [[noreturn]] void throw_with_nested(T&& t);
  template <class E> void rethrow_if_nested(const E& e);
}

Класс nested_­exception предназначен для использования в качестве миксина посредством множественного наследования. Он фиксирует текущее обрабатываемое исключение и сохраняет его для дальнейшего использования.

[ Note: nested_­exception имеет виртуальный деструктор, чтобы сделать его полиморфным классом. Его наличие можно проверить с помощью dynamic_­cast. ]end note

nested_exception() noexcept;

Effects: Конструктор вызывает current_­exception() и сохраняет возвращаемое значение.

[[noreturn]] void rethrow_nested() const;

Effects: Если nested_­ptr() возвращает нулевой указатель, функция вызывает std​::​terminate(). В противном случае он генерирует сохраненное исключение, захваченное *this.

exception_ptr nested_ptr() const noexcept;

Returns: Сохраненное исключение, захваченное этим nested_­exception объектом.

template <class T> [[noreturn]] void throw_with_nested(T&& t);

Пусть U будет decay_­t<T>.

Requires: U будет CopyConstructible.

Throws: Если is_­class_­v<U> && !is_­final_­v<U> && !is_­base_­of_­v<nested_­exception, U> это true, исключение неопределенного типа , который публично производный от обоего U и nested_­exception и построенного std​::​forward<T>(t), в противном случае std​::​forward<T>(t).

template <class E> void rethrow_if_nested(const E& e);

Effects: Если E это не полиморфный тип класса, или если nested_­exception это недоступный или неоднозначный базовый класс E, эффекта не будет. В противном случае выполняет:

if (auto p = dynamic_cast<const nested_exception*>(addressof(e)))
  p->rethrow_nested();