Lacking Natural Simplicity (Posts about modula)
https://tkurtbond.github.io/categories/modula.atom
2024-01-23T18:49:53Z
T. Kurt Bond
Nikola
Lisp-style trampolines in Common Lisp, C, Ada, Oberon-2, and Revised Oberon
https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/
2022-06-14T15:49:55-04:00
2022-06-14T15:49:55-04:00
T. Kurt Bond
<p><em>Last edited: 2024-01-21 11:32:05 EST</em></p>
<p>Are you familiar with <a class="reference external" href="https://en.wikipedia.org/wiki/Trampoline_(computing)#High-level_programming">lisp-style trampolines</a>? A trampoline is a
loop that iteratively invokes functions that return functions. The
previous link will lead you through <a class="reference external" href="https://en.wikipedia.org/wiki/Trampoline_(computing)#cite_note-Baker_1995-1">CONS Should Not CONS Its
Arguments, Part II: Cheney on the M.T.A.</a> (<a class="reference external" href="https://dl.acm.org/doi/10.1145/214448.214454">PDF version</a>; see p. 17
in the original publication, but that is the first page of the PDF
that link eventually leads to), which, while saying you should just go
ahead and convert to <a class="reference external" href="https://en.wikipedia.org/wiki/Continuation-passing_style">Continuation-passing style</a> form (CPS),
mentions in passing <a class="reference external" href="https://dl.acm.org/doi/10.1145/151333.151343">No assembly required: compiling standard ML to C</a>,
(see p. 168 in the original publication, which is the page 8 of the
PDF that link eventually leads to) which leads you to <a class="reference external" href="https://dspace.mit.edu/handle/1721.1/6913">RABBIT: A
Compiler for SCHEME</a>, where the concept is discussed under the name
the "SCHEME UUO handler" (see p. 23–24).</p>
<p>Why is this useful? It allows you to compile a language that requires
proper <a class="reference external" href="https://en.wikipedia.org/wiki/Tail_call">tail call</a> optimization to one that does not provide that.
For instance, if you wanted to compile Scheme, which requires proper
tail call optimization, to Common Lisp, which does not require proper
tail call optimization, you can't just translate Scheme functions
directly into Common Lisp functions, because tail calls allocate stack
space, and eventually the stack will run out of space.</p>
<p>Here's an example that will run forever in any standard confirming
Scheme, <a class="reference external" href="https://tkurtbond.github.io/trampolines/forever.scm">forever.scm</a>:</p>
<div class="code"><pre class="code scheme"><a id="rest_code_096fd17fa42d495aa75bbec7c3e45045-1" name="rest_code_096fd17fa42d495aa75bbec7c3e45045-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_096fd17fa42d495aa75bbec7c3e45045-1"></a><span class="c1">;;; Recurse forever, because with tail call optimization, the stack</span>
<a id="rest_code_096fd17fa42d495aa75bbec7c3e45045-2" name="rest_code_096fd17fa42d495aa75bbec7c3e45045-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_096fd17fa42d495aa75bbec7c3e45045-2"></a><span class="c1">;;; never runs out!</span>
<a id="rest_code_096fd17fa42d495aa75bbec7c3e45045-3" name="rest_code_096fd17fa42d495aa75bbec7c3e45045-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_096fd17fa42d495aa75bbec7c3e45045-3"></a><span class="p">(</span><span class="k">define</span><span class="w"> </span><span class="nv">i</span><span class="w"> </span><span class="mi">0</span><span class="p">)</span>
<a id="rest_code_096fd17fa42d495aa75bbec7c3e45045-4" name="rest_code_096fd17fa42d495aa75bbec7c3e45045-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_096fd17fa42d495aa75bbec7c3e45045-4"></a>
<a id="rest_code_096fd17fa42d495aa75bbec7c3e45045-5" name="rest_code_096fd17fa42d495aa75bbec7c3e45045-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_096fd17fa42d495aa75bbec7c3e45045-5"></a><span class="p">(</span><span class="k">define</span><span class="w"> </span><span class="p">(</span><span class="nf">f</span><span class="p">)</span>
<a id="rest_code_096fd17fa42d495aa75bbec7c3e45045-6" name="rest_code_096fd17fa42d495aa75bbec7c3e45045-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_096fd17fa42d495aa75bbec7c3e45045-6"></a><span class="w"> </span><span class="p">(</span><span class="k">set!</span><span class="w"> </span><span class="nv">i</span><span class="w"> </span><span class="p">(</span><span class="nb">+</span><span class="w"> </span><span class="mi">1</span><span class="w"> </span><span class="nv">i</span><span class="p">))</span>
<a id="rest_code_096fd17fa42d495aa75bbec7c3e45045-7" name="rest_code_096fd17fa42d495aa75bbec7c3e45045-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_096fd17fa42d495aa75bbec7c3e45045-7"></a><span class="w"> </span><span class="p">(</span><span class="nb">display</span><span class="w"> </span><span class="s">"call #"</span><span class="p">)</span><span class="w"> </span><span class="p">(</span><span class="nb">display</span><span class="w"> </span><span class="nv">i</span><span class="p">)</span><span class="w"> </span><span class="p">(</span><span class="nb">newline</span><span class="p">)</span>
<a id="rest_code_096fd17fa42d495aa75bbec7c3e45045-8" name="rest_code_096fd17fa42d495aa75bbec7c3e45045-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_096fd17fa42d495aa75bbec7c3e45045-8"></a><span class="w"> </span><span class="p">(</span><span class="nf">f</span><span class="p">))</span>
<a id="rest_code_096fd17fa42d495aa75bbec7c3e45045-9" name="rest_code_096fd17fa42d495aa75bbec7c3e45045-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_096fd17fa42d495aa75bbec7c3e45045-9"></a>
<a id="rest_code_096fd17fa42d495aa75bbec7c3e45045-10" name="rest_code_096fd17fa42d495aa75bbec7c3e45045-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_096fd17fa42d495aa75bbec7c3e45045-10"></a><span class="p">(</span><span class="nf">f</span><span class="p">)</span>
</pre></div>
<p>Here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/common-lisp/not_forever.lisp">not_forever.lisp</a>, the same thing in Common Lisp:</p>
<div class="code"><pre class="code common-lisp"><a id="rest_code_962263e95e644166a351d683c88357cc-1" name="rest_code_962263e95e644166a351d683c88357cc-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_962263e95e644166a351d683c88357cc-1"></a><span class="c1">;;; Recurse until the stack space runs out.</span>
<a id="rest_code_962263e95e644166a351d683c88357cc-2" name="rest_code_962263e95e644166a351d683c88357cc-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_962263e95e644166a351d683c88357cc-2"></a><span class="p">(</span><span class="nb">defparameter</span><span class="w"> </span><span class="nv">i</span><span class="w"> </span><span class="mi">0</span><span class="p">)</span>
<a id="rest_code_962263e95e644166a351d683c88357cc-3" name="rest_code_962263e95e644166a351d683c88357cc-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_962263e95e644166a351d683c88357cc-3"></a>
<a id="rest_code_962263e95e644166a351d683c88357cc-4" name="rest_code_962263e95e644166a351d683c88357cc-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_962263e95e644166a351d683c88357cc-4"></a><span class="p">(</span><span class="nb">defun</span><span class="w"> </span><span class="nv">f</span><span class="w"> </span><span class="p">()</span>
<a id="rest_code_962263e95e644166a351d683c88357cc-5" name="rest_code_962263e95e644166a351d683c88357cc-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_962263e95e644166a351d683c88357cc-5"></a><span class="w"> </span><span class="p">(</span><span class="nb">incf</span><span class="w"> </span><span class="nv">i</span><span class="p">)</span>
<a id="rest_code_962263e95e644166a351d683c88357cc-6" name="rest_code_962263e95e644166a351d683c88357cc-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_962263e95e644166a351d683c88357cc-6"></a><span class="w"> </span><span class="p">(</span><span class="nb">format</span><span class="w"> </span><span class="no">t</span><span class="w"> </span><span class="s">"call #~d~%"</span><span class="w"> </span><span class="nv">i</span><span class="p">)</span>
<a id="rest_code_962263e95e644166a351d683c88357cc-7" name="rest_code_962263e95e644166a351d683c88357cc-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_962263e95e644166a351d683c88357cc-7"></a><span class="w"> </span><span class="p">(</span><span class="nv">f</span><span class="p">))</span>
<a id="rest_code_962263e95e644166a351d683c88357cc-8" name="rest_code_962263e95e644166a351d683c88357cc-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_962263e95e644166a351d683c88357cc-8"></a>
<a id="rest_code_962263e95e644166a351d683c88357cc-9" name="rest_code_962263e95e644166a351d683c88357cc-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_962263e95e644166a351d683c88357cc-9"></a><span class="p">(</span><span class="nv">f</span><span class="p">)</span>
</pre></div>
<p>Now, some Common Lisp implementations don't do tail call
optimization, and some <strong>do</strong>. Some don't do tail call optimization
unless you compile the functions in question.</p>
<p>So, for instance, if I load that file into GNU CLISP 2.49.92, the
function executes about 4668 times and then <span class="app">CLISP</span> dies with the
error message:</p>
<pre class="literal-block">*** - Lisp stack overflow. RESET</pre>
<p>However if I compile that file in <span class="app">CLISP</span> with the Common Lisp function
<code class="docutils literal"><span class="pre">compile-file</span></code> and then load the resulting <span class="file">.fas</span> file into
<span class="app">CLISP</span>, it will run forever, because <span class="app">CLISP</span> does tail call
optimization when it compiles code.</p>
<p>Furthermore, if I load that file into <span class="app">SBCL</span> it will run forever,
because <span class="app">SBCL</span> does tail call optimization by default.</p>
<p><span class="app">ECL</span> is another Common Lisp system where if you load that file
into an interactive session it will die with stack overflow, but if
you compile that file into an executable it will run forever.</p>
<p>So, suppose you wanted to translate the Scheme code into Common Lisp,
for an implementation that does not do tail call optimization. You'd
use a trampoline to make sure the stack doesn't overflow.</p>
<p>Here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/common-lisp/trampoline.lisp">trampoline.lisp</a>, a trampoline in Common Lisp that runs
through three functions and then stops, for simplicity:</p>
<div class="code"><pre class="code common-lisp"><a id="rest_code_b220a22f72574442a4fae48b0b4d8932-1" name="rest_code_b220a22f72574442a4fae48b0b4d8932-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-1"></a><span class="c1">;;; Demonstrate lisp-style trampolines.</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-2" name="rest_code_b220a22f72574442a4fae48b0b4d8932-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-2"></a><span class="p">(</span><span class="nb">defun</span><span class="w"> </span><span class="nv">baz</span><span class="w"> </span><span class="p">()</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-3" name="rest_code_b220a22f72574442a4fae48b0b4d8932-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-3"></a><span class="w"> </span><span class="p">(</span><span class="nb">format</span><span class="w"> </span><span class="no">t</span><span class="w"> </span><span class="s">"baz~%"</span><span class="p">)</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-4" name="rest_code_b220a22f72574442a4fae48b0b4d8932-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-4"></a><span class="w"> </span><span class="no">nil</span><span class="p">)</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-5" name="rest_code_b220a22f72574442a4fae48b0b4d8932-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-5"></a>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-6" name="rest_code_b220a22f72574442a4fae48b0b4d8932-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-6"></a><span class="p">(</span><span class="nb">defun</span><span class="w"> </span><span class="nv">bar</span><span class="w"> </span><span class="p">()</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-7" name="rest_code_b220a22f72574442a4fae48b0b4d8932-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-7"></a><span class="w"> </span><span class="p">(</span><span class="nb">format</span><span class="w"> </span><span class="no">t</span><span class="w"> </span><span class="s">"bar~%"</span><span class="p">)</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-8" name="rest_code_b220a22f72574442a4fae48b0b4d8932-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-8"></a><span class="w"> </span><span class="nf">#'</span><span class="nv">baz</span><span class="p">)</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-9" name="rest_code_b220a22f72574442a4fae48b0b4d8932-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-9"></a>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-10" name="rest_code_b220a22f72574442a4fae48b0b4d8932-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-10"></a><span class="p">(</span><span class="nb">defun</span><span class="w"> </span><span class="nv">foo</span><span class="w"> </span><span class="p">()</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-11" name="rest_code_b220a22f72574442a4fae48b0b4d8932-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-11"></a><span class="w"> </span><span class="p">(</span><span class="nb">format</span><span class="w"> </span><span class="no">t</span><span class="w"> </span><span class="s">"foo~%"</span><span class="p">)</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-12" name="rest_code_b220a22f72574442a4fae48b0b4d8932-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-12"></a><span class="w"> </span><span class="nf">#'</span><span class="nv">bar</span><span class="p">)</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-13" name="rest_code_b220a22f72574442a4fae48b0b4d8932-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-13"></a>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-14" name="rest_code_b220a22f72574442a4fae48b0b4d8932-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-14"></a><span class="p">(</span><span class="k">let</span><span class="w"> </span><span class="p">((</span><span class="nv">f</span><span class="w"> </span><span class="nf">#'</span><span class="nv">foo</span><span class="p">))</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-15" name="rest_code_b220a22f72574442a4fae48b0b4d8932-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-15"></a><span class="w"> </span><span class="p">(</span><span class="nb">loop</span><span class="w"> </span><span class="nv">for</span><span class="w"> </span><span class="nv">i</span><span class="w"> </span><span class="nv">from</span><span class="w"> </span><span class="mi">1</span><span class="w"> </span><span class="nv">while</span><span class="w"> </span><span class="p">(</span><span class="nb">not</span><span class="w"> </span><span class="p">(</span><span class="nb">null</span><span class="w"> </span><span class="nv">f</span><span class="p">))</span>
<a id="rest_code_b220a22f72574442a4fae48b0b4d8932-16" name="rest_code_b220a22f72574442a4fae48b0b4d8932-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_b220a22f72574442a4fae48b0b4d8932-16"></a><span class="w"> </span><span class="nb">do</span><span class="w"> </span><span class="p">(</span><span class="nb">setf</span><span class="w"> </span><span class="nv">f</span><span class="w"> </span><span class="p">(</span><span class="nb">funcall</span><span class="w"> </span><span class="nv">f</span><span class="p">))))</span>
</pre></div>
<p>Here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/common-lisp/trampoline_forever.lisp">trampoline_forever.lisp</a>, a trampoline in Common Lisp that
runs forever:</p>
<div class="code"><pre class="code common-lisp"><a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-1" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-1"></a><span class="c1">;;; Recurse forever without running out of stack space.</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-2" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-2"></a><span class="p">(</span><span class="nb">defun</span><span class="w"> </span><span class="nv">baz</span><span class="w"> </span><span class="p">()</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-3" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-3"></a><span class="w"> </span><span class="p">(</span><span class="nb">format</span><span class="w"> </span><span class="no">t</span><span class="w"> </span><span class="s">"baz~%"</span><span class="p">)</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-4" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-4"></a><span class="w"> </span><span class="nf">#'</span><span class="nv">foo</span><span class="p">)</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-5" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-5"></a>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-6" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-6"></a><span class="p">(</span><span class="nb">defun</span><span class="w"> </span><span class="nv">bar</span><span class="w"> </span><span class="p">()</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-7" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-7"></a><span class="w"> </span><span class="p">(</span><span class="nb">format</span><span class="w"> </span><span class="no">t</span><span class="w"> </span><span class="s">"bar~%"</span><span class="p">)</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-8" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-8"></a><span class="w"> </span><span class="nf">#'</span><span class="nv">baz</span><span class="p">)</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-9" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-9"></a>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-10" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-10"></a><span class="p">(</span><span class="nb">defun</span><span class="w"> </span><span class="nv">foo</span><span class="w"> </span><span class="p">()</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-11" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-11"></a><span class="w"> </span><span class="p">(</span><span class="nb">format</span><span class="w"> </span><span class="no">t</span><span class="w"> </span><span class="s">"foo~%"</span><span class="p">)</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-12" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-12"></a><span class="w"> </span><span class="nf">#'</span><span class="nv">bar</span><span class="p">)</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-13" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-13"></a>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-14" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-14"></a><span class="p">(</span><span class="k">let</span><span class="w"> </span><span class="p">((</span><span class="nv">f</span><span class="w"> </span><span class="nf">#'</span><span class="nv">foo</span><span class="p">))</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-15" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-15"></a><span class="w"> </span><span class="p">(</span><span class="nb">loop</span><span class="w"> </span><span class="nv">for</span><span class="w"> </span><span class="nv">i</span><span class="w"> </span><span class="nv">from</span><span class="w"> </span><span class="mi">1</span><span class="w"> </span><span class="nv">while</span><span class="w"> </span><span class="p">(</span><span class="nb">not</span><span class="w"> </span><span class="p">(</span><span class="nb">null</span><span class="w"> </span><span class="nv">f</span><span class="p">))</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-16" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-16"></a><span class="w"> </span><span class="nb">do</span><span class="w"> </span><span class="p">(</span><span class="k">progn</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-17" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-17"></a><span class="w"> </span><span class="p">(</span><span class="nb">format</span><span class="w"> </span><span class="no">t</span><span class="w"> </span><span class="s">"trampoline call #~s~%"</span><span class="w"> </span><span class="nv">i</span><span class="p">)</span>
<a id="rest_code_6394f0b1277744f7b8bf6312fbedead8-18" name="rest_code_6394f0b1277744f7b8bf6312fbedead8-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_6394f0b1277744f7b8bf6312fbedead8-18"></a><span class="w"> </span><span class="p">(</span><span class="nb">setf</span><span class="w"> </span><span class="nv">f</span><span class="w"> </span><span class="p">(</span><span class="nb">funcall</span><span class="w"> </span><span class="nv">f</span><span class="p">)))))</span>
</pre></div>
<p>Of course, you can do the same things in C. First, here's
<a class="reference external" href="https://tkurtbond.github.io/trampolines/c/not_forever.c">not_forever.c</a>, a program in C that will (usually) die with a stack
overflow:</p>
<div class="code"><pre class="code c"><a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-1" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-1"></a><span class="cm">/* Recurse until stack space runs out.</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-2" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-2"></a><span class="cm"> Unless the compiler does tail-call optimization. */</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-3" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-3"></a><span class="cp">#include</span><span class="w"> </span><span class="cpf"><stdio.h></span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-4" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-4"></a>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-5" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-5"></a><span class="k">static</span><span class="w"> </span><span class="kt">int</span><span class="w"> </span><span class="n">i</span><span class="p">;</span><span class="w"> </span><span class="cm">/* Number of times f has been called. */</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-6" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-6"></a>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-7" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-7"></a><span class="kt">void</span><span class="w"> </span><span class="nf">f</span><span class="w"> </span><span class="p">(</span><span class="kt">void</span><span class="p">)</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-8" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-8"></a><span class="p">{</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-9" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-9"></a><span class="w"> </span><span class="n">i</span><span class="o">++</span><span class="p">;</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-10" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-10"></a><span class="w"> </span><span class="n">printf</span><span class="w"> </span><span class="p">(</span><span class="s">"call #%d</span><span class="se">\n</span><span class="s">"</span><span class="p">,</span><span class="w"> </span><span class="n">i</span><span class="p">);</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-11" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-11"></a><span class="w"> </span><span class="n">f</span><span class="w"> </span><span class="p">();</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-12" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-12"></a><span class="p">}</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-13" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-13"></a>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-14" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-14"></a><span class="kt">int</span><span class="w"> </span><span class="nf">main</span><span class="w"> </span><span class="p">(</span><span class="kt">int</span><span class="w"> </span><span class="n">argc</span><span class="p">,</span><span class="w"> </span><span class="kt">char</span><span class="w"> </span><span class="o">**</span><span class="n">argv</span><span class="p">)</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-15" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-15"></a><span class="p">{</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-16" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-16"></a><span class="w"> </span><span class="n">i</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="mi">0</span><span class="p">;</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-17" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-17"></a><span class="w"> </span><span class="n">f</span><span class="w"> </span><span class="p">();</span>
<a id="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-18" name="rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_080f8b4c6c4f44029ec4d2421cd28ed9-18"></a><span class="p">}</span>
</pre></div>
<p>I say usually, because tail call optimization is not required by the
standard, and many C compilers do not do it. For instance, <span class="app">gcc</span>
doesn't do tail call optimization <strong>unless</strong> you specify
<code class="docutils literal"><span class="pre">-foptimize-sibling-calls</span></code> or <code class="docutils literal"><span class="pre">-O2</span></code>, <code class="docutils literal"><span class="pre">-O3</span></code>, or <code class="docutils literal"><span class="pre">-Os</span></code>. If I
don't specify any of those options, on my system that program dies
with the error <code class="docutils literal">Segmentation fault: 11</code> after call #523932.</p>
<p>Here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/c/trampoline.c">trampoline.c</a>, the limited trampoline in C:</p>
<div class="code"><pre class="code c"><a id="rest_code_4f2ce7e85f98445f95272d632b30e606-1" name="rest_code_4f2ce7e85f98445f95272d632b30e606-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-1"></a><span class="cm">/* Demonstrate lisp-style trampolines. */</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-2" name="rest_code_4f2ce7e85f98445f95272d632b30e606-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-2"></a><span class="cp">#include</span><span class="w"> </span><span class="cpf"><stdio.h></span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-3" name="rest_code_4f2ce7e85f98445f95272d632b30e606-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-3"></a>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-4" name="rest_code_4f2ce7e85f98445f95272d632b30e606-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-4"></a><span class="k">typedef</span><span class="w"> </span><span class="kt">void</span><span class="o">*</span><span class="w"> </span><span class="p">(</span><span class="o">*</span><span class="n">trampoline</span><span class="p">)(</span><span class="kt">void</span><span class="p">);</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-5" name="rest_code_4f2ce7e85f98445f95272d632b30e606-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-5"></a>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-6" name="rest_code_4f2ce7e85f98445f95272d632b30e606-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-6"></a><span class="kt">void</span><span class="w"> </span><span class="o">*</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-7" name="rest_code_4f2ce7e85f98445f95272d632b30e606-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-7"></a><span class="nf">baz</span><span class="w"> </span><span class="p">(</span><span class="kt">void</span><span class="p">)</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-8" name="rest_code_4f2ce7e85f98445f95272d632b30e606-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-8"></a><span class="p">{</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-9" name="rest_code_4f2ce7e85f98445f95272d632b30e606-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-9"></a><span class="w"> </span><span class="n">printf</span><span class="w"> </span><span class="p">(</span><span class="s">"baz</span><span class="se">\n</span><span class="s">"</span><span class="p">);</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-10" name="rest_code_4f2ce7e85f98445f95272d632b30e606-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-10"></a><span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="nb">NULL</span><span class="p">;</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-11" name="rest_code_4f2ce7e85f98445f95272d632b30e606-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-11"></a><span class="p">}</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-12" name="rest_code_4f2ce7e85f98445f95272d632b30e606-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-12"></a>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-13" name="rest_code_4f2ce7e85f98445f95272d632b30e606-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-13"></a><span class="kt">void</span><span class="w"> </span><span class="o">*</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-14" name="rest_code_4f2ce7e85f98445f95272d632b30e606-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-14"></a><span class="nf">bar</span><span class="w"> </span><span class="p">(</span><span class="kt">void</span><span class="p">)</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-15" name="rest_code_4f2ce7e85f98445f95272d632b30e606-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-15"></a><span class="p">{</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-16" name="rest_code_4f2ce7e85f98445f95272d632b30e606-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-16"></a><span class="w"> </span><span class="n">printf</span><span class="w"> </span><span class="p">(</span><span class="s">"bar</span><span class="se">\n</span><span class="s">"</span><span class="p">);</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-17" name="rest_code_4f2ce7e85f98445f95272d632b30e606-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-17"></a><span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="n">baz</span><span class="p">;</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-18" name="rest_code_4f2ce7e85f98445f95272d632b30e606-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-18"></a><span class="p">}</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-19" name="rest_code_4f2ce7e85f98445f95272d632b30e606-19" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-19"></a>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-20" name="rest_code_4f2ce7e85f98445f95272d632b30e606-20" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-20"></a><span class="kt">void</span><span class="w"> </span><span class="o">*</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-21" name="rest_code_4f2ce7e85f98445f95272d632b30e606-21" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-21"></a><span class="nf">foo</span><span class="w"> </span><span class="p">(</span><span class="kt">void</span><span class="p">)</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-22" name="rest_code_4f2ce7e85f98445f95272d632b30e606-22" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-22"></a><span class="p">{</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-23" name="rest_code_4f2ce7e85f98445f95272d632b30e606-23" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-23"></a><span class="w"> </span><span class="n">printf</span><span class="w"> </span><span class="p">(</span><span class="s">"foo</span><span class="se">\n</span><span class="s">"</span><span class="p">);</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-24" name="rest_code_4f2ce7e85f98445f95272d632b30e606-24" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-24"></a><span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="n">bar</span><span class="p">;</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-25" name="rest_code_4f2ce7e85f98445f95272d632b30e606-25" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-25"></a><span class="p">}</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-26" name="rest_code_4f2ce7e85f98445f95272d632b30e606-26" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-26"></a>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-27" name="rest_code_4f2ce7e85f98445f95272d632b30e606-27" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-27"></a>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-28" name="rest_code_4f2ce7e85f98445f95272d632b30e606-28" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-28"></a><span class="kt">int</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-29" name="rest_code_4f2ce7e85f98445f95272d632b30e606-29" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-29"></a><span class="nf">main</span><span class="w"> </span><span class="p">(</span><span class="kt">int</span><span class="w"> </span><span class="n">argc</span><span class="p">,</span><span class="w"> </span><span class="kt">char</span><span class="w"> </span><span class="o">**</span><span class="n">argv</span><span class="p">)</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-30" name="rest_code_4f2ce7e85f98445f95272d632b30e606-30" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-30"></a><span class="p">{</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-31" name="rest_code_4f2ce7e85f98445f95272d632b30e606-31" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-31"></a><span class="w"> </span><span class="n">trampoline</span><span class="w"> </span><span class="n">t</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">foo</span><span class="p">;</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-32" name="rest_code_4f2ce7e85f98445f95272d632b30e606-32" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-32"></a><span class="w"> </span><span class="k">while</span><span class="w"> </span><span class="p">(</span><span class="n">t</span><span class="p">)</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-33" name="rest_code_4f2ce7e85f98445f95272d632b30e606-33" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-33"></a><span class="w"> </span><span class="n">t</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">t</span><span class="w"> </span><span class="p">();</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-34" name="rest_code_4f2ce7e85f98445f95272d632b30e606-34" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-34"></a><span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="mi">0</span><span class="p">;</span>
<a id="rest_code_4f2ce7e85f98445f95272d632b30e606-35" name="rest_code_4f2ce7e85f98445f95272d632b30e606-35" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_4f2ce7e85f98445f95272d632b30e606-35"></a><span class="p">}</span>
</pre></div>
<p>Notice this works by converting pointers to functions to pointers to void
— it doesn't even require any explicit casting!</p>
<p>And here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/c/trampoline_forever.c">trampoline_forever.c</a>, the trampoline that runs forever:</p>
<div class="code"><pre class="code c"><a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-1" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-1"></a><span class="cm">/* Recurse forever without running out of stack spacc. */</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-2" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-2"></a><span class="cp">#include</span><span class="w"> </span><span class="cpf"><stdio.h></span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-3" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-3"></a>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-4" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-4"></a><span class="k">typedef</span><span class="w"> </span><span class="kt">void</span><span class="o">*</span><span class="w"> </span><span class="p">(</span><span class="o">*</span><span class="n">trampoline</span><span class="p">)(</span><span class="kt">void</span><span class="p">);</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-5" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-5"></a>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-6" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-6"></a><span class="kt">void</span><span class="w"> </span><span class="o">*</span><span class="nf">foo</span><span class="w"> </span><span class="p">(</span><span class="kt">void</span><span class="p">);</span><span class="w"> </span><span class="cm">/* Forward declaration. */</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-7" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-7"></a>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-8" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-8"></a><span class="kt">void</span><span class="w"> </span><span class="o">*</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-9" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-9"></a><span class="nf">baz</span><span class="w"> </span><span class="p">(</span><span class="kt">void</span><span class="p">)</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-10" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-10"></a><span class="p">{</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-11" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-11"></a><span class="w"> </span><span class="n">printf</span><span class="w"> </span><span class="p">(</span><span class="s">"baz</span><span class="se">\n</span><span class="s">"</span><span class="p">);</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-12" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-12"></a><span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="n">foo</span><span class="p">;</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-13" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-13"></a><span class="p">}</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-14" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-14"></a>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-15" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-15"></a><span class="kt">void</span><span class="w"> </span><span class="o">*</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-16" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-16"></a><span class="nf">bar</span><span class="w"> </span><span class="p">(</span><span class="kt">void</span><span class="p">)</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-17" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-17"></a><span class="p">{</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-18" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-18"></a><span class="w"> </span><span class="n">printf</span><span class="w"> </span><span class="p">(</span><span class="s">"bar</span><span class="se">\n</span><span class="s">"</span><span class="p">);</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-19" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-19" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-19"></a><span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="n">baz</span><span class="p">;</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-20" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-20" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-20"></a><span class="p">}</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-21" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-21" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-21"></a>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-22" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-22" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-22"></a><span class="kt">void</span><span class="w"> </span><span class="o">*</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-23" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-23" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-23"></a><span class="nf">foo</span><span class="w"> </span><span class="p">(</span><span class="kt">void</span><span class="p">)</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-24" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-24" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-24"></a><span class="p">{</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-25" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-25" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-25"></a><span class="w"> </span><span class="n">printf</span><span class="w"> </span><span class="p">(</span><span class="s">"foo</span><span class="se">\n</span><span class="s">"</span><span class="p">);</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-26" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-26" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-26"></a><span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="n">bar</span><span class="p">;</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-27" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-27" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-27"></a><span class="p">}</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-28" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-28" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-28"></a>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-29" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-29" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-29"></a>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-30" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-30" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-30"></a><span class="kt">int</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-31" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-31" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-31"></a><span class="nf">main</span><span class="w"> </span><span class="p">(</span><span class="kt">int</span><span class="w"> </span><span class="n">argc</span><span class="p">,</span><span class="w"> </span><span class="kt">char</span><span class="w"> </span><span class="o">**</span><span class="n">argv</span><span class="p">)</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-32" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-32" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-32"></a><span class="p">{</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-33" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-33" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-33"></a><span class="w"> </span><span class="n">trampoline</span><span class="w"> </span><span class="n">t</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">foo</span><span class="p">;</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-34" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-34" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-34"></a><span class="w"> </span><span class="k">while</span><span class="w"> </span><span class="p">(</span><span class="n">t</span><span class="p">)</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-35" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-35" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-35"></a><span class="w"> </span><span class="n">t</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">t</span><span class="w"> </span><span class="p">();</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-36" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-36" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-36"></a><span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="mi">0</span><span class="p">;</span>
<a id="rest_code_7ab67d6e73a74f3b95b4892f627e9418-37" name="rest_code_7ab67d6e73a74f3b95b4892f627e9418-37" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7ab67d6e73a74f3b95b4892f627e9418-37"></a><span class="p">}</span>
</pre></div>
<p>So, here's where C's weak typing lets it get away with things that
more strongly typed languages don't. Notice the declaration of the
trampoline type:</p>
<div class="code"><pre class="code c"><a id="rest_code_7bb80030465446a6827cf3477f198a8c-1" name="rest_code_7bb80030465446a6827cf3477f198a8c-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_7bb80030465446a6827cf3477f198a8c-1"></a><span class="n">type</span><span class="w"> </span><span class="n">def</span><span class="w"> </span><span class="kt">void</span><span class="o">*</span><span class="w"> </span><span class="p">(</span><span class="o">*</span><span class="n">trampoline</span><span class="p">)(</span><span class="kt">void</span><span class="p">);</span>
</pre></div>
<p id="mentioning-recursive-types">Notice how it returns a <code class="docutils literal">void *</code>, instead of something more
specific? That's because if it tried to return something more
specific, it would have to a <a class="reference external" href="https://en.wikipedia.org/wiki/Recursive_data_type">recursive type</a>: that is to say, while
defining the type <code class="docutils literal">trampoline</code>, you would use a reference to the
type while defining the type. It would look something like this:</p>
<div class="code"><pre class="code c"><a id="rest_code_a32f532c1299409696c0950ee3fe2f39-1" name="rest_code_a32f532c1299409696c0950ee3fe2f39-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_a32f532c1299409696c0950ee3fe2f39-1"></a><span class="k">typedef</span><span class="w"> </span><span class="n">trampoline</span><span class="o">*</span><span class="w"> </span><span class="p">(</span><span class="o">*</span><span class="n">trampoline</span><span class="p">)(</span><span class="kt">void</span><span class="p">);</span>
</pre></div>
<p>and that results in <span class="app">gcc</span> issuing the following error:</p>
<pre class="literal-block">error: unknown type name 'trampoline'</pre>
<p>Very few traditional programming languages allow this. It isn't a
problem in Scheme or Common Lisp because those languages use strong
dynamic typing, where the types are checked at runtime.</p>
<p>So how do you do this in languages with strong static typing?</p>
<p>Well, let's try this in some of the <a class="reference external" href="https://en.wikipedia.org/wiki/Oberon_(programming_language)">Oberon</a> programming language
dialects. <a class="reference external" href="https://en.wikipedia.org/wiki/Oberon_(programming_language)">Oberon</a> was designed and implemented by Niklaus Wirth
(<a class="reference external" href="https://people.inf.ethz.ch/wirth/">NW1</a>, <a class="reference external" href="https://en.wikipedia.org/wiki/Niklaus_Wirth">NW2</a>) as a simplification and generalization of his earlier
languages <a class="reference external" href="https://en.wikipedia.org/wiki/Pascal_(programming_language)">Pascal</a>, <a class="reference external" href="https://en.wikipedia.org/wiki/Modula">Modula</a>, and <a class="reference external" href="https://en.wikipedia.org/wiki/Modula-2">Modula-2</a>. (Here's <a class="reference external" href="https://people.inf.ethz.ch/wirth/Oberon/Oberon.Report.pdf">The Programming
Language Oberon (1990)</a>, the original Oberon language report, in PDF
for reference.) I find the original Oberon admirable for its
simplicity, strong typing, understandable syntax, and its introduction
of <a class="reference external" href="https://dl.acm.org/doi/abs/10.1145/42190.46167">Type Extensions</a> (which organizes <a class="reference external" href="https://en.wikipedia.org/wiki/Record_(computer_science)">record types</a> in a
inheritance hierarchy, which with the use of procedure variables
enables object oriented programming in a particularly straightforward
and flexible way) but struggle with its minimalism and how its
standard libraries differ in paradigm from the standard Unix
libraries, since Oberon was used to implement a new operating system,
the <a class="reference external" href="https://en.wikipedia.org/wiki/Oberon_(operating_system)">Oberon System</a> with its own completely unique <a class="reference external" href="https://en.wikipedia.org/wiki/API">API</a>.</p>
<p><a class="reference external" href="https://en.wikipedia.org/wiki/Oberon_(programming_language)">Oberon</a> has a number of dialects. I'm most fond of <a class="reference external" href="https://en.wikipedia.org/wiki/Oberon-2">Oberon-2</a>, which
was the second language in the <a class="reference external" href="https://en.wikipedia.org/wiki/Oberon_(programming_language)">Oberon</a> family, developed by <a class="reference external" href="https://en.wikipedia.org/wiki/Hanspeter_M%C3%B6ssenb%C3%B6ck">Hanspeter
Mössenböck</a> and Niklaus Wirth. It is a little less minimalist than
<a class="reference external" href="https://en.wikipedia.org/wiki/Oberon_(programming_language)">Oberon</a>, and among a few other things adds type-bound procedures to
the record hierarchy provided by <a class="reference external" href="https://dl.acm.org/doi/abs/10.1145/42190.46167">Type Extensions</a>, providing a
appealingly simple and direct design for object-oriented programming
that was later adopted by the <a class="reference external" href="https://en.wikipedia.org/wiki/Ada_(programming_language)">Ada</a> programming language in a more
complicated and subtle version, as might be expected by <a class="reference external" href="https://en.wikipedia.org/wiki/Ada_(programming_language)">Ada</a>'s
plethora of design goals and constraints. (Here's a couple of papers
that mention it: <a class="reference external" href="https://dl.acm.org/doi/10.1145/122028.122033">Object-oriented programming through type
extension in Ada 9X</a> (<a class="reference external" href="https://dl.acm.org/doi/pdf/10.1145/122028.122033">ADAOO1PDF</a>) and <a class="reference external" href="http://citeseer.ist.psu.edu/viewdoc/summary?doi=10.1.1.167.7445&rank=1">Integrating Object-Oriented
Programming and Protected Objects in Ada 95</a> (<a class="reference external" href="http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.167.7445&rep=rep1&type=pdf">ADAOO2PDF</a>). I wish I
knew of a reference that discussed explicitly the process of choosing
<a class="reference external" href="https://dl.acm.org/doi/abs/10.1145/42190.46167">Type Extensions</a> for <a class="reference external" href="https://en.wikipedia.org/wiki/Ada_(programming_language)">Ada</a> and how they were adopted and adapted in
<a class="reference external" href="https://en.wikipedia.org/wiki/Ada_(programming_language)">Ada</a>.)</p>
<p>Here's a copy of the Oberon-2 language report in PDF (<a class="reference external" href="https://tkurtbond.github.io/Oberon-2/Oberon2.pdf">O2PDF</a>) and HTML
(<a class="reference external" href="https://web.archive.org/web/20151104101932/https://cseweb.ucsd.edu/~wgg/CSE131B/oberon2.htm">O2HTML</a>), for reference.</p>
<p>Anyway, <a class="reference external" href="https://en.wikipedia.org/wiki/Oberon-2">Oberon-2</a> has procedure types and procedure variables, so one
would think it would be simple to implement trampolines in <a class="reference external" href="https://en.wikipedia.org/wiki/Oberon-2">Oberon-2</a>,
without messing about with pointers. It turns out to be more
complicated than one would think.</p>
<p>I'm using <a class="reference external" href="https://github.com/vishaps/voc">Vishap Oberon</a>, a free and open source Oberon-2 compiler,
by the way.</p>
<p>First, here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/oberon-2/NotForever.Mod">NotForever.Mod</a>, the standard program with a recursive
function procedure that will overflow the stack.</p>
<div class="code"><pre class="code modula2"><a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-1" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-1"></a><span class="kr">MODULE</span> <span class="n">NotForever</span><span class="p">;</span> <span class="cm">(* Recurse until stack space runs out. *)</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-2" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-2"></a> <span class="kr">IMPORT</span> <span class="n">Out</span><span class="p">;</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-3" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-3"></a> <span class="kr">VAR</span> <span class="n">i</span><span class="p">:</span> <span class="nb">LONGINT</span><span class="p">;</span> <span class="cm">(* Number of times f has been called. *)</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-4" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-4"></a>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-5" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-5"></a> <span class="kr">PROCEDURE</span> <span class="n">f</span><span class="p">;</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-6" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-6"></a> <span class="kr">BEGIN</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-7" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-7"></a> <span class="nb">INC</span><span class="p">(</span><span class="n">i</span><span class="p">);</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-8" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-8"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"call #"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Int</span> <span class="p">(</span><span class="n">i</span><span class="p">,</span> <span class="mi">0</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-9" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-9"></a> <span class="n">f</span><span class="p">;</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-10" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-10"></a> <span class="kr">END</span> <span class="n">f</span><span class="p">;</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-11" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-11"></a>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-12" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-12"></a><span class="kr">BEGIN</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-13" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-13"></a> <span class="n">i</span> <span class="o">:=</span> <span class="mi">0</span><span class="p">;</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-14" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-14"></a> <span class="n">f</span><span class="p">;</span>
<a id="rest_code_75240e1614ff42b8aaaf24acd6fa1694-15" name="rest_code_75240e1614ff42b8aaaf24acd6fa1694-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_75240e1614ff42b8aaaf24acd6fa1694-15"></a><span class="kr">END</span> <span class="n">NotForever</span><span class="p">.</span>
</pre></div>
<p>On my system, this program dies with with the error <code class="docutils literal">Segmentation
fault: 11</code> after call #524008.</p>
<p>Now on to trampolines. In theory we should be able to declare a type
that is a function procedure that returns other function procedures.
Here's the first attempt at the limited trampoline,
<a class="reference external" href="https://tkurtbond.github.io/trampolines/oberon-2/TrampolineBroken.Mod">TrampolineBroken.Mod</a>.</p>
<div class="code"><pre class="code modula2"><a id="rest_code_da6279691fa746fb856344325f7d631a-1" name="rest_code_da6279691fa746fb856344325f7d631a-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-1"></a><span class="kr">MODULE</span> <span class="n">TrampolineBroken</span><span class="p">;</span> <span class="cm">(* Fail to demonstrate lisp-style trampolines. *)</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-2" name="rest_code_da6279691fa746fb856344325f7d631a-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-2"></a> <span class="kr">IMPORT</span> <span class="n">Out</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-3" name="rest_code_da6279691fa746fb856344325f7d631a-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-3"></a>
<a id="rest_code_da6279691fa746fb856344325f7d631a-4" name="rest_code_da6279691fa746fb856344325f7d631a-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-4"></a> <span class="kr">TYPE</span> <span class="n">Thunk</span> <span class="o">=</span> <span class="kr">PROCEDURE</span> <span class="p">():</span> <span class="n">Thunk</span><span class="p">;</span> <span class="cm">(* This is an error. *)</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-5" name="rest_code_da6279691fa746fb856344325f7d631a-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-5"></a>
<a id="rest_code_da6279691fa746fb856344325f7d631a-6" name="rest_code_da6279691fa746fb856344325f7d631a-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-6"></a> <span class="kr">VAR</span> <span class="n">next</span><span class="p">:</span> <span class="n">Thunk</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-7" name="rest_code_da6279691fa746fb856344325f7d631a-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-7"></a>
<a id="rest_code_da6279691fa746fb856344325f7d631a-8" name="rest_code_da6279691fa746fb856344325f7d631a-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-8"></a> <span class="kr">PROCEDURE</span> <span class="n">baz</span> <span class="p">():</span> <span class="n">Thunk</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-9" name="rest_code_da6279691fa746fb856344325f7d631a-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-9"></a> <span class="kr">BEGIN</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-10" name="rest_code_da6279691fa746fb856344325f7d631a-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-10"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"baz"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-11" name="rest_code_da6279691fa746fb856344325f7d631a-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-11"></a> <span class="n">next</span> <span class="o">:=</span> <span class="nb">NIL</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-12" name="rest_code_da6279691fa746fb856344325f7d631a-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-12"></a> <span class="kr">END</span> <span class="n">baz</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-13" name="rest_code_da6279691fa746fb856344325f7d631a-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-13"></a>
<a id="rest_code_da6279691fa746fb856344325f7d631a-14" name="rest_code_da6279691fa746fb856344325f7d631a-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-14"></a> <span class="kr">PROCEDURE</span> <span class="n">bar</span> <span class="p">():</span> <span class="n">Thunk</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-15" name="rest_code_da6279691fa746fb856344325f7d631a-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-15"></a> <span class="kr">BEGIN</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-16" name="rest_code_da6279691fa746fb856344325f7d631a-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-16"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"bar"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-17" name="rest_code_da6279691fa746fb856344325f7d631a-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-17"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">baz</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-18" name="rest_code_da6279691fa746fb856344325f7d631a-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-18"></a> <span class="kr">END</span> <span class="n">bar</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-19" name="rest_code_da6279691fa746fb856344325f7d631a-19" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-19"></a>
<a id="rest_code_da6279691fa746fb856344325f7d631a-20" name="rest_code_da6279691fa746fb856344325f7d631a-20" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-20"></a> <span class="kr">PROCEDURE</span> <span class="n">foo</span> <span class="p">():</span> <span class="n">Thunk</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-21" name="rest_code_da6279691fa746fb856344325f7d631a-21" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-21"></a> <span class="kr">BEGIN</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-22" name="rest_code_da6279691fa746fb856344325f7d631a-22" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-22"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"foo"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-23" name="rest_code_da6279691fa746fb856344325f7d631a-23" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-23"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">bar</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-24" name="rest_code_da6279691fa746fb856344325f7d631a-24" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-24"></a> <span class="kr">END</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-25" name="rest_code_da6279691fa746fb856344325f7d631a-25" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-25"></a>
<a id="rest_code_da6279691fa746fb856344325f7d631a-26" name="rest_code_da6279691fa746fb856344325f7d631a-26" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-26"></a><span class="kr">BEGIN</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-27" name="rest_code_da6279691fa746fb856344325f7d631a-27" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-27"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-28" name="rest_code_da6279691fa746fb856344325f7d631a-28" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-28"></a> <span class="kr">WHILE</span> <span class="n">next</span> <span class="o">#</span> <span class="nb">NIL</span> <span class="kr">DO</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-29" name="rest_code_da6279691fa746fb856344325f7d631a-29" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-29"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">next</span> <span class="p">();</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-30" name="rest_code_da6279691fa746fb856344325f7d631a-30" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-30"></a> <span class="kr">END</span><span class="p">;</span>
<a id="rest_code_da6279691fa746fb856344325f7d631a-31" name="rest_code_da6279691fa746fb856344325f7d631a-31" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_da6279691fa746fb856344325f7d631a-31"></a><span class="kr">END</span> <span class="n">TrampolineBroken</span><span class="p">.</span>
</pre></div>
<p>Unfortunately, trying to compile this dies with the following error
message:</p>
<pre class="literal-block">TrampolineBroken.Mod Compiling TrampolineBroken.
4: TYPE Thunk = PROCEDURE (): Thunk;
^
pos 126 err 244 cyclic type definition not allowed
Module compilation failed.</pre>
<p>As mentioned <a class="reference external" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#mentioning-recursive-types">above</a>, this is a case of a <a class="reference external" href="https://en.wikipedia.org/wiki/Recursive_data_type">recursive type</a>. Well, drat.</p>
<p>At this point the immediate reaction is to look at the C version and
try to hack up something analogous using functionality from
<a class="reference external" href="https://en.wikipedia.org/wiki/Oberon-2">Oberon-2</a>'s <code class="docutils literal">SYSTEM</code> module, but that way lies madness, difficulty,
and type errors. Instead, you have to step back and think about
things from another viewpoint. The problem is that we can't declare a
type for a function procedure that returns another function procedure
of its type, because that is recursive. Instead of trying for a
<a class="reference external" href="https://en.wikipedia.org/wiki/Recursive_data_type">recursive type</a>, what if we switched to storing the next procedure
to be run in a global variable, <code class="docutils literal">next</code>, and having each procedure in
the chain set that to the procedure that should run next? That should
work!</p>
<p>Here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/oberon-2/Trampoline.Mod">Trampoline.Mod</a>, a version that works!</p>
<div class="code"><pre class="code modula2"><a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-1" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-1"></a><span class="kr">MODULE</span> <span class="n">Trampoline</span><span class="p">;</span> <span class="cm">(* Demonstrate lisp-style trampolines. *)</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-2" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-2"></a> <span class="kr">IMPORT</span> <span class="n">Out</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-3" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-3"></a>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-4" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-4"></a> <span class="kr">TYPE</span> <span class="n">Thunk</span> <span class="o">=</span> <span class="kr">PROCEDURE</span> <span class="p">();</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-5" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-5"></a>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-6" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-6"></a> <span class="kr">VAR</span> <span class="n">next</span><span class="p">:</span> <span class="n">Thunk</span><span class="p">;</span> <span class="cm">(* Next procedure to be called. *)</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-7" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-7"></a>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-8" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-8"></a> <span class="kr">PROCEDURE</span> <span class="n">baz</span> <span class="p">();</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-9" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-9"></a> <span class="kr">BEGIN</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-10" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-10"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"baz"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-11" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-11"></a> <span class="n">next</span> <span class="o">:=</span> <span class="nb">NIL</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-12" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-12"></a> <span class="kr">END</span> <span class="n">baz</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-13" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-13"></a>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-14" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-14"></a> <span class="kr">PROCEDURE</span> <span class="n">bar</span> <span class="p">();</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-15" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-15"></a> <span class="kr">BEGIN</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-16" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-16"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"bar"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-17" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-17"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">baz</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-18" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-18"></a> <span class="kr">END</span> <span class="n">bar</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-19" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-19" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-19"></a>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-20" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-20" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-20"></a> <span class="kr">PROCEDURE</span> <span class="n">foo</span> <span class="p">();</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-21" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-21" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-21"></a> <span class="kr">BEGIN</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-22" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-22" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-22"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"foo"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-23" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-23" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-23"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">bar</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-24" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-24" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-24"></a> <span class="kr">END</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-25" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-25" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-25"></a>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-26" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-26" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-26"></a><span class="kr">BEGIN</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-27" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-27" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-27"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-28" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-28" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-28"></a> <span class="kr">WHILE</span> <span class="n">next</span> <span class="o">#</span> <span class="nb">NIL</span> <span class="kr">DO</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-29" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-29" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-29"></a> <span class="n">next</span> <span class="p">();</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-30" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-30" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-30"></a> <span class="kr">END</span><span class="p">;</span>
<a id="rest_code_c0ce5aad01fe4f37adab745007d202d8-31" name="rest_code_c0ce5aad01fe4f37adab745007d202d8-31" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_c0ce5aad01fe4f37adab745007d202d8-31"></a><span class="kr">END</span> <span class="n">Trampoline</span><span class="p">.</span>
</pre></div>
<p>And here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/oberon-2/TrampolineForever.Mod">TrampolineForever.Mod</a>, which also works!</p>
<div class="code"><pre class="code modula2"><a id="rest_code_2e43905e6da44676b9edca5066d065c8-1" name="rest_code_2e43905e6da44676b9edca5066d065c8-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-1"></a><span class="kr">MODULE</span> <span class="n">TrampolineForever</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-2" name="rest_code_2e43905e6da44676b9edca5066d065c8-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-2"></a> <span class="cm">(* Recurse forever without running out of stack space. *)</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-3" name="rest_code_2e43905e6da44676b9edca5066d065c8-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-3"></a> <span class="kr">IMPORT</span> <span class="n">Out</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-4" name="rest_code_2e43905e6da44676b9edca5066d065c8-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-4"></a>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-5" name="rest_code_2e43905e6da44676b9edca5066d065c8-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-5"></a> <span class="kr">TYPE</span> <span class="n">Thunk</span> <span class="o">=</span> <span class="kr">PROCEDURE</span> <span class="p">();</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-6" name="rest_code_2e43905e6da44676b9edca5066d065c8-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-6"></a>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-7" name="rest_code_2e43905e6da44676b9edca5066d065c8-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-7"></a> <span class="kr">VAR</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-8" name="rest_code_2e43905e6da44676b9edca5066d065c8-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-8"></a> <span class="n">next</span><span class="p">:</span> <span class="n">Thunk</span><span class="p">;</span> <span class="cm">(* Next procedure to be called. *)</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-9" name="rest_code_2e43905e6da44676b9edca5066d065c8-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-9"></a> <span class="n">i</span><span class="p">:</span> <span class="nb">INTEGER</span><span class="p">;</span> <span class="cm">(* Number of times through the trampoline. *)</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-10" name="rest_code_2e43905e6da44676b9edca5066d065c8-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-10"></a>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-11" name="rest_code_2e43905e6da44676b9edca5066d065c8-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-11"></a> <span class="kr">PROCEDURE</span> <span class="o">^</span><span class="n">foo</span><span class="p">;</span> <span class="cm">(* Forward declaration. *)</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-12" name="rest_code_2e43905e6da44676b9edca5066d065c8-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-12"></a>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-13" name="rest_code_2e43905e6da44676b9edca5066d065c8-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-13"></a> <span class="kr">PROCEDURE</span> <span class="n">baz</span> <span class="p">();</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-14" name="rest_code_2e43905e6da44676b9edca5066d065c8-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-14"></a> <span class="kr">BEGIN</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-15" name="rest_code_2e43905e6da44676b9edca5066d065c8-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-15"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"baz"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-16" name="rest_code_2e43905e6da44676b9edca5066d065c8-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-16"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-17" name="rest_code_2e43905e6da44676b9edca5066d065c8-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-17"></a> <span class="kr">END</span> <span class="n">baz</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-18" name="rest_code_2e43905e6da44676b9edca5066d065c8-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-18"></a>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-19" name="rest_code_2e43905e6da44676b9edca5066d065c8-19" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-19"></a> <span class="kr">PROCEDURE</span> <span class="n">bar</span> <span class="p">();</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-20" name="rest_code_2e43905e6da44676b9edca5066d065c8-20" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-20"></a> <span class="kr">BEGIN</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-21" name="rest_code_2e43905e6da44676b9edca5066d065c8-21" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-21"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"bar"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-22" name="rest_code_2e43905e6da44676b9edca5066d065c8-22" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-22"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">baz</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-23" name="rest_code_2e43905e6da44676b9edca5066d065c8-23" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-23"></a> <span class="kr">END</span> <span class="n">bar</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-24" name="rest_code_2e43905e6da44676b9edca5066d065c8-24" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-24"></a>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-25" name="rest_code_2e43905e6da44676b9edca5066d065c8-25" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-25"></a> <span class="kr">PROCEDURE</span> <span class="n">foo</span> <span class="p">();</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-26" name="rest_code_2e43905e6da44676b9edca5066d065c8-26" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-26"></a> <span class="kr">BEGIN</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-27" name="rest_code_2e43905e6da44676b9edca5066d065c8-27" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-27"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"foo"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-28" name="rest_code_2e43905e6da44676b9edca5066d065c8-28" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-28"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">bar</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-29" name="rest_code_2e43905e6da44676b9edca5066d065c8-29" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-29"></a> <span class="kr">END</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-30" name="rest_code_2e43905e6da44676b9edca5066d065c8-30" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-30"></a>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-31" name="rest_code_2e43905e6da44676b9edca5066d065c8-31" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-31"></a><span class="kr">BEGIN</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-32" name="rest_code_2e43905e6da44676b9edca5066d065c8-32" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-32"></a> <span class="n">i</span> <span class="o">:=</span> <span class="mi">0</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-33" name="rest_code_2e43905e6da44676b9edca5066d065c8-33" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-33"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-34" name="rest_code_2e43905e6da44676b9edca5066d065c8-34" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-34"></a> <span class="kr">WHILE</span> <span class="n">next</span> <span class="o">#</span> <span class="nb">NIL</span> <span class="kr">DO</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-35" name="rest_code_2e43905e6da44676b9edca5066d065c8-35" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-35"></a> <span class="nb">INC</span> <span class="p">(</span><span class="n">i</span><span class="p">);</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-36" name="rest_code_2e43905e6da44676b9edca5066d065c8-36" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-36"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"call #"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Int</span> <span class="p">(</span><span class="n">i</span><span class="p">,</span> <span class="mi">0</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-37" name="rest_code_2e43905e6da44676b9edca5066d065c8-37" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-37"></a> <span class="n">next</span> <span class="p">();</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-38" name="rest_code_2e43905e6da44676b9edca5066d065c8-38" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-38"></a> <span class="kr">END</span><span class="p">;</span>
<a id="rest_code_2e43905e6da44676b9edca5066d065c8-39" name="rest_code_2e43905e6da44676b9edca5066d065c8-39" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_2e43905e6da44676b9edca5066d065c8-39"></a><span class="kr">END</span> <span class="n">TrampolineForever</span><span class="p">.</span>
</pre></div>
<p>Wirth has continued to work on Oberon, producing an even more
minimalist revision, often know as Oberon-07, or <a class="reference external" href="https://people.inf.ethz.ch/wirth/Oberon/index.html">Revised Oberon</a>.
(Here's the <a class="reference external" href="https://people.inf.ethz.ch/wirth/Oberon/Oberon07.Report.pdf">The Programming Language Oberon-07 (Revised Oberon)</a> in
PDF, for reference.) Unfortunately, he removed forward declarations
and the <code class="docutils literal">LONGINT</code> type, which means we have to make some minor
changes.</p>
<p>I'm using OBNC (<a class="reference external" href="https://miasap.se/obnc/">OBNC1</a>, <a class="reference external" href="https://github.com/GunterMueller/OBNC">OBNC2</a>) for <a class="reference external" href="https://people.inf.ethz.ch/wirth/Oberon/index.html">Revised Oberon</a>.</p>
<p>Here's the <a class="reference external" href="https://tkurtbond.github.io/trampolines/revised-oberon/NotForever.Mod">Revised Oberon NotForever.Mod</a>, with <code class="docutils literal">LONGINT</code> replaced
by <code class="docutils literal">INTEGER</code>:</p>
<div class="code"><pre class="code modula2"><a id="rest_code_146baaf618e54089b1d45eba951e116e-1" name="rest_code_146baaf618e54089b1d45eba951e116e-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-1"></a><span class="kr">MODULE</span> <span class="n">NotForever</span><span class="p">;</span> <span class="cm">(* Recurse until stack space runs out. *)</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-2" name="rest_code_146baaf618e54089b1d45eba951e116e-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-2"></a> <span class="kr">IMPORT</span> <span class="n">Out</span><span class="p">;</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-3" name="rest_code_146baaf618e54089b1d45eba951e116e-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-3"></a> <span class="kr">VAR</span> <span class="n">i</span><span class="p">:</span> <span class="nb">INTEGER</span><span class="p">;</span> <span class="cm">(* Number of times f has been called. *)</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-4" name="rest_code_146baaf618e54089b1d45eba951e116e-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-4"></a> <span class="cm">(* Alas, no more LONGINT. *)</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-5" name="rest_code_146baaf618e54089b1d45eba951e116e-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-5"></a>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-6" name="rest_code_146baaf618e54089b1d45eba951e116e-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-6"></a> <span class="kr">PROCEDURE</span> <span class="n">f</span><span class="p">;</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-7" name="rest_code_146baaf618e54089b1d45eba951e116e-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-7"></a> <span class="kr">BEGIN</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-8" name="rest_code_146baaf618e54089b1d45eba951e116e-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-8"></a> <span class="nb">INC</span><span class="p">(</span><span class="n">i</span><span class="p">);</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-9" name="rest_code_146baaf618e54089b1d45eba951e116e-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-9"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"call #"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Int</span> <span class="p">(</span><span class="n">i</span><span class="p">,</span> <span class="mi">0</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-10" name="rest_code_146baaf618e54089b1d45eba951e116e-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-10"></a> <span class="n">f</span><span class="p">;</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-11" name="rest_code_146baaf618e54089b1d45eba951e116e-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-11"></a> <span class="kr">END</span> <span class="n">f</span><span class="p">;</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-12" name="rest_code_146baaf618e54089b1d45eba951e116e-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-12"></a>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-13" name="rest_code_146baaf618e54089b1d45eba951e116e-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-13"></a><span class="kr">BEGIN</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-14" name="rest_code_146baaf618e54089b1d45eba951e116e-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-14"></a> <span class="n">i</span> <span class="o">:=</span> <span class="mi">0</span><span class="p">;</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-15" name="rest_code_146baaf618e54089b1d45eba951e116e-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-15"></a> <span class="n">f</span><span class="p">;</span>
<a id="rest_code_146baaf618e54089b1d45eba951e116e-16" name="rest_code_146baaf618e54089b1d45eba951e116e-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_146baaf618e54089b1d45eba951e116e-16"></a><span class="kr">END</span> <span class="n">NotForever</span><span class="p">.</span>
</pre></div>
<p>Here's the <a class="reference external" href="https://tkurtbond.github.io/trampolines/revised-oberon/Trampoline.Mod">Revised Oberon Trampoline.Mod</a>:</p>
<div class="code"><pre class="code modula2"><a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-1" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-1"></a><span class="kr">MODULE</span> <span class="n">Trampoline</span><span class="p">;</span> <span class="cm">(* Demonstrate lisp-style trampolines. *)</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-2" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-2"></a> <span class="kr">IMPORT</span> <span class="n">Out</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-3" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-3"></a>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-4" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-4"></a> <span class="kr">TYPE</span> <span class="n">Thunk</span> <span class="o">=</span> <span class="kr">PROCEDURE</span> <span class="p">();</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-5" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-5"></a>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-6" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-6"></a> <span class="kr">VAR</span> <span class="n">next</span><span class="p">:</span> <span class="n">Thunk</span><span class="p">;</span> <span class="cm">(* Next procedure to be called. *)</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-7" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-7"></a>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-8" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-8"></a> <span class="kr">PROCEDURE</span> <span class="n">baz</span> <span class="p">();</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-9" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-9"></a> <span class="kr">BEGIN</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-10" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-10"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"baz"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-11" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-11"></a> <span class="n">next</span> <span class="o">:=</span> <span class="nb">NIL</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-12" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-12"></a> <span class="kr">END</span> <span class="n">baz</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-13" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-13"></a>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-14" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-14"></a> <span class="kr">PROCEDURE</span> <span class="n">bar</span> <span class="p">();</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-15" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-15"></a> <span class="kr">BEGIN</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-16" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-16"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"bar"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-17" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-17"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">baz</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-18" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-18"></a> <span class="kr">END</span> <span class="n">bar</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-19" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-19" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-19"></a>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-20" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-20" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-20"></a> <span class="kr">PROCEDURE</span> <span class="n">foo</span> <span class="p">();</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-21" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-21" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-21"></a> <span class="kr">BEGIN</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-22" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-22" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-22"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"foo"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-23" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-23" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-23"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">bar</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-24" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-24" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-24"></a> <span class="kr">END</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-25" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-25" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-25"></a>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-26" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-26" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-26"></a><span class="kr">BEGIN</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-27" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-27" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-27"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-28" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-28" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-28"></a> <span class="kr">WHILE</span> <span class="n">next</span> <span class="o">#</span> <span class="nb">NIL</span> <span class="kr">DO</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-29" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-29" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-29"></a> <span class="n">next</span> <span class="p">();</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-30" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-30" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-30"></a> <span class="kr">END</span><span class="p">;</span>
<a id="rest_code_97e66a3c60e64cca80b06e2a8126615c-31" name="rest_code_97e66a3c60e64cca80b06e2a8126615c-31" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_97e66a3c60e64cca80b06e2a8126615c-31"></a><span class="kr">END</span> <span class="n">Trampoline</span><span class="p">.</span>
</pre></div>
<p>Here's the <a class="reference external" href="https://tkurtbond.github.io/trampolines/revised-oberon/TrampolineForever.Mod">Revised Oberon TrampolineForever.Mod</a>, with a workaround
for the removal of forward declarations of procedures:</p>
<div class="code"><pre class="code modula2"><a id="rest_code_99dc53a0f144475c9a582626a13664ab-1" name="rest_code_99dc53a0f144475c9a582626a13664ab-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-1"></a><span class="kr">MODULE</span> <span class="n">TrampolineForever</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-2" name="rest_code_99dc53a0f144475c9a582626a13664ab-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-2"></a> <span class="cm">(* Recurse forever without running out of stack space. *)</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-3" name="rest_code_99dc53a0f144475c9a582626a13664ab-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-3"></a> <span class="kr">IMPORT</span> <span class="n">Out</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-4" name="rest_code_99dc53a0f144475c9a582626a13664ab-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-4"></a>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-5" name="rest_code_99dc53a0f144475c9a582626a13664ab-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-5"></a> <span class="kr">TYPE</span> <span class="n">Thunk</span> <span class="o">=</span> <span class="kr">PROCEDURE</span> <span class="p">();</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-6" name="rest_code_99dc53a0f144475c9a582626a13664ab-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-6"></a>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-7" name="rest_code_99dc53a0f144475c9a582626a13664ab-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-7"></a> <span class="kr">VAR</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-8" name="rest_code_99dc53a0f144475c9a582626a13664ab-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-8"></a> <span class="n">forward</span><span class="p">:</span> <span class="n">Thunk</span><span class="p">;</span> <span class="cm">(* Forward declaration. *)</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-9" name="rest_code_99dc53a0f144475c9a582626a13664ab-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-9"></a> <span class="n">next</span><span class="p">:</span> <span class="n">Thunk</span><span class="p">;</span> <span class="cm">(* Next procedure to be called. *)</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-10" name="rest_code_99dc53a0f144475c9a582626a13664ab-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-10"></a> <span class="n">i</span><span class="p">:</span> <span class="nb">INTEGER</span><span class="p">;</span> <span class="cm">(* Number of times through the trampoline. *)</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-11" name="rest_code_99dc53a0f144475c9a582626a13664ab-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-11"></a>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-12" name="rest_code_99dc53a0f144475c9a582626a13664ab-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-12"></a> <span class="kr">PROCEDURE</span> <span class="n">baz</span> <span class="p">();</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-13" name="rest_code_99dc53a0f144475c9a582626a13664ab-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-13"></a> <span class="kr">BEGIN</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-14" name="rest_code_99dc53a0f144475c9a582626a13664ab-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-14"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"baz"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-15" name="rest_code_99dc53a0f144475c9a582626a13664ab-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-15"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">forward</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-16" name="rest_code_99dc53a0f144475c9a582626a13664ab-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-16"></a> <span class="kr">END</span> <span class="n">baz</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-17" name="rest_code_99dc53a0f144475c9a582626a13664ab-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-17"></a>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-18" name="rest_code_99dc53a0f144475c9a582626a13664ab-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-18"></a> <span class="kr">PROCEDURE</span> <span class="n">bar</span> <span class="p">();</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-19" name="rest_code_99dc53a0f144475c9a582626a13664ab-19" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-19"></a> <span class="kr">BEGIN</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-20" name="rest_code_99dc53a0f144475c9a582626a13664ab-20" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-20"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"bar"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-21" name="rest_code_99dc53a0f144475c9a582626a13664ab-21" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-21"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">baz</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-22" name="rest_code_99dc53a0f144475c9a582626a13664ab-22" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-22"></a> <span class="kr">END</span> <span class="n">bar</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-23" name="rest_code_99dc53a0f144475c9a582626a13664ab-23" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-23"></a>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-24" name="rest_code_99dc53a0f144475c9a582626a13664ab-24" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-24"></a> <span class="kr">PROCEDURE</span> <span class="n">foo</span> <span class="p">();</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-25" name="rest_code_99dc53a0f144475c9a582626a13664ab-25" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-25"></a> <span class="kr">BEGIN</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-26" name="rest_code_99dc53a0f144475c9a582626a13664ab-26" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-26"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"foo"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-27" name="rest_code_99dc53a0f144475c9a582626a13664ab-27" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-27"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">bar</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-28" name="rest_code_99dc53a0f144475c9a582626a13664ab-28" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-28"></a> <span class="kr">END</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-29" name="rest_code_99dc53a0f144475c9a582626a13664ab-29" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-29"></a>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-30" name="rest_code_99dc53a0f144475c9a582626a13664ab-30" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-30"></a><span class="kr">BEGIN</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-31" name="rest_code_99dc53a0f144475c9a582626a13664ab-31" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-31"></a> <span class="n">forward</span> <span class="o">:=</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-32" name="rest_code_99dc53a0f144475c9a582626a13664ab-32" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-32"></a> <span class="n">i</span> <span class="o">:=</span> <span class="mi">0</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-33" name="rest_code_99dc53a0f144475c9a582626a13664ab-33" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-33"></a> <span class="n">next</span> <span class="o">:=</span> <span class="n">foo</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-34" name="rest_code_99dc53a0f144475c9a582626a13664ab-34" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-34"></a> <span class="kr">WHILE</span> <span class="n">next</span> <span class="o">#</span> <span class="nb">NIL</span> <span class="kr">DO</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-35" name="rest_code_99dc53a0f144475c9a582626a13664ab-35" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-35"></a> <span class="nb">INC</span> <span class="p">(</span><span class="n">i</span><span class="p">);</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-36" name="rest_code_99dc53a0f144475c9a582626a13664ab-36" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-36"></a> <span class="n">Out</span><span class="p">.</span><span class="n">String</span> <span class="p">(</span><span class="s2">"call #"</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Int</span> <span class="p">(</span><span class="n">i</span><span class="p">,</span> <span class="mi">0</span><span class="p">);</span> <span class="n">Out</span><span class="p">.</span><span class="n">Ln</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-37" name="rest_code_99dc53a0f144475c9a582626a13664ab-37" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-37"></a> <span class="n">next</span> <span class="p">();</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-38" name="rest_code_99dc53a0f144475c9a582626a13664ab-38" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-38"></a> <span class="kr">END</span><span class="p">;</span>
<a id="rest_code_99dc53a0f144475c9a582626a13664ab-39" name="rest_code_99dc53a0f144475c9a582626a13664ab-39" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_99dc53a0f144475c9a582626a13664ab-39"></a><span class="kr">END</span> <span class="n">TrampolineForever</span><span class="p">.</span>
</pre></div>
<p>Note that with forward declarations removed, we just declare a
procedure variable, <code class="docutils literal">forward</code>, initialize it before starting the
trampoline, and refer to it instead of <code class="docutils literal">foo</code> in procedure <code class="docutils literal">baz</code>.</p>
<p>And of course, since we mentioned <a class="reference external" href="https://en.wikipedia.org/wiki/Ada_(programming_language)">Ada</a> above, we should do a version
in that. I'm using <a class="reference external" href="https://en.wikipedia.org/wiki/GNAT">GNAT</a>.</p>
<p>Here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/ada/not_forever.adb">not_forever.adb</a>:</p>
<div class="code"><pre class="code ada"><a id="rest_code_0385449473644583a667a5b9631a4eb2-1" name="rest_code_0385449473644583a667a5b9631a4eb2-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-1"></a><span class="kn">with</span> <span class="n">Ada.Text_IO</span><span class="p">;</span> <span class="kn">use</span> <span class="n">Ada.Text_IO</span><span class="p">;</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-2" name="rest_code_0385449473644583a667a5b9631a4eb2-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-2"></a><span class="kd">procedure</span> <span class="nf">not_forever</span> <span class="kr">is</span> <span class="c1">-- recurse until stack space runs out.</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-3" name="rest_code_0385449473644583a667a5b9631a4eb2-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-3"></a> <span class="kd">type</span> <span class="kt">Unsigned</span> <span class="kr">is</span> <span class="ow">mod</span> <span class="mi">2</span><span class="o">**</span><span class="mi">64</span><span class="p">;</span> <span class="c1">-- wrap to 0 when maximum value is execeeded.</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-4" name="rest_code_0385449473644583a667a5b9631a4eb2-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-4"></a> <span class="n">i</span><span class="p">:</span> <span class="n">Unsigned</span> <span class="p">:=</span> <span class="mi">0</span><span class="p">;</span> <span class="c1">-- Number of times f has been called.</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-5" name="rest_code_0385449473644583a667a5b9631a4eb2-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-5"></a>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-6" name="rest_code_0385449473644583a667a5b9631a4eb2-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-6"></a> <span class="kd">procedure</span> <span class="nf">f</span> <span class="kr">is</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-7" name="rest_code_0385449473644583a667a5b9631a4eb2-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-7"></a> <span class="kr">begin</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-8" name="rest_code_0385449473644583a667a5b9631a4eb2-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-8"></a> <span class="n">i</span> <span class="p">:=</span> <span class="n">i</span> <span class="o">+</span> <span class="mi">1</span><span class="p">;</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-9" name="rest_code_0385449473644583a667a5b9631a4eb2-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-9"></a> <span class="n">f</span><span class="p">;</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-10" name="rest_code_0385449473644583a667a5b9631a4eb2-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-10"></a> <span class="kr">end</span> <span class="nf">f</span><span class="p">;</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-11" name="rest_code_0385449473644583a667a5b9631a4eb2-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-11"></a>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-12" name="rest_code_0385449473644583a667a5b9631a4eb2-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-12"></a><span class="kr">begin</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-13" name="rest_code_0385449473644583a667a5b9631a4eb2-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-13"></a> <span class="n">f</span><span class="p">;</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-14" name="rest_code_0385449473644583a667a5b9631a4eb2-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-14"></a><span class="kr">exception</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-15" name="rest_code_0385449473644583a667a5b9631a4eb2-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-15"></a> <span class="kr">when</span> <span class="n">STORAGE_ERROR</span> <span class="p">=></span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-16" name="rest_code_0385449473644583a667a5b9631a4eb2-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-16"></a> <span class="n">Put</span> <span class="p">(</span><span class="s">"STORAGE_ERROR raised with i = "</span><span class="p">);</span> <span class="n">Put</span> <span class="p">(</span><span class="n">i</span><span class="p">'</span><span class="na">Image</span><span class="p">);</span> <span class="n">New_Line</span><span class="p">;</span>
<a id="rest_code_0385449473644583a667a5b9631a4eb2-17" name="rest_code_0385449473644583a667a5b9631a4eb2-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0385449473644583a667a5b9631a4eb2-17"></a><span class="kr">end</span> <span class="nf">not_forever</span><span class="p">;</span>
</pre></div>
<p>Since <a class="reference external" href="https://en.wikipedia.org/wiki/Ada_(programming_language)">Ada</a> has exceptions, we actually catch the exception that
happens when the stack runs out of space:</p>
<pre class="literal-block">STORAGE_ERROR raised with i = 262002</pre>
<p>Again, <a class="reference external" href="https://en.wikipedia.org/wiki/Ada_(programming_language)">Ada</a> would have the same problem with <a class="reference external" href="https://en.wikipedia.org/wiki/Recursive_data_type">recursive type</a>s as
the Oberon dialects. Don't look at the C version and wander off into
forest of <code class="docutils literal">Ada.Unchecked_Conversion</code> because that's unsafe, or the
thicket of <code class="docutils literal">System.Address_To_Access_Conversions</code>, because that
one's also unsafe and more complicated (and the simple approach didn't
work, when I tried it). Instead, do the same thing as we did in the
Oberon dialects, and move to a global variable instead of returning
the values from the functions.</p>
<p>Here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/ada/trampoline.adb">trampoline.adb</a>:</p>
<div class="code"><pre class="code ada"><a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-1" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-1"></a><span class="kn">with</span> <span class="n">Ada.Text_IO</span><span class="p">;</span> <span class="kn">use</span> <span class="n">Ada.Text_IO</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-2" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-2"></a><span class="kd">procedure</span> <span class="nf">trampoline</span> <span class="kr">is</span> <span class="c1">-- Demonstrate lisp-style trampolines.</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-3" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-3"></a> <span class="kd">type</span> <span class="kt">Thunk</span> <span class="kr">is</span> <span class="kr">access</span> <span class="kd">procedure</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-4" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-4"></a>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-5" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-5"></a> <span class="n">Next</span><span class="p">:</span> <span class="n">Thunk</span> <span class="p">:=</span> <span class="kc">null</span><span class="p">;</span> <span class="c1">-- Next procedure to be called.</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-6" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-6"></a>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-7" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-7"></a> <span class="kd">procedure</span> <span class="nf">baz</span> <span class="kr">is</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-8" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-8"></a> <span class="kr">begin</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-9" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-9"></a> <span class="n">Put_Line</span> <span class="p">(</span><span class="s">"baz"</span><span class="p">);</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-10" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-10"></a> <span class="n">Next</span> <span class="p">:=</span> <span class="kc">null</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-11" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-11"></a> <span class="kr">end</span> <span class="nf">baz</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-12" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-12"></a>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-13" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-13"></a> <span class="kd">procedure</span> <span class="nf">bar</span> <span class="kr">is</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-14" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-14"></a> <span class="kr">begin</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-15" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-15"></a> <span class="n">Put_Line</span> <span class="p">(</span><span class="s">"bar"</span><span class="p">);</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-16" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-16"></a> <span class="n">Next</span> <span class="p">:=</span> <span class="n">baz</span><span class="p">'</span><span class="na">Access</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-17" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-17"></a> <span class="kr">end</span> <span class="nf">bar</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-18" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-18"></a>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-19" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-19" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-19"></a> <span class="kd">procedure</span> <span class="nf">foo</span> <span class="kr">is</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-20" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-20" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-20"></a> <span class="kr">begin</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-21" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-21" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-21"></a> <span class="n">Put_Line</span> <span class="p">(</span><span class="s">"foo"</span><span class="p">);</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-22" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-22" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-22"></a> <span class="n">Next</span> <span class="p">:=</span> <span class="n">bar</span><span class="p">'</span><span class="na">Access</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-23" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-23" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-23"></a> <span class="kr">end</span> <span class="nf">foo</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-24" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-24" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-24"></a>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-25" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-25" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-25"></a><span class="kr">begin</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-26" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-26" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-26"></a> <span class="n">next</span> <span class="p">:=</span> <span class="n">foo</span><span class="p">'</span><span class="na">Access</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-27" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-27" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-27"></a> <span class="kr">while</span> <span class="n">Next</span> <span class="o">/=</span> <span class="kc">null</span> <span class="kr">loop</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-28" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-28" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-28"></a> <span class="n">Next</span><span class="p">.</span><span class="kr">all</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-29" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-29" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-29"></a> <span class="kr">end</span> <span class="kr">loop</span><span class="p">;</span>
<a id="rest_code_5e205ea565214f0ca9bbc93c5b69458b-30" name="rest_code_5e205ea565214f0ca9bbc93c5b69458b-30" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_5e205ea565214f0ca9bbc93c5b69458b-30"></a><span class="kr">end</span> <span class="nf">trampoline</span><span class="p">;</span>
</pre></div>
<p>And here's <a class="reference external" href="https://tkurtbond.github.io/trampolines/ada/trampoline_forever.adb">trampoline_forever.adb</a>:</p>
<div class="code"><pre class="code ada"><a id="rest_code_0939bf7895c4454baad1d2782f3379de-1" name="rest_code_0939bf7895c4454baad1d2782f3379de-1" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-1"></a><span class="kn">with</span> <span class="n">Ada.Text_IO</span><span class="p">;</span> <span class="kn">use</span> <span class="n">Ada.Text_IO</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-2" name="rest_code_0939bf7895c4454baad1d2782f3379de-2" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-2"></a><span class="kd">procedure</span> <span class="nf">trampoline_forever</span> <span class="kr">is</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-3" name="rest_code_0939bf7895c4454baad1d2782f3379de-3" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-3"></a> <span class="c1">-- Recurse forever without running out of stack space.</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-4" name="rest_code_0939bf7895c4454baad1d2782f3379de-4" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-4"></a> <span class="kd">type</span> <span class="kt">Unsigned</span> <span class="kr">is</span> <span class="ow">mod</span> <span class="mi">2</span><span class="o">**</span><span class="mi">64</span><span class="p">;</span> <span class="c1">-- wrap to 0 when maximum value is execeeded.</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-5" name="rest_code_0939bf7895c4454baad1d2782f3379de-5" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-5"></a> <span class="n">i</span><span class="p">:</span> <span class="n">Unsigned</span> <span class="p">:=</span> <span class="mi">0</span><span class="p">;</span> <span class="c1">-- Number of times through the trampoline.</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-6" name="rest_code_0939bf7895c4454baad1d2782f3379de-6" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-6"></a>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-7" name="rest_code_0939bf7895c4454baad1d2782f3379de-7" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-7"></a> <span class="kd">type</span> <span class="kt">Thunk</span> <span class="kr">is</span> <span class="kr">access</span> <span class="kd">procedure</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-8" name="rest_code_0939bf7895c4454baad1d2782f3379de-8" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-8"></a>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-9" name="rest_code_0939bf7895c4454baad1d2782f3379de-9" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-9"></a> <span class="n">Next</span><span class="p">:</span> <span class="n">Thunk</span> <span class="p">:=</span> <span class="kc">null</span><span class="p">;</span> <span class="c1">-- Next procedure to be called.</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-10" name="rest_code_0939bf7895c4454baad1d2782f3379de-10" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-10"></a>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-11" name="rest_code_0939bf7895c4454baad1d2782f3379de-11" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-11"></a> <span class="kd">procedure</span> <span class="nf">foo</span><span class="p">;</span> <span class="c1">-- forward declaration.</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-12" name="rest_code_0939bf7895c4454baad1d2782f3379de-12" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-12"></a>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-13" name="rest_code_0939bf7895c4454baad1d2782f3379de-13" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-13"></a> <span class="kd">procedure</span> <span class="nf">baz</span> <span class="kr">is</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-14" name="rest_code_0939bf7895c4454baad1d2782f3379de-14" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-14"></a> <span class="kr">begin</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-15" name="rest_code_0939bf7895c4454baad1d2782f3379de-15" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-15"></a> <span class="n">Put_Line</span> <span class="p">(</span><span class="s">"baz"</span><span class="p">);</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-16" name="rest_code_0939bf7895c4454baad1d2782f3379de-16" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-16"></a> <span class="n">Next</span> <span class="p">:=</span> <span class="n">foo</span><span class="p">'</span><span class="na">access</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-17" name="rest_code_0939bf7895c4454baad1d2782f3379de-17" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-17"></a> <span class="kr">end</span> <span class="nf">baz</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-18" name="rest_code_0939bf7895c4454baad1d2782f3379de-18" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-18"></a>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-19" name="rest_code_0939bf7895c4454baad1d2782f3379de-19" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-19"></a> <span class="kd">procedure</span> <span class="nf">bar</span> <span class="kr">is</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-20" name="rest_code_0939bf7895c4454baad1d2782f3379de-20" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-20"></a> <span class="kr">begin</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-21" name="rest_code_0939bf7895c4454baad1d2782f3379de-21" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-21"></a> <span class="n">Put_Line</span> <span class="p">(</span><span class="s">"bar"</span><span class="p">);</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-22" name="rest_code_0939bf7895c4454baad1d2782f3379de-22" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-22"></a> <span class="n">Next</span> <span class="p">:=</span> <span class="n">baz</span><span class="p">'</span><span class="na">Access</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-23" name="rest_code_0939bf7895c4454baad1d2782f3379de-23" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-23"></a> <span class="kr">end</span> <span class="nf">bar</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-24" name="rest_code_0939bf7895c4454baad1d2782f3379de-24" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-24"></a>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-25" name="rest_code_0939bf7895c4454baad1d2782f3379de-25" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-25"></a> <span class="kd">procedure</span> <span class="nf">foo</span> <span class="kr">is</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-26" name="rest_code_0939bf7895c4454baad1d2782f3379de-26" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-26"></a> <span class="kr">begin</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-27" name="rest_code_0939bf7895c4454baad1d2782f3379de-27" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-27"></a> <span class="n">Put_Line</span> <span class="p">(</span><span class="s">"foo"</span><span class="p">);</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-28" name="rest_code_0939bf7895c4454baad1d2782f3379de-28" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-28"></a> <span class="n">Next</span> <span class="p">:=</span> <span class="n">bar</span><span class="p">'</span><span class="na">Access</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-29" name="rest_code_0939bf7895c4454baad1d2782f3379de-29" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-29"></a> <span class="kr">end</span> <span class="nf">foo</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-30" name="rest_code_0939bf7895c4454baad1d2782f3379de-30" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-30"></a>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-31" name="rest_code_0939bf7895c4454baad1d2782f3379de-31" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-31"></a><span class="kr">begin</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-32" name="rest_code_0939bf7895c4454baad1d2782f3379de-32" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-32"></a> <span class="n">next</span> <span class="p">:=</span> <span class="n">foo</span><span class="p">'</span><span class="na">Access</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-33" name="rest_code_0939bf7895c4454baad1d2782f3379de-33" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-33"></a> <span class="kr">while</span> <span class="n">Next</span> <span class="o">/=</span> <span class="kc">null</span> <span class="kr">loop</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-34" name="rest_code_0939bf7895c4454baad1d2782f3379de-34" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-34"></a> <span class="n">i</span> <span class="p">:=</span> <span class="n">i</span> <span class="o">+</span> <span class="mi">1</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-35" name="rest_code_0939bf7895c4454baad1d2782f3379de-35" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-35"></a> <span class="n">Put</span> <span class="p">(</span><span class="s">"call #"</span><span class="p">);</span> <span class="n">Put</span> <span class="p">(</span><span class="n">i</span><span class="p">'</span><span class="na">Image</span><span class="p">);</span> <span class="n">New_Line</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-36" name="rest_code_0939bf7895c4454baad1d2782f3379de-36" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-36"></a> <span class="n">Next</span><span class="p">.</span><span class="kr">all</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-37" name="rest_code_0939bf7895c4454baad1d2782f3379de-37" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-37"></a> <span class="kr">end</span> <span class="kr">loop</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-38" name="rest_code_0939bf7895c4454baad1d2782f3379de-38" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-38"></a><span class="kr">exception</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-39" name="rest_code_0939bf7895c4454baad1d2782f3379de-39" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-39"></a> <span class="kr">when</span> <span class="n">STORAGE_ERROR</span> <span class="p">=></span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-40" name="rest_code_0939bf7895c4454baad1d2782f3379de-40" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-40"></a> <span class="n">Put</span> <span class="p">(</span><span class="s">"STORAGE_ERROR raised with i = "</span><span class="p">);</span> <span class="n">Put</span> <span class="p">(</span><span class="n">i</span><span class="p">'</span><span class="na">Image</span><span class="p">);</span> <span class="n">New_Line</span><span class="p">;</span>
<a id="rest_code_0939bf7895c4454baad1d2782f3379de-41" name="rest_code_0939bf7895c4454baad1d2782f3379de-41" href="https://tkurtbond.github.io/posts/2022/06/14/lisp-style-trampolines-in-common-lisp-c-ada-oberon-2-and-revised-oberon/#rest_code_0939bf7895c4454baad1d2782f3379de-41"></a><span class="kr">end</span> <span class="nf">trampoline_forever</span><span class="p">;</span>
</pre></div>
<hr class="docutils">
<p>Of course, languages with more sophisticated type systems have other
ways of dealing with things, but I haven't investigated them. I did
stumble across an <a class="reference external" href="https://gist.github.com/rapha/119788">example</a> in OCaml (<a class="reference external" href="https://en.wikipedia.org/wiki/OCaml">OCAML1</a>, <a class="reference external" href="https://ocaml.org/">OCAML2</a>).</p>
<hr class="docutils">
<p>If you want to play around with this, the code is in a
<a class="reference external" href="https://github.com/tkurtbond/trampolines">repository</a> at <a class="reference external" href="https://github.com/">Github</a>.</p>
<!-- Local Variables:
time-stamp-format: "%Y-%02m-%02d %02H:%02M:%02S %Z"
time-stamp-start: "\\*Last edited:[ \t]+\\\\?"
time-stamp-end: "\\*\\\\?\n"
End: -->