• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1<html>
2<head>
3<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
4<title>Context switching with call/cc</title>
5<link rel="stylesheet" href="../../../../../doc/src/boostbook.css" type="text/css">
6<meta name="generator" content="DocBook XSL Stylesheets V1.79.1">
7<link rel="home" href="../index.html" title="Chapter 1. Context">
8<link rel="up" href="../index.html" title="Chapter 1. Context">
9<link rel="prev" href="ff/class__fiber_.html" title="Class fiber">
10<link rel="next" href="cc/implementations__fcontext_t__ucontext_t_and_winfiber.html" title="Implementations: fcontext_t, ucontext_t and WinFiber">
11</head>
12<body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
13<table cellpadding="2" width="100%"><tr>
14<td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../boost.png"></td>
15<td align="center"><a href="../../../../../index.html">Home</a></td>
16<td align="center"><a href="../../../../../libs/libraries.htm">Libraries</a></td>
17<td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
18<td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
19<td align="center"><a href="../../../../../more/index.htm">More</a></td>
20</tr></table>
21<hr>
22<div class="spirit-nav">
23<a accesskey="p" href="ff/class__fiber_.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="cc/implementations__fcontext_t__ucontext_t_and_winfiber.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
24</div>
25<div class="section">
26<div class="titlepage"><div><div><h2 class="title" style="clear: both">
27<a name="context.cc"></a><a name="cc"></a><a class="link" href="cc.html" title="Context switching with call/cc">Context switching with call/cc</a>
28</h2></div></div></div>
29<div class="toc"><dl class="toc">
30<dt><span class="section"><a href="cc/implementations__fcontext_t__ucontext_t_and_winfiber.html">Implementations:
31      fcontext_t, ucontext_t and WinFiber</a></span></dt>
32<dt><span class="section"><a href="cc/class__continuation_.html">Class <code class="computeroutput"><span class="identifier">continuation</span></code></a></span></dt>
33</dl></div>
34<div class="note"><table border="0" summary="Note">
35<tr>
36<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../doc/src/images/note.png"></td>
37<th align="left">Note</th>
38</tr>
39<tr><td align="left" valign="top"><p>
40        <span class="emphasis"><em>call/cc</em></span> is the reference implementation of C++ proposal
41        <a href="http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2017/p0534r3.pdf" target="_top">P0534R3:
42        call/cc (call-with-current-continuation): A low-level API for stackful context
43        switching</a>.
44      </p></td></tr>
45</table></div>
46<p>
47      <span class="emphasis"><em>call/cc</em></span> (call with current continuation) is a universal
48      control operator (well-known from the programming language Scheme) that captures
49      the current continuation as a first-class object and pass it as an argument
50      to another continuation.
51    </p>
52<p>
53      A continuation (abstract concept of functional programming languages) represents
54      the state of the control flow of a program at a given point in time. Continuations
55      can be suspended and resumed later in order to change the control flow of a
56      program.
57    </p>
58<p>
59      Modern micro-processors are registers machines; the content of processor registers
60      represent a continuation of the executed program at a given point in time.
61      Operating systems simulate parallel execution of programs on a single processor
62      by switching between programs (context switch) by preserving and restoring
63      the continuation, e.g. the content of all registers.
64    </p>
65<h4>
66<a name="context.cc.h0"></a>
67      <span class="phrase"><a name="context.cc._link_linkend__cc___emphasis_callcc____emphasis___link_"></a></span><a class="link" href="cc.html#context.cc._link_linkend__cc___emphasis_callcc____emphasis___link_"><span class="emphasis"><em>callcc()</em></span></a>
68    </h4>
69<p>
70      <a class="link" href="cc.html#cc"><span class="emphasis"><em>callcc()</em></span></a> is the C++ equivalent
71      to Scheme's <span class="emphasis"><em>call/cc</em></span> operator. It captures the current
72      continuation (the rest of the computation; code after <a class="link" href="cc.html#cc"><span class="emphasis"><em>callcc()</em></span></a>)
73      and triggers a context switch. The context switch is achieved by preserving
74      certain registers (including instruction and stack pointer), defined by the
75      calling convention of the ABI, of the current continuation and restoring those
76      registers of the resumed continuation. The control flow of the resumed continuation
77      continues. The current continuation is suspended and passed as argument to
78      the resumed continuation.
79    </p>
80<p>
81      <a class="link" href="cc.html#cc"><span class="emphasis"><em>callcc()</em></span></a> expects a <span class="emphasis"><em>context-function</em></span>
82      with signature <code class="computeroutput"><span class="char">'continuation(continuation &amp;&amp;
83      c)'</span></code>. The parameter <code class="computeroutput"><span class="identifier">c</span></code>
84      represents the current continuation from which this continuation was resumed
85      (e.g. that has called <a class="link" href="cc.html#cc"><span class="emphasis"><em>callcc()</em></span></a>).
86    </p>
87<p>
88      On return the <span class="emphasis"><em>context-function</em></span> of the current continuation
89      has to specify an <a class="link" href="cc.html#cc"><span class="emphasis"><em>continuation</em></span></a>
90      to which the execution control is transferred after termination of the current
91      continuation.
92    </p>
93<p>
94      If an instance with valid state goes out of scope and the <span class="emphasis"><em>context-function</em></span>
95      has not yet returned, the stack is traversed in order to access the control
96      structure (address stored at the first stack frame) and continuation's stack
97      is deallocated via the <span class="emphasis"><em>StackAllocator</em></span>.
98    </p>
99<div class="note"><table border="0" summary="Note">
100<tr>
101<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../doc/src/images/note.png"></td>
102<th align="left">Note</th>
103</tr>
104<tr><td align="left" valign="top"><p>
105        <a class="link" href="stack/segmented.html#segmented"><span class="emphasis"><em>Segmented stacks</em></span></a> are
106        supported by <a class="link" href="cc.html#cc"><span class="emphasis"><em>callcc()</em></span></a> using
107        <a class="link" href="ff/implementations__fcontext_t__ucontext_t_and_winfiber.html#implementation"><span class="emphasis"><em>ucontext_t</em></span></a>.
108      </p></td></tr>
109</table></div>
110<h4>
111<a name="context.cc.h1"></a>
112      <span class="phrase"><a name="context.cc._link_linkend__cc___emphasis_continuation__emphasis___link_"></a></span><a class="link" href="cc.html#context.cc._link_linkend__cc___emphasis_continuation__emphasis___link_"><span class="emphasis"><em>continuation</em></span></a>
113    </h4>
114<p>
115      <a class="link" href="cc.html#cc"><span class="emphasis"><em>continuation</em></span></a> represents a continuation;
116      it contains the content of preserved registers and manages the associated stack
117      (allocation/deallocation). <a class="link" href="cc.html#cc"><span class="emphasis"><em>continuation</em></span></a>
118      is a one-shot continuation - it can be used only once, after calling <span class="emphasis"><em>continuation::resume()</em></span>
119      or <span class="emphasis"><em>continuation::resume_with()</em></span> it is invalidated.
120    </p>
121<p>
122      <a class="link" href="cc.html#cc"><span class="emphasis"><em>continuation</em></span></a> is only move-constructible
123      and move-assignable.
124    </p>
125<p>
126      As a first-class object <a class="link" href="cc.html#cc"><span class="emphasis"><em>continuation</em></span></a>
127      can be applied to and returned from a function, assigned to a variable or stored
128      in a container.
129    </p>
130<p>
131      A continuation is continued by calling <code class="computeroutput"><span class="identifier">resume</span><span class="special">()</span></code>/<code class="computeroutput"><span class="identifier">resume_with</span><span class="special">()</span></code>.
132    </p>
133<h4>
134<a name="context.cc.h2"></a>
135      <span class="phrase"><a name="context.cc.usage"></a></span><a class="link" href="cc.html#context.cc.usage">Usage</a>
136    </h4>
137<pre class="programlisting"><span class="keyword">namespace</span> <span class="identifier">ctx</span><span class="special">=</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">context</span><span class="special">;</span>
138<span class="keyword">int</span> <span class="identifier">a</span><span class="special">;</span>
139<span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="identifier">source</span><span class="special">=</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">callcc</span><span class="special">(</span>
140    <span class="special">[&amp;</span><span class="identifier">a</span><span class="special">](</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="special">&amp;&amp;</span> <span class="identifier">sink</span><span class="special">){</span>
141        <span class="identifier">a</span><span class="special">=</span><span class="number">0</span><span class="special">;</span>
142        <span class="keyword">int</span> <span class="identifier">b</span><span class="special">=</span><span class="number">1</span><span class="special">;</span>
143        <span class="keyword">for</span><span class="special">(;;){</span>
144            <span class="identifier">sink</span><span class="special">=</span><span class="identifier">sink</span><span class="special">.</span><span class="identifier">resume</span><span class="special">();</span>
145            <span class="keyword">int</span> <span class="identifier">next</span><span class="special">=</span><span class="identifier">a</span><span class="special">+</span><span class="identifier">b</span><span class="special">;</span>
146            <span class="identifier">a</span><span class="special">=</span><span class="identifier">b</span><span class="special">;</span>
147            <span class="identifier">b</span><span class="special">=</span><span class="identifier">next</span><span class="special">;</span>
148        <span class="special">}</span>
149        <span class="keyword">return</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">move</span><span class="special">(</span><span class="identifier">sink</span><span class="special">);</span>
150    <span class="special">});</span>
151<span class="keyword">for</span> <span class="special">(</span><span class="keyword">int</span> <span class="identifier">j</span><span class="special">=</span><span class="number">0</span><span class="special">;</span><span class="identifier">j</span><span class="special">&lt;</span><span class="number">10</span><span class="special">;++</span><span class="identifier">j</span><span class="special">)</span> <span class="special">{</span>
152    <span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="identifier">a</span> <span class="special">&lt;&lt;</span> <span class="string">" "</span><span class="special">;</span>
153    <span class="identifier">source</span><span class="special">=</span><span class="identifier">source</span><span class="special">.</span><span class="identifier">resume</span><span class="special">();</span>
154<span class="special">}</span>
155
156<span class="identifier">output</span><span class="special">:</span>
157    <span class="number">0</span> <span class="number">1</span> <span class="number">1</span> <span class="number">2</span> <span class="number">3</span> <span class="number">5</span> <span class="number">8</span> <span class="number">13</span> <span class="number">21</span> <span class="number">34</span>
158</pre>
159<p>
160      This simple example demonstrates the basic usage of <span class="emphasis"><em>call/cc</em></span>
161      as a <span class="emphasis"><em>generator</em></span>. The continuation <code class="computeroutput"><span class="identifier">sink</span></code>
162      represents the <span class="emphasis"><em>main</em></span>-continuation (function <code class="computeroutput"><span class="identifier">main</span><span class="special">()</span></code>).
163      <code class="computeroutput"><span class="identifier">sink</span></code> is captured (current-continuation)
164      by invoking <a class="link" href="cc.html#cc"><span class="emphasis"><em>callcc()</em></span></a> and passed
165      as parameter to the lambda.
166    </p>
167<p>
168      Because the state is invalidated (one-shot continuation) by each call of <span class="emphasis"><em>continuation::resume()</em></span>,
169      the new state of the <a class="link" href="cc.html#cc"><span class="emphasis"><em>continuation</em></span></a>,
170      returned by <span class="emphasis"><em>continuation::resume()</em></span>, needs to be assigned
171      to <code class="computeroutput"><span class="identifier">sink</span></code> after each call.
172    </p>
173<p>
174      The lambda that calculates the Fibonacci numbers is executed inside the continuation
175      represented by <code class="computeroutput"><span class="identifier">source</span></code>. Calculated
176      Fibonacci numbers are transferred between the two continuations via variable
177      <code class="computeroutput"><span class="identifier">a</span></code> (lambda capture reference).
178    </p>
179<p>
180      The locale variables <code class="computeroutput"><span class="identifier">b</span></code> and
181      <code class="computeroutput"> <span class="identifier">next</span></code> remain their values during
182      each context switch. This is possible due <code class="computeroutput"><span class="identifier">source</span></code>
183      has its own stack and the stack is exchanged by each context switch.
184    </p>
185<h4>
186<a name="context.cc.h3"></a>
187      <span class="phrase"><a name="context.cc.parameter_passing"></a></span><a class="link" href="cc.html#context.cc.parameter_passing">Parameter
188      passing</a>
189    </h4>
190<p>
191      Data can be transferred between two continuations via global pointers, calling
192      wrappers (like <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">bind</span></code>) or lambda captures.
193    </p>
194<pre class="programlisting"><span class="keyword">namespace</span> <span class="identifier">ctx</span><span class="special">=</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">context</span><span class="special">;</span>
195<span class="keyword">int</span> <span class="identifier">i</span><span class="special">=</span><span class="number">1</span><span class="special">;</span>
196<span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="identifier">c1</span><span class="special">=</span><span class="identifier">callcc</span><span class="special">([&amp;</span><span class="identifier">i</span><span class="special">](</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="special">&amp;&amp;</span> <span class="identifier">c2</span><span class="special">){</span>
197            <span class="identifier">std</span><span class="special">::</span><span class="identifier">printf</span><span class="special">(</span><span class="string">"inside c1,i==%d\n"</span><span class="special">,</span><span class="identifier">i</span><span class="special">);</span>
198            <span class="identifier">i</span><span class="special">+=</span><span class="number">1</span><span class="special">;</span>
199            <span class="keyword">return</span> <span class="identifier">c2</span><span class="special">.</span><span class="identifier">resume</span><span class="special">();</span>
200        <span class="special">});</span>
201<span class="identifier">std</span><span class="special">::</span><span class="identifier">printf</span><span class="special">(</span><span class="string">"i==%d\n"</span><span class="special">,</span><span class="identifier">i</span><span class="special">);</span>
202
203<span class="identifier">output</span><span class="special">:</span>
204    <span class="identifier">inside</span> <span class="identifier">c1</span><span class="special">,</span><span class="identifier">i</span><span class="special">==</span><span class="number">1</span>
205    <span class="identifier">i</span><span class="special">==</span><span class="number">2</span>
206</pre>
207<p>
208      <code class="computeroutput"><span class="identifier">callcc</span><span class="special">(&lt;</span><span class="identifier">lambda</span><span class="special">&gt;)</span></code>
209      enters the lambda in continuation represented by <code class="computeroutput"><span class="identifier">c1</span></code>
210      with lambda capture reference <code class="computeroutput"><span class="identifier">i</span><span class="special">=</span><span class="number">1</span></code>. The expression
211      <code class="computeroutput"><span class="identifier">c2</span><span class="special">.</span><span class="identifier">resume</span><span class="special">()</span></code>
212      resumes the continuation <code class="computeroutput"><span class="identifier">c2</span></code>.
213      On return of <code class="computeroutput"><span class="identifier">callcc</span><span class="special">(&lt;</span><span class="identifier">lambda</span><span class="special">&gt;)</span></code>,
214      the variable <code class="computeroutput"><span class="identifier">i</span></code> has the value
215      of <code class="computeroutput"><span class="identifier">i</span><span class="special">+</span><span class="number">1</span></code>.
216    </p>
217<h4>
218<a name="context.cc.h4"></a>
219      <span class="phrase"><a name="context.cc.exception_handling"></a></span><a class="link" href="cc.html#context.cc.exception_handling">Exception
220      handling</a>
221    </h4>
222<p>
223      If the function executed inside a <span class="emphasis"><em>context-function</em></span> emits
224      an exception, the application is terminated by calling <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">terminate</span><span class="special">()</span></code>. <code class="computeroutput"><span class="identifier">std</span><span class="special">::</span><span class="identifier">exception_ptr</span></code>
225      can be used to transfer exceptions between different continuations.
226    </p>
227<div class="important"><table border="0" summary="Important">
228<tr>
229<td rowspan="2" align="center" valign="top" width="25"><img alt="[Important]" src="../../../../../doc/src/images/important.png"></td>
230<th align="left">Important</th>
231</tr>
232<tr><td align="left" valign="top"><p>
233        Do not jump from inside a catch block and then re-throw the exception in
234        another continuation.
235      </p></td></tr>
236</table></div>
237<a name="cc_ontop"></a><h4>
238<a name="context.cc.h5"></a>
239      <span class="phrase"><a name="context.cc.executing_function_on_top_of_a_continuation"></a></span><a class="link" href="cc.html#context.cc.executing_function_on_top_of_a_continuation">Executing
240      function on top of a continuation</a>
241    </h4>
242<p>
243      Sometimes it is useful to execute a new function on top of a resumed continuation.
244      For this purpose <span class="emphasis"><em>continuation::resume_with()</em></span> has to be
245      used. The function passed as argument must accept a rvalue reference to <a class="link" href="cc.html#cc"><span class="emphasis"><em>continuation</em></span></a> and return <code class="computeroutput"><span class="keyword">void</span></code>.
246    </p>
247<pre class="programlisting"><span class="keyword">namespace</span> <span class="identifier">ctx</span><span class="special">=</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">context</span><span class="special">;</span>
248<span class="keyword">int</span> <span class="identifier">data</span><span class="special">=</span><span class="number">0</span><span class="special">;</span>
249<span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="identifier">c</span><span class="special">=</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">callcc</span><span class="special">([&amp;</span><span class="identifier">data</span><span class="special">](</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="special">&amp;&amp;</span> <span class="identifier">c</span><span class="special">)</span> <span class="special">{</span>
250                    <span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"f1: entered first time: "</span> <span class="special">&lt;&lt;</span> <span class="identifier">data</span> <span class="special">&lt;&lt;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">endl</span><span class="special">;</span>
251                    <span class="identifier">data</span><span class="special">+=</span><span class="number">1</span><span class="special">;</span>
252                    <span class="identifier">c</span><span class="special">=</span><span class="identifier">c</span><span class="special">.</span><span class="identifier">resume</span><span class="special">();</span>
253                    <span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"f1: entered second time: "</span> <span class="special">&lt;&lt;</span> <span class="identifier">data</span> <span class="special">&lt;&lt;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">endl</span><span class="special">;</span>
254                    <span class="identifier">data</span><span class="special">+=</span><span class="number">1</span><span class="special">;</span>
255                    <span class="identifier">c</span><span class="special">=</span><span class="identifier">c</span><span class="special">.</span><span class="identifier">resume</span><span class="special">();</span>
256                    <span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"f1: entered third time: "</span> <span class="special">&lt;&lt;</span> <span class="identifier">data</span> <span class="special">&lt;&lt;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">endl</span><span class="special">;</span>
257                    <span class="keyword">return</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">move</span><span class="special">(</span><span class="identifier">c</span><span class="special">);</span>
258                <span class="special">});</span>
259<span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"f1: returned first time: "</span> <span class="special">&lt;&lt;</span> <span class="identifier">data</span> <span class="special">&lt;&lt;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">endl</span><span class="special">;</span>
260<span class="identifier">data</span><span class="special">+=</span><span class="number">1</span><span class="special">;</span>
261<span class="identifier">c</span><span class="special">=</span><span class="identifier">c</span><span class="special">.</span><span class="identifier">resume</span><span class="special">();</span>
262<span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"f1: returned second time: "</span> <span class="special">&lt;&lt;</span> <span class="identifier">data</span> <span class="special">&lt;&lt;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">endl</span><span class="special">;</span>
263<span class="identifier">data</span><span class="special">+=</span><span class="number">1</span><span class="special">;</span>
264<span class="identifier">c</span><span class="special">=</span><span class="identifier">c</span><span class="special">.</span><span class="identifier">resume_with</span><span class="special">([&amp;</span><span class="identifier">data</span><span class="special">](</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="special">&amp;&amp;</span> <span class="identifier">c</span><span class="special">){</span>
265                    <span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"f2: entered: "</span> <span class="special">&lt;&lt;</span> <span class="identifier">data</span> <span class="special">&lt;&lt;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">endl</span><span class="special">;</span>
266                    <span class="identifier">data</span><span class="special">=-</span><span class="number">1</span><span class="special">;</span>
267                    <span class="keyword">return</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">move</span><span class="special">(</span> <span class="identifier">c</span><span class="special">);</span>
268                <span class="special">});</span>
269<span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"f1: returned third time"</span> <span class="special">&lt;&lt;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">endl</span><span class="special">;</span>
270
271<span class="identifier">output</span><span class="special">:</span>
272    <span class="identifier">f1</span><span class="special">:</span> <span class="identifier">entered</span> <span class="identifier">first</span> <span class="identifier">time</span><span class="special">:</span> <span class="number">0</span>
273    <span class="identifier">f1</span><span class="special">:</span> <span class="identifier">returned</span> <span class="identifier">first</span> <span class="identifier">time</span><span class="special">:</span> <span class="number">1</span>
274    <span class="identifier">f1</span><span class="special">:</span> <span class="identifier">entered</span> <span class="identifier">second</span> <span class="identifier">time</span><span class="special">:</span> <span class="number">2</span>
275    <span class="identifier">f1</span><span class="special">:</span> <span class="identifier">returned</span> <span class="identifier">second</span> <span class="identifier">time</span><span class="special">:</span> <span class="number">3</span>
276    <span class="identifier">f2</span><span class="special">:</span> <span class="identifier">entered</span><span class="special">:</span> <span class="number">4</span>
277    <span class="identifier">f1</span><span class="special">:</span> <span class="identifier">entered</span> <span class="identifier">third</span> <span class="identifier">time</span><span class="special">:</span> <span class="special">-</span><span class="number">1</span>
278    <span class="identifier">f1</span><span class="special">:</span> <span class="identifier">returned</span> <span class="identifier">third</span> <span class="identifier">time</span>
279</pre>
280<p>
281      The expression <code class="computeroutput"><span class="identifier">c</span><span class="special">.</span><span class="identifier">resume_with</span><span class="special">(...)</span></code>
282      executes a lambda on top of continuation <code class="computeroutput"><span class="identifier">c</span></code>,
283      e.g. an additional stack frame is allocated on top of the stack. This lambda
284      assigns <code class="computeroutput"><span class="special">-</span><span class="number">1</span></code>
285      to <code class="computeroutput"><span class="identifier">data</span></code> and returns to the
286      second invocation of <code class="computeroutput"><span class="identifier">c</span><span class="special">.</span><span class="identifier">resume</span><span class="special">()</span></code>.
287    </p>
288<p>
289      Another option is to execute a function on top of the continuation that throws
290      an exception.
291    </p>
292<pre class="programlisting"><span class="keyword">namespace</span> <span class="identifier">ctx</span><span class="special">=</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">context</span><span class="special">;</span>
293<span class="keyword">struct</span> <span class="identifier">my_exception</span> <span class="special">:</span> <span class="keyword">public</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">runtime_error</span> <span class="special">{</span>
294    <span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span>    <span class="identifier">c</span><span class="special">;</span>
295    <span class="identifier">my_exception</span><span class="special">(</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="special">&amp;&amp;</span> <span class="identifier">c_</span><span class="special">,</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="keyword">const</span><span class="special">&amp;</span> <span class="identifier">what</span><span class="special">)</span> <span class="special">:</span>
296        <span class="identifier">std</span><span class="special">::</span><span class="identifier">runtime_error</span><span class="special">{</span> <span class="identifier">what</span> <span class="special">},</span>
297        <span class="identifier">c</span><span class="special">{</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">move</span><span class="special">(</span> <span class="identifier">c_</span><span class="special">)</span> <span class="special">}</span> <span class="special">{</span>
298    <span class="special">}</span>
299<span class="special">};</span>
300
301<span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="identifier">c</span><span class="special">=</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">callcc</span><span class="special">([](</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="special">&amp;&amp;</span> <span class="identifier">c</span><span class="special">)</span> <span class="special">{</span>
302    <span class="keyword">for</span> <span class="special">(;;)</span> <span class="special">{</span>
303        <span class="keyword">try</span> <span class="special">{</span>
304            <span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"entered"</span> <span class="special">&lt;&lt;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">endl</span><span class="special">;</span>
305            <span class="identifier">c</span><span class="special">=</span><span class="identifier">c</span><span class="special">.</span><span class="identifier">resume</span><span class="special">();</span>
306        <span class="special">}</span> <span class="keyword">catch</span> <span class="special">(</span><span class="identifier">my_exception</span> <span class="special">&amp;</span> <span class="identifier">ex</span><span class="special">)</span> <span class="special">{</span>
307            <span class="identifier">std</span><span class="special">::</span><span class="identifier">cerr</span> <span class="special">&lt;&lt;</span> <span class="string">"my_exception: "</span> <span class="special">&lt;&lt;</span> <span class="identifier">ex</span><span class="special">.</span><span class="identifier">what</span><span class="special">()</span> <span class="special">&lt;&lt;</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">endl</span><span class="special">;</span>
308            <span class="keyword">return</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">move</span><span class="special">(</span><span class="identifier">ex</span><span class="special">.</span><span class="identifier">c</span><span class="special">);</span>
309        <span class="special">}</span>
310    <span class="special">}</span>
311    <span class="keyword">return</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">move</span><span class="special">(</span><span class="identifier">c</span><span class="special">);</span>
312<span class="special">});</span>
313<span class="identifier">c</span> <span class="special">=</span> <span class="identifier">c</span><span class="special">.</span><span class="identifier">resume_with</span><span class="special">(</span>
314       <span class="special">[](</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="special">&amp;&amp;</span> <span class="identifier">c</span><span class="special">){</span>
315           <span class="keyword">throw</span> <span class="identifier">my_exception</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">move</span><span class="special">(</span><span class="identifier">c</span><span class="special">),</span><span class="string">"abc"</span><span class="special">);</span>
316           <span class="keyword">return</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">move</span><span class="special">(</span> <span class="identifier">c</span><span class="special">);</span>
317       <span class="special">});</span>
318
319<span class="identifier">output</span><span class="special">:</span>
320    <span class="identifier">entered</span>
321    <span class="identifier">my_exception</span><span class="special">:</span> <span class="identifier">abc</span>
322</pre>
323<p>
324      In this exception <code class="computeroutput"><span class="identifier">my_exception</span></code>
325      is throw from a function invoked on-top of continuation <code class="computeroutput"><span class="identifier">c</span></code>
326      and catched inside the <code class="computeroutput"><span class="keyword">for</span></code>-loop.
327    </p>
328<h4>
329<a name="context.cc.h6"></a>
330      <span class="phrase"><a name="context.cc.stack_unwinding"></a></span><a class="link" href="cc.html#context.cc.stack_unwinding">Stack
331      unwinding</a>
332    </h4>
333<p>
334      On construction of <a class="link" href="cc.html#cc"><span class="emphasis"><em>continuation</em></span></a>
335      a stack is allocated. If the <span class="emphasis"><em>context-function</em></span> returns
336      the stack will be destructed. If the <span class="emphasis"><em>context-function</em></span>
337      has not yet returned and the destructor of an valid <a class="link" href="cc.html#cc"><span class="emphasis"><em>continuation</em></span></a>
338      instance (e.g. <span class="emphasis"><em>continuation::operator bool()</em></span> returns
339      <code class="computeroutput"><span class="keyword">true</span></code>) is called, the stack will
340      be destructed too.
341    </p>
342<div class="important"><table border="0" summary="Important">
343<tr>
344<td rowspan="2" align="center" valign="top" width="25"><img alt="[Important]" src="../../../../../doc/src/images/important.png"></td>
345<th align="left">Important</th>
346</tr>
347<tr><td align="left" valign="top"><p>
348        Code executed by <span class="emphasis"><em>context-function</em></span> must not prevent the
349        propagation ofs the <span class="emphasis"><em>detail::forced_unwind</em></span> exception.
350        Absorbing that exception will cause stack unwinding to fail. Thus, any code
351        that catches all exceptions must re-throw any pending <span class="emphasis"><em>detail::forced_unwind</em></span>
352        exception.
353      </p></td></tr>
354</table></div>
355<a name="cc_prealloc"></a><h4>
356<a name="context.cc.h7"></a>
357      <span class="phrase"><a name="context.cc.allocating_control_structures_on_top_of_stack"></a></span><a class="link" href="cc.html#context.cc.allocating_control_structures_on_top_of_stack">Allocating
358      control structures on top of stack</a>
359    </h4>
360<p>
361      Allocating control structures on top of the stack requires to allocated the
362      <span class="emphasis"><em>stack_context</em></span> and create the control structure with placement
363      new before <a class="link" href="cc.html#cc"><span class="emphasis"><em>continuation</em></span></a> is created.
364    </p>
365<div class="note"><table border="0" summary="Note">
366<tr>
367<td rowspan="2" align="center" valign="top" width="25"><img alt="[Note]" src="../../../../../doc/src/images/note.png"></td>
368<th align="left">Note</th>
369</tr>
370<tr><td align="left" valign="top"><p>
371        The user is responsible for destructing the control structure at the top
372        of the stack.
373      </p></td></tr>
374</table></div>
375<pre class="programlisting"><span class="keyword">namespace</span> <span class="identifier">ctx</span><span class="special">=</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">context</span><span class="special">;</span>
376<span class="comment">// stack-allocator used for (de-)allocating stack</span>
377<span class="identifier">fixedsize_stack</span> <span class="identifier">salloc</span><span class="special">(</span><span class="number">4048</span><span class="special">);</span>
378<span class="comment">// allocate stack space</span>
379<span class="identifier">stack_context</span> <span class="identifier">sctx</span><span class="special">(</span><span class="identifier">salloc</span><span class="special">.</span><span class="identifier">allocate</span><span class="special">());</span>
380<span class="comment">// reserve space for control structure on top of the stack</span>
381<span class="keyword">void</span> <span class="special">*</span> <span class="identifier">sp</span><span class="special">=</span><span class="keyword">static_cast</span><span class="special">&lt;</span><span class="keyword">char</span><span class="special">*&gt;(</span><span class="identifier">sctx</span><span class="special">.</span><span class="identifier">sp</span><span class="special">)-</span><span class="keyword">sizeof</span><span class="special">(</span><span class="identifier">my_control_structure</span><span class="special">);</span>
382<span class="identifier">std</span><span class="special">::</span><span class="identifier">size_t</span> <span class="identifier">size</span><span class="special">=</span><span class="identifier">sctx</span><span class="special">.</span><span class="identifier">size</span><span class="special">-</span><span class="keyword">sizeof</span><span class="special">(</span><span class="identifier">my_control_structure</span><span class="special">);</span>
383<span class="comment">// placement new creates control structure on reserved space</span>
384<span class="identifier">my_control_structure</span> <span class="special">*</span> <span class="identifier">cs</span><span class="special">=</span><span class="keyword">new</span><span class="special">(</span><span class="identifier">sp</span><span class="special">)</span><span class="identifier">my_control_structure</span><span class="special">(</span><span class="identifier">sp</span><span class="special">,</span><span class="identifier">size</span><span class="special">,</span><span class="identifier">sctx</span><span class="special">,</span><span class="identifier">salloc</span><span class="special">);</span>
385<span class="special">...</span>
386<span class="comment">// destructing the control structure</span>
387<span class="identifier">cs</span><span class="special">-&gt;~</span><span class="identifier">my_control_structure</span><span class="special">();</span>
388<span class="special">...</span>
389<span class="keyword">struct</span> <span class="identifier">my_control_structure</span>  <span class="special">{</span>
390    <span class="comment">// captured continuation</span>
391    <span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span>   <span class="identifier">c</span><span class="special">;</span>
392
393    <span class="keyword">template</span><span class="special">&lt;</span> <span class="keyword">typename</span> <span class="identifier">StackAllocator</span> <span class="special">&gt;</span>
394    <span class="identifier">my_control_structure</span><span class="special">(</span><span class="keyword">void</span> <span class="special">*</span> <span class="identifier">sp</span><span class="special">,</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">size_t</span> <span class="identifier">size</span><span class="special">,</span><span class="identifier">stack_context</span> <span class="identifier">sctx</span><span class="special">,</span><span class="identifier">StackAllocator</span> <span class="identifier">salloc</span><span class="special">)</span> <span class="special">:</span>
395        <span class="comment">// create captured continuation</span>
396        <span class="identifier">c</span><span class="special">{}</span> <span class="special">{</span>
397        <span class="identifier">c</span><span class="special">=</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">callcc</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">allocator_arg</span><span class="special">,</span><span class="identifier">preallocated</span><span class="special">(</span><span class="identifier">sp</span><span class="special">,</span><span class="identifier">size</span><span class="special">,</span><span class="identifier">sctx</span><span class="special">),</span><span class="identifier">salloc</span><span class="special">,</span><span class="identifier">entry_func</span><span class="special">);</span>
398    <span class="special">}</span>
399    <span class="special">...</span>
400<span class="special">};</span>
401</pre>
402<h4>
403<a name="context.cc.h8"></a>
404      <span class="phrase"><a name="context.cc.inverting_the_control_flow"></a></span><a class="link" href="cc.html#context.cc.inverting_the_control_flow">Inverting
405      the control flow</a>
406    </h4>
407<pre class="programlisting"><span class="keyword">namespace</span> <span class="identifier">ctx</span><span class="special">=</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">context</span><span class="special">;</span>
408<span class="comment">/*
409 * grammar:
410 *   P ---&gt; E '\0'
411 *   E ---&gt; T {('+'|'-') T}
412 *   T ---&gt; S {('*'|'/') S}
413 *   S ---&gt; digit | '(' E ')'
414 */</span>
415<span class="keyword">class</span> <span class="identifier">Parser</span><span class="special">{</span>
416   <span class="keyword">char</span> <span class="identifier">next</span><span class="special">;</span>
417   <span class="identifier">std</span><span class="special">::</span><span class="identifier">istream</span><span class="special">&amp;</span> <span class="identifier">is</span><span class="special">;</span>
418   <span class="identifier">std</span><span class="special">::</span><span class="identifier">function</span><span class="special">&lt;</span><span class="keyword">void</span><span class="special">(</span><span class="keyword">char</span><span class="special">)&gt;</span> <span class="identifier">cb</span><span class="special">;</span>
419
420   <span class="keyword">char</span> <span class="identifier">pull</span><span class="special">(){</span>
421        <span class="keyword">return</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">char_traits</span><span class="special">&lt;</span><span class="keyword">char</span><span class="special">&gt;::</span><span class="identifier">to_char_type</span><span class="special">(</span><span class="identifier">is</span><span class="special">.</span><span class="identifier">get</span><span class="special">());</span>
422   <span class="special">}</span>
423
424   <span class="keyword">void</span> <span class="identifier">scan</span><span class="special">(){</span>
425       <span class="keyword">do</span><span class="special">{</span>
426           <span class="identifier">next</span><span class="special">=</span><span class="identifier">pull</span><span class="special">();</span>
427       <span class="special">}</span>
428       <span class="keyword">while</span><span class="special">(</span><span class="identifier">isspace</span><span class="special">(</span><span class="identifier">next</span><span class="special">));</span>
429   <span class="special">}</span>
430
431<span class="keyword">public</span><span class="special">:</span>
432   <span class="identifier">Parser</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">istream</span><span class="special">&amp;</span> <span class="identifier">is_</span><span class="special">,</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">function</span><span class="special">&lt;</span><span class="keyword">void</span><span class="special">(</span><span class="keyword">char</span><span class="special">)&gt;</span> <span class="identifier">cb_</span><span class="special">)</span> <span class="special">:</span>
433      <span class="identifier">next</span><span class="special">(),</span> <span class="identifier">is</span><span class="special">(</span><span class="identifier">is_</span><span class="special">),</span> <span class="identifier">cb</span><span class="special">(</span><span class="identifier">cb_</span><span class="special">)</span>
434    <span class="special">{}</span>
435
436   <span class="keyword">void</span> <span class="identifier">run</span><span class="special">()</span> <span class="special">{</span>
437      <span class="identifier">scan</span><span class="special">();</span>
438      <span class="identifier">E</span><span class="special">();</span>
439   <span class="special">}</span>
440
441<span class="keyword">private</span><span class="special">:</span>
442   <span class="keyword">void</span> <span class="identifier">E</span><span class="special">(){</span>
443      <span class="identifier">T</span><span class="special">();</span>
444      <span class="keyword">while</span> <span class="special">(</span><span class="identifier">next</span><span class="special">==</span><span class="char">'+'</span><span class="special">||</span><span class="identifier">next</span><span class="special">==</span><span class="char">'-'</span><span class="special">){</span>
445         <span class="identifier">cb</span><span class="special">(</span><span class="identifier">next</span><span class="special">);</span>
446         <span class="identifier">scan</span><span class="special">();</span>
447         <span class="identifier">T</span><span class="special">();</span>
448      <span class="special">}</span>
449   <span class="special">}</span>
450
451   <span class="keyword">void</span> <span class="identifier">T</span><span class="special">(){</span>
452      <span class="identifier">S</span><span class="special">();</span>
453      <span class="keyword">while</span> <span class="special">(</span><span class="identifier">next</span><span class="special">==</span><span class="char">'*'</span><span class="special">||</span><span class="identifier">next</span><span class="special">==</span><span class="char">'/'</span><span class="special">){</span>
454         <span class="identifier">cb</span><span class="special">(</span><span class="identifier">next</span><span class="special">);</span>
455         <span class="identifier">scan</span><span class="special">();</span>
456         <span class="identifier">S</span><span class="special">();</span>
457      <span class="special">}</span>
458   <span class="special">}</span>
459
460   <span class="keyword">void</span> <span class="identifier">S</span><span class="special">(){</span>
461      <span class="keyword">if</span> <span class="special">(</span><span class="identifier">isdigit</span><span class="special">(</span><span class="identifier">next</span><span class="special">)){</span>
462         <span class="identifier">cb</span><span class="special">(</span><span class="identifier">next</span><span class="special">);</span>
463         <span class="identifier">scan</span><span class="special">();</span>
464      <span class="special">}</span>
465      <span class="keyword">else</span> <span class="keyword">if</span><span class="special">(</span><span class="identifier">next</span><span class="special">==</span><span class="char">'('</span><span class="special">){</span>
466         <span class="identifier">cb</span><span class="special">(</span><span class="identifier">next</span><span class="special">);</span>
467         <span class="identifier">scan</span><span class="special">();</span>
468         <span class="identifier">E</span><span class="special">();</span>
469         <span class="keyword">if</span> <span class="special">(</span><span class="identifier">next</span><span class="special">==</span><span class="char">')'</span><span class="special">){</span>
470             <span class="identifier">cb</span><span class="special">(</span><span class="identifier">next</span><span class="special">);</span>
471             <span class="identifier">scan</span><span class="special">();</span>
472         <span class="special">}</span><span class="keyword">else</span><span class="special">{</span>
473             <span class="keyword">throw</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">runtime_error</span><span class="special">(</span><span class="string">"parsing failed"</span><span class="special">);</span>
474         <span class="special">}</span>
475      <span class="special">}</span>
476      <span class="keyword">else</span><span class="special">{</span>
477         <span class="keyword">throw</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">runtime_error</span><span class="special">(</span><span class="string">"parsing failed"</span><span class="special">);</span>
478      <span class="special">}</span>
479   <span class="special">}</span>
480<span class="special">};</span>
481
482<span class="identifier">std</span><span class="special">::</span><span class="identifier">istringstream</span> <span class="identifier">is</span><span class="special">(</span><span class="string">"1+1"</span><span class="special">);</span>
483<span class="comment">// execute parser in new continuation</span>
484<span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="identifier">source</span><span class="special">;</span>
485<span class="comment">// user-code pulls parsed data from parser</span>
486<span class="comment">// invert control flow</span>
487<span class="keyword">char</span> <span class="identifier">c</span><span class="special">;</span>
488<span class="keyword">bool</span> <span class="identifier">done</span><span class="special">=</span><span class="keyword">false</span><span class="special">;</span>
489<span class="identifier">source</span><span class="special">=</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">callcc</span><span class="special">(</span>
490        <span class="special">[&amp;</span><span class="identifier">is</span><span class="special">,&amp;</span><span class="identifier">c</span><span class="special">,&amp;</span><span class="identifier">done</span><span class="special">](</span><span class="identifier">ctx</span><span class="special">::</span><span class="identifier">continuation</span> <span class="special">&amp;&amp;</span> <span class="identifier">sink</span><span class="special">){</span>
491        <span class="comment">// create parser with callback function</span>
492        <span class="identifier">Parser</span> <span class="identifier">p</span><span class="special">(</span><span class="identifier">is</span><span class="special">,</span>
493                 <span class="special">[&amp;</span><span class="identifier">sink</span><span class="special">,&amp;</span><span class="identifier">c</span><span class="special">](</span><span class="keyword">char</span> <span class="identifier">c_</span><span class="special">){</span>
494                    <span class="comment">// resume main continuation</span>
495                    <span class="identifier">c</span><span class="special">=</span><span class="identifier">c_</span><span class="special">;</span>
496                    <span class="identifier">sink</span><span class="special">=</span><span class="identifier">sink</span><span class="special">.</span><span class="identifier">resume</span><span class="special">();</span>
497                 <span class="special">});</span>
498            <span class="comment">// start recursive parsing</span>
499            <span class="identifier">p</span><span class="special">.</span><span class="identifier">run</span><span class="special">();</span>
500            <span class="comment">// signal termination</span>
501            <span class="identifier">done</span><span class="special">=</span><span class="keyword">true</span><span class="special">;</span>
502            <span class="comment">// resume main continuation</span>
503            <span class="keyword">return</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">move</span><span class="special">(</span><span class="identifier">sink</span><span class="special">);</span>
504        <span class="special">});</span>
505<span class="keyword">while</span><span class="special">(!</span><span class="identifier">done</span><span class="special">){</span>
506    <span class="identifier">printf</span><span class="special">(</span><span class="string">"Parsed: %c\n"</span><span class="special">,</span><span class="identifier">c</span><span class="special">);</span>
507    <span class="identifier">source</span><span class="special">=</span><span class="identifier">source</span><span class="special">.</span><span class="identifier">resume</span><span class="special">();</span>
508<span class="special">}</span>
509
510<span class="identifier">output</span><span class="special">:</span>
511    <span class="identifier">Parsed</span><span class="special">:</span> <span class="number">1</span>
512    <span class="identifier">Parsed</span><span class="special">:</span> <span class="special">+</span>
513    <span class="identifier">Parsed</span><span class="special">:</span> <span class="number">1</span>
514</pre>
515<p>
516      In this example a recursive descent parser uses a callback to emit a newly
517      passed symbol. Using <span class="emphasis"><em>call/cc</em></span> the control flow can be inverted,
518      e.g. the user-code pulls parsed symbols from the parser - instead to get pushed
519      from the parser (via callback).
520    </p>
521<p>
522      The data (character) is transferred between the two continuations.
523    </p>
524</div>
525<table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
526<td align="left"></td>
527<td align="right"><div class="copyright-footer">Copyright © 2014 Oliver Kowalke<p>
528        Distributed under the Boost Software License, Version 1.0. (See accompanying
529        file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
530      </p>
531</div></td>
532</tr></table>
533<hr>
534<div class="spirit-nav">
535<a accesskey="p" href="ff/class__fiber_.html"><img src="../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../index.html"><img src="../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../index.html"><img src="../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="cc/implementations__fcontext_t__ucontext_t_and_winfiber.html"><img src="../../../../../doc/src/images/next.png" alt="Next"></a>
536</div>
537</body>
538</html>
539