%\pagebreak
\section{Cancellation Constructs}
\label{sec:cancellation}
\index{cancellation!cancel construct@\kcode{cancel} construct}
\index{constructs!cancel@\kcode{cancel}}
\index{cancel construct@\kcode{cancel} construct}

The examples in this section show how the \kcode{cancel} directive can be used to terminate 
an OpenMP region. Cancellation of the binding region is activated only if the \plc{cancel-var} ICV 
is true, in which case the \kcode{cancel} construct (except \kcode{taskgroup}) causes the encountering 
\kcode{task} to continue execution at the end of the binding. If the \plc{cancel-var} ICV is false, the 
\kcode{cancel} construct is ignored.

\index{cancellation!for parallel region@for \kcode{parallel} region}
\index{cancellation!for worksharing region}

In the following example although the \kcode{cancel} construct terminates the OpenMP 
worksharing region, programmers must still track the exception through the pointer 
\ucode{ex} and issue a cancellation for the \kcode{parallel} region if an exception has
been raised. The primary thread checks the exception pointer to make sure that the 
exception is properly handled in the sequential part. If cancellation of the \kcode{parallel} 
region has been requested, some threads might have executed \ucode{phase_1()}. 
However, it is guaranteed that none of the threads executed \ucode{phase_2()}.

\cppexample[4.0]{cancellation}{1}


\index{cancellation!cancellation point construct@\kcode{cancellation point} construct}
\index{constructs!cancellation point@\kcode{cancellation point}}
\index{cancellation point construct@\kcode{cancellation point} construct}
The following example illustrates the use of the \kcode{cancel} construct in error 
handling. If there is an error condition from the \bcode{allocate} statement, 
the cancellation is activated. The encountering thread sets the shared variable 
\ucode{err} and other threads of the binding thread set proceed to the end of 
the worksharing construct after the cancellation has been activated. 

\ffreeexample[4.0]{cancellation}{1}

\index{cancellation!for taskgroup region@for \kcode{taskgroup} region}
The following example shows how to cancel a parallel search on a binary tree as 
soon as the search value has been detected. The code creates a task to descend 
into the child nodes of the current tree node. If the search value has been found, 
the code remembers the tree node with the found value through an \kcode{atomic} 
write to the result variable (\ucode{found}) and then cancels execution of all search tasks. The
function \ucode{search_tree_parallel} groups all search tasks into a single 
task group to control the effect of the \kcode{cancel taskgroup} directive. The 
\ucode{level} argument is used to create undeferred tasks after the first ten 
levels of the tree.

\cexample[5.1]{cancellation}{2}


The following is the equivalent parallel search example in Fortran.
The code uses the \kcode{atomic write} directive for atomically
updating pointer variables -- a feature defined in OpenMP 6.0.
For earlier versions of OpenMP, the \kcode{critical} directive could 
be used instead.

\ffreeexample[6.0]{cancellation}{2}


