[except.terminate]

# 14 Exception handling [[except]](./#except)

## 14.6 Special functions [[except.special]](except.special#except.terminate)

### 14.6.2 The std​::​terminate function [except.terminate]

[1](#1)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/exceptions.tex#L1030)

Some errors in a program cannot be recovered from, such as when an exception
is not handled or a std​::​thread object is destroyed while its thread
function is still executing[.](#1.sentence-1)

In such cases,
the function std​::​terminate ([[exception.terminate]](exception.terminate "17.9.5 Abnormal termination")) is invoked[.](#1.sentence-2)

[*Note [1](#note-1)*:

These situations are:

- [(1.1)](#1.1)

when the exception handling mechanism, after completing
the initialization of the exception object
but before
activation of a handler for the exception ([[except.throw]](except.throw "14.2 Throwing an exception")),
calls a function that exits
via an exception, or

- [(1.2)](#1.2)

when the exception handling mechanism cannot find a handler for a thrown exception ([[except.handle]](except.handle "14.4 Handling an exception")), or

- [(1.3)](#1.3)

when the search for a [handler](except.handle "14.4 Handling an exception [except.handle]") exits the function body of a function
with a non-throwing [exception specification](except.spec "14.5 Exception specifications [except.spec]"),
including when a contract-violation handler
invoked from an evaluation of
a function contract assertion ([[basic.contract.eval]](basic.contract.eval "6.11.2 Evaluation")) associated with the function
exits via an exception,
or

- [(1.4)](#1.4)

when the destruction of an object during [stack unwinding](except.ctor#def:stack_unwinding "14.3 Stack unwinding [except.ctor]") terminates by throwing an exception, or

- [(1.5)](#1.5)

when initialization of a non-block
variable with static or thread storage duration ([[basic.start.dynamic]](basic.start.dynamic "6.10.3.3 Dynamic initialization of non-block variables"))
exits via an exception, or

- [(1.6)](#1.6)

when destruction of an object with static or thread storage duration exits
via an exception ([[basic.start.term]](basic.start.term "6.10.3.4 Termination")), or

- [(1.7)](#1.7)

when execution of a function registered withstd​::​atexit or std​::​at_quick_exit exits via an exception ([[support.start.term]](support.start.term "17.5 Startup and termination")), or

- [(1.8)](#1.8)

when a[*throw-expression*](expr.throw#nt:throw-expression "7.6.18 Throwing an exception [expr.throw]") ([[expr.throw]](expr.throw "7.6.18 Throwing an exception"))
with no operand attempts to rethrow an exception and no exception is being
handled ([[except.throw]](except.throw "14.2 Throwing an exception")), or

- [(1.9)](#1.9)

when the function std​::​nested_exception​::​rethrow_nested is called for an object
that has captured no exception ([[except.nested]](except.nested "17.9.8 nested_­exception")), or

- [(1.10)](#1.10)

when execution of the initial function of a thread exits via
an exception ([[thread.thread.constr]](thread.thread.constr "32.4.3.3 Constructors")), or

- [(1.11)](#1.11)

for a parallel algorithm whose ExecutionPolicy specifies such
behavior ([[execpol.seq]](execpol.seq "26.3.6.3 Sequenced execution policy"), [[execpol.par]](execpol.par "26.3.6.4 Parallel execution policy"), [[execpol.parunseq]](execpol.parunseq "26.3.6.5 Parallel and unsequenced execution policy")),
when execution of an element access function ([[algorithms.parallel.defns]](algorithms.parallel.defns "26.3.1 Preamble"))
of the parallel algorithm exits via an exception ([[algorithms.parallel.exceptions]](algorithms.parallel.exceptions "26.3.4 Parallel algorithm exceptions")), or

- [(1.12)](#1.12)

when the destructor or the move assignment operator is invoked on an object
of type std​::​thread that refers to
a joinable thread ([[thread.thread.destr]](thread.thread.destr "32.4.3.4 Destructor"), [[thread.thread.assign]](thread.thread.assign "32.4.3.5 Assignment")), or

- [(1.13)](#1.13)

when a call to a wait(), wait_until(), or wait_for() function on a condition variable ([[thread.condition.condvar]](thread.condition.condvar "32.7.4 Class condition_­variable"), [[thread.condition.condvarany]](thread.condition.condvarany "32.7.5 Class condition_­variable_­any"))
fails to meet a postcondition, or

- [(1.14)](#1.14)

when a callback invocation exits via an exception
when requesting stop on
a std​::​stop_source or
a std​::​inplace_stop_source ([[stopsource.mem]](stopsource.mem "32.3.5.3 Member functions"), [[stopsource.inplace.mem]](stopsource.inplace.mem "32.3.9.3 Member functions")),
or in the constructor ofstd​::​stop_callback orstd​::​inplace_stop_callback ([[stopcallback.cons]](stopcallback.cons "32.3.6.2 Constructors and destructor"), [[stopcallback.inplace.cons]](stopcallback.inplace.cons "32.3.10.2 Constructors and destructor"))
when a callback invocation exits via an exception, or

- [(1.15)](#1.15)

when a run_loop object is destroyed
that is still in the running state ([[exec.run.loop]](exec.run.loop "33.12.1 execution​::​run_­loop")), or

- [(1.16)](#1.16)

when unhandled_stopped is called on
a with_awaitable_senders<T> object ([[exec.with.awaitable.senders]](exec.with.awaitable.senders "33.13.2 execution​::​with_­awaitable_­senders"))
whose continuation is not a handle to a coroutine
whose promise type has an unhandled_stopped member function, or

- [(1.17)](#1.17)

when an object scope of typestd​::​execution​::​simple_counting_scope orstd​::​execution​::​counting_scope is destroyed andscope.*state* is not equal to*joined*,*unused*, or*unused-and-closed* ([[exec.simple.counting.ctor]](exec.simple.counting.ctor "33.14.2.2.2 Constructor and Destructor")), or

- [(1.18)](#1.18)

when std​::​execution​::​get_parallel_scheduler is called andstd​::​execution​::​system_context_replaceability​::​query_parallel_scheduler_backend() returns a null pointer value ([[exec.par.scheduler]](exec.par.scheduler "33.15 Parallel scheduler")), or

- [(1.19)](#1.19)

when an exception is thrown from a coroutine std​::​execution​::​task ([[exec.task]](exec.task "33.13.6 execution​::​task"))
which doesn't support a std​::​execution​::​set_error_t(std​::​exception_ptr) completion[.](#1.sentence-3)

â *end note*]

[2](#2)

[#](http://github.com/Eelis/draft/tree/9adde4bc1c62ec234483e63ea3b70a59724c745a/source/exceptions.tex#L1149)

In the situation where no matching handler is found, it isimplementation-defined
whether or not the stack is unwound
before std​::​terminate is invoked[.](#2.sentence-1)

In the situation where the search for a handler ([[except.handle]](except.handle "14.4 Handling an exception"))
exits the function body of a function
with a non-throwing exception specification ([[except.spec]](except.spec "14.5 Exception specifications")), it isimplementation-defined
whether the stack is unwound, unwound partially, or not unwound at all
before the function std​::​terminate is invoked[.](#2.sentence-2)

In all other situations, the stack shall not be unwound before
the function std​::​terminate is invoked[.](#2.sentence-3)

An implementation is not permitted to finish stack unwinding
prematurely based on a determination that the unwind process
will eventually cause an invocation of the functionstd​::​terminate[.](#2.sentence-4)
