mirror of
https://github.com/ganelson/inform.git
synced 2024-07-05 08:34:22 +03:00
1745 lines
244 KiB
HTML
1745 lines
244 KiB
HTML
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
|
|
<html>
|
|
<head>
|
|
<title>5/gv</title>
|
|
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
|
|
<meta http-equiv="Content-Language" content="en-gb">
|
|
<link href="inweb.css" rel="stylesheet" rev="stylesheet" type="text/css">
|
|
</head>
|
|
<body>
|
|
|
|
<!--Weave of '5/gl' generated by 7-->
|
|
<ul class="crumbs"><li><a href="../webs.html">★</a></li><li><a href="index.html">if</a></li><li><a href="index.html#5">Chapter 5: Command Grammar</a></li><li><b>Grammar Lines</b></li></ul><p class="purpose">A grammar line is a list of tokens to specify a textual pattern. For example, the NI source for a grammar line might be |"take [something] out"|, which is a sequence of three tokens.</p>
|
|
|
|
<ul class="toc"><li><a href="#SP1">§1. Definitions</a></li><li><a href="#SP5">§5. GL lists</a></li><li><a href="#SP6">§6. Two special forms of grammar lines</a></li><li><a href="#SP7">§7. Conditional lines</a></li><li><a href="#SP9">§9. Mistakes</a></li><li><a href="#SP10">§10. Single word optimisation</a></li><li><a href="#SP12">§12. Phase I: Slash Grammar</a></li><li><a href="#SP14">§14. Phase II: Determining Grammar</a></li><li><a href="#SP16">§16. Phase III: Sort Grammar</a></li><li><a href="#SP18">§18. Phase IV: Compile Grammar</a></li><li><a href="#SP22">§22. Indexing by grammar</a></li><li><a href="#SP23">§23. Indexing by action</a></li></ul><hr class="tocbar">
|
|
|
|
<p class="inwebparagraph"><a id="SP1"></a><b>§1. Definitions. </b></p>
|
|
|
|
<p class="inwebparagraph"><a id="SP2"></a><b>§2. </b>A grammar line is in turn a sequence of tokens. If it matches, it will
|
|
result in 0, 1 or 2 parameters, though only if the grammar verb owning
|
|
the line is a genuine <code class="display"><span class="extract">GV_IS_COMMAND</span></code> command grammar will the case of
|
|
2 parameters be possible. (This is for text matching, say, "put X in Y":
|
|
the objects X and Y are two parameters resulting.) And in that case (alone),
|
|
there will also be a <code class="display"><span class="extract">resulting_action</span></code>.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">A small amount of disjunction is allowed in a grammar line: for instance,
|
|
"look in/inside/into [something]" consists of five tokens, but only three
|
|
lexemes, basic units to be matched. (The first is "look", the second
|
|
is "one out of in, inside or into", and the third is an object in scope.)
|
|
In the following structure we cache the lexeme count since it is fiddly
|
|
to calculate, and useful when sorting grammar lines into applicability order.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">The individual tokens are stored simply as parse tree nodes of type
|
|
<code class="display"><span class="extract">TOKEN_NT</span></code>, and are the children of the node <code class="display"><span class="extract">gl->tokens</span></code>, which is why
|
|
(for now, anyway) there is no grammar token structure.
|
|
</p>
|
|
|
|
|
|
<pre class="definitions">
|
|
<span class="definitionkeyword">define</span> <span class="constant">UNCALCULATED_BONUS</span><span class="plain"> -1000000</span>
|
|
</pre>
|
|
|
|
<pre class="display">
|
|
<span class="reserved">typedef</span><span class="plain"> </span><span class="reserved">struct</span><span class="plain"> </span><span class="reserved">grammar_line</span><span class="plain"> {</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">next_line</span><span class="plain">; </span> <span class="comment">linked list in creation order</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">sorted_next_line</span><span class="plain">; </span> <span class="comment">and in applicability order</span>
|
|
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">where_grammar_specified</span><span class="plain">; </span> <span class="comment">where found in source</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">original_text</span><span class="plain">; </span> <span class="comment">the word number of the double-quoted grammar text...</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">tokens</span><span class="plain">; </span> <span class="comment">...which is parsed into this list of tokens</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">lexeme_count</span><span class="plain">; </span> <span class="comment">number of lexemes, or <code class="display"><span class="extract">-1</span></code> if not yet counted</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="identifier">wording</span><span class="plain"> </span><span class="identifier">understand_when_text</span><span class="plain">; </span> <span class="comment">only when this condition holds</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="identifier">pcalc_prop</span><span class="plain"> *</span><span class="identifier">understand_when_prop</span><span class="plain">; </span> <span class="comment">and when this condition holds</span>
|
|
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">pluralised</span><span class="plain">; </span> <span class="comment"><code class="display"><span class="extract">GV_IS_OBJECT</span></code>: refers in the plural</span>
|
|
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="reserved">action_name</span><span class="plain"> *</span><span class="identifier">resulting_action</span><span class="plain">; </span> <span class="comment"><code class="display"><span class="extract">GV_IS_COMMAND</span></code>: the action</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">reversed</span><span class="plain">; </span> <span class="comment"><code class="display"><span class="extract">GV_IS_COMMAND</span></code>: the two arguments are in reverse order</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">mistaken</span><span class="plain">; </span> <span class="comment"><code class="display"><span class="extract">GV_IS_COMMAND</span></code>: is this understood as a mistake?</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="identifier">wording</span><span class="plain"> </span><span class="identifier">mistake_response_text</span><span class="plain">; </span> <span class="comment">if so, reply thus</span>
|
|
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="reserved">grammar_type</span><span class="plain"> </span><span class="identifier">gl_type</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">suppress_compilation</span><span class="plain">; </span> <span class="comment">has been compiled in a single I6 grammar token already?</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">next_with_action</span><span class="plain">; </span> <span class="comment">used when indexing actions</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="reserved">grammar_verb</span><span class="plain"> *</span><span class="identifier">belongs_to_gv</span><span class="plain">; </span> <span class="comment">similarly, used only in indexing</span>
|
|
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="identifier">inter_name</span><span class="plain"> *</span><span class="identifier">cond_token_iname</span><span class="plain">; </span> <span class="comment">for its <code class="display"><span class="extract">Cond_Token_*</span></code> routine, if any</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="identifier">inter_name</span><span class="plain"> *</span><span class="identifier">mistake_iname</span><span class="plain">; </span> <span class="comment">for its <code class="display"><span class="extract">Mistake_Token_*</span></code> routine, if any</span>
|
|
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">general_sort_bonus</span><span class="plain">; </span> <span class="comment">temporary values used in grammar line sorting</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">understanding_sort_bonus</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">MEMORY_MANAGEMENT</span>
|
|
<span class="plain">} </span><span class="reserved">grammar_line</span><span class="plain">;</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The structure grammar_line is accessed in 5/tfg and here.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP3"></a><b>§3. </b></p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">typedef</span><span class="plain"> </span><span class="reserved">struct</span><span class="plain"> </span><span class="reserved">slash_gpr</span><span class="plain"> {</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">first_choice</span><span class="plain">;</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">last_choice</span><span class="plain">;</span>
|
|
<span class="reserved">struct</span><span class="plain"> </span><span class="identifier">inter_name</span><span class="plain"> *</span><span class="identifier">sgpr_iname</span><span class="plain">;</span>
|
|
<span class="identifier">MEMORY_MANAGEMENT</span>
|
|
<span class="plain">} </span><span class="reserved">slash_gpr</span><span class="plain">;</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The structure slash_gpr is private to this section.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP4"></a><b>§4. </b></p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="functiontext">PL::Parsing::Lines::new</span><span class="plain">(</span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">wn</span><span class="plain">, </span><span class="reserved">action_name</span><span class="plain"> *</span><span class="identifier">ac</span><span class="plain">,</span>
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">token_list</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">reversed</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">pluralised</span><span class="plain">) {</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">CREATE</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain">);</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>original_text</span><span class="plain"> = </span><span class="identifier">wn</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>resulting_action</span><span class="plain"> = </span><span class="identifier">ac</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>belongs_to_gv</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">ac</span><span class="plain"> != </span><span class="identifier">NULL</span><span class="plain">) </span><span class="functiontext">PL::Actions::add_gl</span><span class="plain">(</span><span class="identifier">ac</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistake_response_text</span><span class="plain"> = </span><span class="identifier">EMPTY_WORDING</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>next_with_action</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain"> = </span><span class="identifier">token_list</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>where_grammar_specified</span><span class="plain"> = </span><span class="identifier">current_sentence</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>gl_type</span><span class="plain"> = </span><span class="functiontext">PL::Parsing::Tokens::Types::new</span><span class="plain">(</span><span class="identifier">TRUE</span><span class="plain">);</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain"> = -1; </span> <span class="comment">no count made as yet</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>reversed</span><span class="plain"> = </span><span class="identifier">reversed</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>pluralised</span><span class="plain"> = </span><span class="identifier">pluralised</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>understand_when_text</span><span class="plain"> = </span><span class="identifier">EMPTY_WORDING</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>understand_when_prop</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>suppress_compilation</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain"> = </span><span class="constant">UNCALCULATED_BONUS</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>understanding_sort_bonus</span><span class="plain"> = </span><span class="constant">UNCALCULATED_BONUS</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>cond_token_iname</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistake_iname</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::log</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">) {</span>
|
|
<span class="identifier">LOG</span><span class="plain">(</span><span class="string">"<GL%d:%W>"</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">-></span><span class="identifier">allocation_id</span><span class="plain">, </span><span class="identifier">ParseTree::get_text</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">));</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::set_single_type</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">gl_value</span><span class="plain">) {</span>
|
|
<span class="functiontext">PL::Parsing::Tokens::Types::set_single_type</span><span class="plain">(&(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>gl_type</span><span class="plain">), </span><span class="identifier">gl_value</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::new is used in 5/tfg (<a href="5-tfg.html#SP21">§21</a>).</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::log is used in 1/im (<a href="1-im.html#SP4">§4</a>, <a href="1-im.html#SP4_4">§4.4</a>).</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::set_single_type is used in 5/tfg (<a href="5-tfg.html#SP21">§21</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP5"></a><b>§5. GL lists. </b>Grammar lines are themselves generally stored in linked lists (belonging,
|
|
for instance, to a GV). Here we add a GL to the back of a list.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::list_length</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">) {</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">c</span><span class="plain"> = 0;</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">posn</span><span class="plain">;</span>
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">posn</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">; </span><span class="identifier">posn</span><span class="plain">; </span><span class="identifier">posn</span><span class="plain"> = </span><span class="identifier">posn</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">) </span><span class="identifier">c</span><span class="plain">++;</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">c</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="functiontext">PL::Parsing::Lines::list_add</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">new_gl</span><span class="plain">) {</span>
|
|
<span class="identifier">new_gl</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">list_head</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) </span><span class="identifier">list_head</span><span class="plain"> = </span><span class="identifier">new_gl</span><span class="plain">;</span>
|
|
<span class="reserved">else</span><span class="plain"> {</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">posn</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">;</span>
|
|
<span class="reserved">while</span><span class="plain"> (</span><span class="identifier">posn</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">) </span><span class="identifier">posn</span><span class="plain"> = </span><span class="identifier">posn</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">;</span>
|
|
<span class="identifier">posn</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain"> = </span><span class="identifier">new_gl</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">list_head</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="functiontext">PL::Parsing::Lines::list_remove</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">, </span><span class="reserved">action_name</span><span class="plain"> *</span><span class="identifier">find</span><span class="plain">) {</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">prev</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">, *</span><span class="identifier">posn</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">;</span>
|
|
<span class="reserved">while</span><span class="plain"> (</span><span class="identifier">posn</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">posn</span><span class="plain">-</span><span class="element">>resulting_action</span><span class="plain"> == </span><span class="identifier">find</span><span class="plain">) {</span>
|
|
<span class="identifier">LOGIF</span><span class="plain">(</span><span class="identifier">GRAMMAR_CONSTRUCTION</span><span class="plain">, </span><span class="string">"Removing grammar line: $g\</span><span class="plain">n</span><span class="string">"</span><span class="plain">, </span><span class="identifier">posn</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">prev</span><span class="plain">) </span><span class="identifier">prev</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain"> = </span><span class="identifier">posn</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">;</span>
|
|
<span class="reserved">else</span><span class="plain"> </span><span class="identifier">list_head</span><span class="plain"> = </span><span class="identifier">posn</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">;</span>
|
|
<span class="plain">} </span><span class="reserved">else</span><span class="plain"> {</span>
|
|
<span class="identifier">prev</span><span class="plain"> = </span><span class="identifier">posn</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">posn</span><span class="plain"> = </span><span class="identifier">posn</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">list_head</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::list_length is used in 5/gv (<a href="5-gv.html#SP20">§20</a>).</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::list_add is used in 5/gv (<a href="5-gv.html#SP20">§20</a>).</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::list_remove is used in 5/gv (<a href="5-gv.html#SP9">§9</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP6"></a><b>§6. Two special forms of grammar lines. </b>GLs can have either or both of two orthogonal special forms: they can be
|
|
mistaken or conditional. (Mistakes only occur in command grammars, but
|
|
conditional GLs can occur in any grammar.) GLs of this kind need special
|
|
support, in that I6 general parsing routines need to be compiled for them
|
|
to use as tokens: here's where that support is provided. The following
|
|
step needs to take place before the command grammar (I6 <code class="display"><span class="extract">Verb</span></code> directives,
|
|
etc.) is compiled because of I6's requirement that all GPRs be defined
|
|
as routines prior to the <code class="display"><span class="extract">Verb</span></code> directive using them.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::line_list_compile_condition_tokens</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">) {</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">) {</span>
|
|
<span class="functiontext">PL::Parsing::Lines::gl_compile_condition_token_as_needed</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">);</span>
|
|
<span class="functiontext">PL::Parsing::Lines::gl_compile_mistake_token_as_needed</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::line_list_compile_condition_tokens is used in 5/gv (<a href="5-gv.html#SP22">§22</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP7"></a><b>§7. Conditional lines. </b>Some grammar lines take effect only when some circumstance holds: most I7
|
|
conditions are valid to specify this, with the notation "Understand ... as
|
|
... when ...". However, we want to protect new authors from mistakes
|
|
like this:
|
|
</p>
|
|
|
|
<blockquote>
|
|
<p>Understand "mate" as Fred when asking Fred to do something: ...</p>
|
|
|
|
</blockquote>
|
|
|
|
<p class="inwebparagraph">where the condition couldn't test anything useful because it's not yet
|
|
known what the action will be.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="plain"><</span><span class="identifier">understand</span><span class="plain">-</span><span class="identifier">condition</span><span class="plain">> ::=</span>
|
|
<span class="plain"><</span><span class="identifier">s</span><span class="plain">-</span><span class="identifier">non</span><span class="plain">-</span><span class="identifier">action</span><span class="plain">-</span><span class="identifier">condition</span><span class="plain">> | ==> 0; <<</span><span class="identifier">parse_node</span><span class="plain">:</span><span class="identifier">cond</span><span class="plain">>> = </span><span class="identifier">RP</span><span class="plain">[1];</span>
|
|
<span class="plain"><</span><span class="identifier">s</span><span class="plain">-</span><span class="identifier">condition</span><span class="plain">> | ==> </span><<span class="cwebmacro">Issue PM_WhenAction problem</span> <span class="cwebmacronumber">7.1</span>>
|
|
<span class="plain">... ==> </span><<span class="cwebmacro">Issue PM_BadWhen problem</span> <span class="cwebmacronumber">7.2</span>><span class="plain">;</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="inwebparagraph"><a id="SP7_1"></a><b>§7.1. </b><code class="display">
|
|
<<span class="cwebmacrodefn">Issue PM_WhenAction problem</span> <span class="cwebmacronumber">7.1</span>> =
|
|
</code></p>
|
|
|
|
|
|
<pre class="displaydefn">
|
|
<span class="identifier">Problems::Issue::sentence_problem</span><span class="plain">(</span><span class="identifier">_p_</span><span class="plain">(</span><span class="identifier">PM_WhenAction</span><span class="plain">),</span>
|
|
<span class="string">"the condition after 'when' involves the current action"</span><span class="plain">,</span>
|
|
<span class="string">"but this can never work, because when Inform is still trying to "</span>
|
|
<span class="string">"understand a command, the current action isn't yet decided on."</span><span class="plain">);</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">This code is used in <a href="#SP7">§7</a>.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP7_2"></a><b>§7.2. </b><code class="display">
|
|
<<span class="cwebmacrodefn">Issue PM_BadWhen problem</span> <span class="cwebmacronumber">7.2</span>> =
|
|
</code></p>
|
|
|
|
|
|
<pre class="displaydefn">
|
|
<span class="identifier">Problems::Issue::sentence_problem</span><span class="plain">(</span><span class="identifier">_p_</span><span class="plain">(</span><span class="identifier">PM_BadWhen</span><span class="plain">),</span>
|
|
<span class="string">"the condition after 'when' makes no sense to me"</span><span class="plain">,</span>
|
|
<span class="string">"although otherwise this worked - it is only the part after 'when' "</span>
|
|
<span class="string">"which I can't follow."</span><span class="plain">);</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">This code is used in <a href="#SP7">§7</a>, <a href="#SP8">§8</a>.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP8"></a><b>§8. </b>Such GLs have an "understand when" set, as follows.
|
|
They compile preceded by a match-no-text token which matches correctly
|
|
if the condition holds and incorrectly if it fails. For instance, for
|
|
a command grammar, we might have:
|
|
</p>
|
|
|
|
<p class="inwebparagraph"><code class="display"><span class="extract">* Cond_Token_26 'draw' noun -> Draw</span></code>
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::set_understand_when</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">wording</span><span class="plain"> </span><span class="identifier">W</span><span class="plain">) {</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>understand_when_text</span><span class="plain"> = </span><span class="identifier">W</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::set_understand_prop</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">pcalc_prop</span><span class="plain"> *</span><span class="identifier">prop</span><span class="plain">) {</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>understand_when_prop</span><span class="plain"> = </span><span class="identifier">prop</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::conditional</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">Wordings::nonempty</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>understand_when_text</span><span class="plain">)) || (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>understand_when_prop</span><span class="plain">))</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::gl_compile_condition_token_as_needed</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="functiontext">PL::Parsing::Lines::conditional</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">)) {</span>
|
|
<span class="identifier">current_sentence</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>where_grammar_specified</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">package_request</span><span class="plain"> *</span><span class="identifier">PR</span><span class="plain"> = </span><span class="identifier">Hierarchy::local_package</span><span class="plain">(</span><span class="identifier">COND_TOKENS_HAP</span><span class="plain">);</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>cond_token_iname</span><span class="plain"> = </span><span class="identifier">Hierarchy::make_iname_in</span><span class="plain">(</span><span class="identifier">CONDITIONAL_TOKEN_FN_HL</span><span class="plain">, </span><span class="identifier">PR</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">packaging_state</span><span class="plain"> </span><span class="identifier">save</span><span class="plain"> = </span><span class="identifier">Routines::begin</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>cond_token_iname</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">spec</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">Wordings::nonempty</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>understand_when_text</span><span class="plain">)) {</span>
|
|
<span class="identifier">current_sentence</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>where_grammar_specified</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (<</span><span class="identifier">understand</span><span class="plain">-</span><span class="identifier">condition</span><span class="plain">>(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>understand_when_text</span><span class="plain">)) {</span>
|
|
<span class="identifier">spec</span><span class="plain"> = <<</span><span class="identifier">parse_node</span><span class="plain">:</span><span class="identifier">cond</span><span class="plain">>>;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">Dash::validate_conditional_clause</span><span class="plain">(</span><span class="identifier">spec</span><span class="plain">) == </span><span class="identifier">FALSE</span><span class="plain">) {</span>
|
|
<<span class="cwebmacro">Issue PM_BadWhen problem</span> <span class="cwebmacronumber">7.2</span>><span class="plain">;</span>
|
|
<span class="identifier">spec</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">pcalc_prop</span><span class="plain"> *</span><span class="identifier">prop</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>understand_when_prop</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">spec</span><span class="plain">) || (</span><span class="identifier">prop</span><span class="plain">)) {</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">IF_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">spec</span><span class="plain">) && (</span><span class="identifier">prop</span><span class="plain">)) {</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">AND_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">spec</span><span class="plain">) </span><span class="identifier">Specifications::Compiler::emit_as_val</span><span class="plain">(</span><span class="identifier">K_truth_state</span><span class="plain">, </span><span class="identifier">spec</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">prop</span><span class="plain">) </span><span class="identifier">Calculus::Deferrals::emit_test_of_proposition</span><span class="plain">(</span><span class="identifier">Rvalues::new_self_object_constant</span><span class="plain">(), </span><span class="identifier">prop</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">spec</span><span class="plain">) && (</span><span class="identifier">prop</span><span class="plain">)) {</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">Produce::code</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">RETURN_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">GPR_PREPOSITION_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">RETURN_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">GPR_FAIL_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
|
|
<span class="identifier">Routines::end</span><span class="plain">(</span><span class="identifier">save</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::gl_compile_extra_token_for_condition</span><span class="plain">(</span><span class="reserved">gpr_kit</span><span class="plain"> *</span><span class="identifier">gprk</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">,</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">gv_is</span><span class="plain">, </span><span class="identifier">inter_symbol</span><span class="plain"> *</span><span class="identifier">current_label</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="functiontext">PL::Parsing::Lines::conditional</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">)) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>cond_token_iname</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) </span><span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"GL cond token not ready"</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gv_is</span><span class="plain"> == </span><span class="constant">GV_IS_COMMAND</span><span class="plain">) {</span>
|
|
<span class="identifier">Emit::array_iname_entry</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>cond_token_iname</span><span class="plain">);</span>
|
|
<span class="plain">} </span><span class="reserved">else</span><span class="plain"> {</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">IF_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">EQ_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_call_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>cond_token_iname</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">GPR_FAIL_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::code</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">JUMP_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::lab</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">current_label</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::set_understand_when is used in 5/tfg (<a href="5-tfg.html#SP21">§21</a>).</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::set_understand_prop is used in 5/tfg (<a href="5-tfg.html#SP21">§21</a>).</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::conditional is used in <a href="#SP10">§10</a>, <a href="#SP17">§17</a>.</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::gl_compile_condition_token_as_needed is used in <a href="#SP6">§6</a>.</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::gl_compile_extra_token_for_condition is used in <a href="#SP20">§20</a>.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP9"></a><b>§9. Mistakes. </b>These are grammar lines used in command GVs for commands which are accepted
|
|
but only in order to print nicely worded rejections. A number of schemes
|
|
were tried for this, for instance producing parser errors and setting <code class="display"><span class="extract">pe</span></code>
|
|
to some high value, but the method now used is for a mistaken line to
|
|
produce a successful parse at the I6 level, resulting in the (I6 only)
|
|
action <code class="display"><span class="extract">##MistakeAction</span></code>. The tricky part is to send information to the
|
|
I6 action routine <code class="display"><span class="extract">MistakeActionSub</span></code> indicating what the mistake was,
|
|
exactly: we do this by including, in the I6 grammar, a token which
|
|
matches empty text and returns a "preposition", so that it has no
|
|
direct result, but which also sets a special global variable as a
|
|
side-effect. Thus a mistaken line "act [thing]" comes out as something
|
|
like:
|
|
</p>
|
|
|
|
<p class="inwebparagraph"><code class="display"><span class="extract">* Mistake_Token_12 'act' noun -> MistakeAction</span></code>
|
|
</p>
|
|
|
|
<p class="inwebparagraph">Since the I6 parser accepts the first command which matches, and since
|
|
none of this can be recursive, the value of this variable at the end of
|
|
I6 parsing is guaranteed to be the one set during the line causing
|
|
the mistake.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::set_mistake</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">wn</span><span class="plain">) {</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistake_response_text</span><span class="plain"> = </span><span class="identifier">Wordings::one_word</span><span class="plain">(</span><span class="identifier">wn</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistake_iname</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) {</span>
|
|
<span class="identifier">package_request</span><span class="plain"> *</span><span class="identifier">PR</span><span class="plain"> = </span><span class="identifier">Hierarchy::local_package</span><span class="plain">(</span><span class="identifier">MISTAKES_HAP</span><span class="plain">);</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistake_iname</span><span class="plain"> = </span><span class="identifier">Hierarchy::make_iname_in</span><span class="plain">(</span><span class="identifier">MISTAKE_FN_HL</span><span class="plain">, </span><span class="identifier">PR</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::gl_compile_mistake_token_as_needed</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain">) {</span>
|
|
<span class="identifier">packaging_state</span><span class="plain"> </span><span class="identifier">save</span><span class="plain"> = </span><span class="identifier">Routines::begin</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistake_iname</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">IF_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">NE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_object</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">ACTOR_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_object</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">PLAYER_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::code</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">RETURN_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">GPR_FAIL_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_number</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">UNDERSTAND_AS_MISTAKE_NUMBER_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::val</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_number</span><span class="plain">, </span><span class="identifier">LITERAL_IVAL</span><span class="plain">, (</span><span class="identifier">inter_t</span><span class="plain">) (100 + </span><span class="identifier">gl</span><span class="plain">-></span><span class="identifier">allocation_id</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">RETURN_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">GPR_PREPOSITION_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
|
|
<span class="identifier">Routines::end</span><span class="plain">(</span><span class="identifier">save</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::gl_compile_extra_token_for_mistake</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">gv_is</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gv_is</span><span class="plain"> == </span><span class="constant">GV_IS_COMMAND</span><span class="plain">) {</span>
|
|
<span class="identifier">Emit::array_iname_entry</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistake_iname</span><span class="plain">);</span>
|
|
<span class="plain">} </span><span class="reserved">else</span>
|
|
<span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"GLs may only be mistaken in command grammar"</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">inter_name</span><span class="plain"> *</span><span class="identifier">MistakeAction_iname</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::gl_compile_result_of_mistake</span><span class="plain">(</span><span class="reserved">gpr_kit</span><span class="plain"> *</span><span class="identifier">gprk</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">MistakeAction_iname</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) </span><span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"no MistakeAction yet"</span><span class="plain">);</span>
|
|
<span class="identifier">Emit::array_iname_entry</span><span class="plain">(</span><span class="identifier">VERB_DIRECTIVE_RESULT_iname</span><span class="plain">);</span>
|
|
<span class="identifier">Emit::array_iname_entry</span><span class="plain">(</span><span class="identifier">MistakeAction_iname</span><span class="plain">);</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::MistakeActionSub_routine</span><span class="plain">(</span><span class="reserved">void</span><span class="plain">) {</span>
|
|
<span class="identifier">package_request</span><span class="plain"> *</span><span class="identifier">MAP</span><span class="plain"> = </span><span class="identifier">Hierarchy::synoptic_package</span><span class="plain">(</span><span class="identifier">SACTIONS_HAP</span><span class="plain">);</span>
|
|
<span class="identifier">packaging_state</span><span class="plain"> </span><span class="identifier">save</span><span class="plain"> = </span><span class="identifier">Routines::begin</span><span class="plain">(</span><span class="identifier">Hierarchy::make_iname_in</span><span class="plain">(</span><span class="identifier">MISTAKEACTIONSUB_HL</span><span class="plain">, </span><span class="identifier">MAP</span><span class="plain">));</span>
|
|
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">SWITCH_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">UNDERSTAND_AS_MISTAKE_NUMBER_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::code</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="identifier">LOOP_OVER</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain">)</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">Wordings::nonempty</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistake_response_text</span><span class="plain">)) {</span>
|
|
<span class="identifier">current_sentence</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>where_grammar_specified</span><span class="plain">;</span>
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">spec</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (<</span><span class="identifier">s</span><span class="plain">-</span><span class="identifier">value</span><span class="plain">>(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistake_response_text</span><span class="plain">))</span>
|
|
<span class="identifier">spec</span><span class="plain"> = <<</span><span class="identifier">rp</span><span class="plain">>>;</span>
|
|
<span class="reserved">else</span><span class="plain"> </span><span class="identifier">spec</span><span class="plain"> = </span><span class="identifier">Specifications::new_UNKNOWN</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>mistake_response_text</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">CASE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_number</span><span class="plain">, </span><span class="identifier">LITERAL_IVAL</span><span class="plain">, (</span><span class="identifier">inter_t</span><span class="plain">) (100+</span><span class="identifier">gl</span><span class="plain">-></span><span class="identifier">allocation_id</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::code</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_call_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">PARSERERROR_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Specifications::Compiler::emit_constant_to_kind_as_val</span><span class="plain">(</span><span class="identifier">spec</span><span class="plain">, </span><span class="identifier">K_text</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">DEFAULT_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::code</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">PRINT_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_text</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">I</span><span class="string">"I didn't understand that sentence.\</span><span class="plain">n</span><span class="string">"</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::rtrue</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_number</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">SAY__P_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::val</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_number</span><span class="plain">, </span><span class="identifier">LITERAL_IVAL</span><span class="plain">, 1);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
|
|
<span class="identifier">Routines::end</span><span class="plain">(</span><span class="identifier">save</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">MistakeAction_iname</span><span class="plain"> = </span><span class="identifier">Hierarchy::make_iname_in</span><span class="plain">(</span><span class="identifier">MISTAKEACTION_HL</span><span class="plain">, </span><span class="identifier">MAP</span><span class="plain">);</span>
|
|
<span class="identifier">Emit::named_pseudo_numeric_constant</span><span class="plain">(</span><span class="identifier">MistakeAction_iname</span><span class="plain">, </span><span class="identifier">K_action_name</span><span class="plain">, 10000);</span>
|
|
<span class="identifier">Produce::annotate_i</span><span class="plain">(</span><span class="identifier">MistakeAction_iname</span><span class="plain">, </span><span class="identifier">ACTION_IANN</span><span class="plain">, 1);</span>
|
|
<span class="identifier">Hierarchy::make_available</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">MistakeAction_iname</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::set_mistake is used in 5/tfg (<a href="5-tfg.html#SP21">§21</a>).</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::gl_compile_mistake_token_as_needed is used in <a href="#SP6">§6</a>.</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::gl_compile_extra_token_for_mistake is used in <a href="#SP20">§20</a>.</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::gl_compile_result_of_mistake is used in <a href="#SP20">§20</a>.</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::MistakeActionSub_routine appears nowhere else.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP10"></a><b>§10. Single word optimisation. </b>The grammars used to parse names of objects are normally compiled into
|
|
<code class="display"><span class="extract">parse_name</span></code> routines. But the I6 parser also uses the <code class="display"><span class="extract">name</span></code> property,
|
|
and it is advantageous to squeeze as much as possible into <code class="display"><span class="extract">name</span></code> and
|
|
as little as possible into <code class="display"><span class="extract">parse_name</span></code>. The only possible candidates
|
|
are grammar lines consisting of single unconditional words, as detected
|
|
by the following routine:
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::gl_contains_single_unconditional_word</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">) {</span>
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">-></span><span class="identifier">down</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">pn</span><span class="plain">)</span>
|
|
<span class="plain">&& (</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">)</span>
|
|
<span class="plain">&& (</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">) == 0)</span>
|
|
<span class="plain">&& (</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">grammar_token_literal_ANNOT</span><span class="plain">))</span>
|
|
<span class="plain">&& (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>pluralised</span><span class="plain"> == </span><span class="identifier">FALSE</span><span class="plain">)</span>
|
|
<span class="plain">&& (</span><span class="functiontext">PL::Parsing::Lines::conditional</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">) == </span><span class="identifier">FALSE</span><span class="plain">))</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">Wordings::first_wn</span><span class="plain">(</span><span class="identifier">ParseTree::get_text</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">));</span>
|
|
<span class="reserved">return</span><span class="plain"> -1;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::gl_contains_single_unconditional_word is used in <a href="#SP11">§11</a>.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP11"></a><b>§11. </b>This routine looks through a GL list and marks to suppress all those
|
|
GLs consisting only of single unconditional words, which means they
|
|
will not be compiled into a <code class="display"><span class="extract">parse_name</span></code> routine (or anywhere else).
|
|
If the <code class="display"><span class="extract">of</span></code> file handle is set, then the words in question are printed
|
|
as I6-style dictionary words to it. In practice, this is done when
|
|
compiling the <code class="display"><span class="extract">name</span></code> property, so that a single scan achieves both
|
|
the transfer into <code class="display"><span class="extract">name</span></code> and the exclusion from <code class="display"><span class="extract">parse_name</span></code> of
|
|
affected GLs.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="functiontext">PL::Parsing::Lines::list_take_out_one_word_grammar</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">) {</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">, *</span><span class="identifier">glp</span><span class="plain">;</span>
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">, </span><span class="identifier">glp</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">) {</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">wn</span><span class="plain"> = </span><span class="functiontext">PL::Parsing::Lines::gl_contains_single_unconditional_word</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">wn</span><span class="plain"> >= 0) {</span>
|
|
<span class="identifier">TEMPORARY_TEXT</span><span class="plain">(</span><span class="identifier">content</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE_TO</span><span class="plain">(</span><span class="identifier">content</span><span class="plain">, </span><span class="string">"%w"</span><span class="plain">, </span><span class="identifier">Lexer::word_text</span><span class="plain">(</span><span class="identifier">wn</span><span class="plain">));</span>
|
|
<span class="identifier">Emit::array_dword_entry</span><span class="plain">(</span><span class="identifier">content</span><span class="plain">);</span>
|
|
<span class="identifier">DISCARD_TEXT</span><span class="plain">(</span><span class="identifier">content</span><span class="plain">);</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>suppress_compilation</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="plain">} </span><span class="reserved">else</span><span class="plain"> </span><span class="identifier">glp</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">list_head</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::list_take_out_one_word_grammar is used in 5/gv (<a href="5-gv.html#SP17">§17</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP12"></a><b>§12. Phase I: Slash Grammar. </b>Slashing is an activity carried out on a per-grammar-line basis, so to slash
|
|
a list of GLs we simply slash each GL in turn.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::line_list_slash</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl_head</span><span class="plain">) {</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl_head</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">) {</span>
|
|
<span class="functiontext">PL::Parsing::Lines::slash_grammar_line</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::line_list_slash is used in 5/gv (<a href="5-gv.html#SP24">§24</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP13"></a><b>§13. </b>Now the actual slashing process, which does not descend to tokens. We
|
|
remove any slashes, and fill in positive numbers in the <code class="display"><span class="extract">qualifier</span></code> field
|
|
corresponding to non-singleton equivalence classes. Thus "take up/in all
|
|
washing/laundry/linen" begins as 10 tokens, three of them forward slashes,
|
|
and ends as 7 tokens, with <code class="display"><span class="extract">qualifier</span></code> values 0, 1, 1, 0, 2, 2, 2, for
|
|
four equivalence classes in turn. Each equivalence class is one lexical
|
|
unit, or "lexeme", so the lexeme count is then 4.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">In addition, if one of the slashed options is "--", then this means the
|
|
empty word, and is removed from the token list; but the first token of the
|
|
lexeme is annotated accordingly.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::slash_grammar_line</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">) {</span>
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">pn</span><span class="plain">;</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">alternatives_group</span><span class="plain"> = 0;</span>
|
|
|
|
<span class="identifier">current_sentence</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>where_grammar_specified</span><span class="plain">; </span> <span class="comment">to report problems</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">)</span>
|
|
<span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"Null tokens on grammar"</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">LOGIF</span><span class="plain">(</span><span class="identifier">GRAMMAR_CONSTRUCTION</span><span class="plain">, </span><span class="string">"Preparing grammar line:\</span><span class="plain">n</span><span class="string">$T"</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">);</span>
|
|
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">-></span><span class="identifier">down</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">)</span>
|
|
<span class="identifier">ParseTree::annotate_int</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">, 0);</span>
|
|
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">class_start</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">-></span><span class="identifier">down</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) &&</span>
|
|
<span class="plain">(</span><span class="identifier">Wordings::length</span><span class="plain">(</span><span class="identifier">ParseTree::get_text</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">)) == 1) &&</span>
|
|
<span class="plain">(</span><span class="identifier">Lexer::word</span><span class="plain">(</span><span class="identifier">Wordings::first_wn</span><span class="plain">(</span><span class="identifier">ParseTree::get_text</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">))) == </span><span class="identifier">FORWARDSLASH_V</span><span class="plain">)) { </span> <span class="comment">slash follows:</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">) == 0) {</span>
|
|
<span class="identifier">class_start</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">; </span><span class="identifier">alternatives_group</span><span class="plain">++; </span> <span class="comment">start new equiv class</span>
|
|
<span class="identifier">ParseTree::annotate_int</span><span class="plain">(</span><span class="identifier">class_start</span><span class="plain">, </span><span class="identifier">slash_dash_dash_ANNOT</span><span class="plain">, </span><span class="identifier">FALSE</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">ParseTree::annotate_int</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">,</span>
|
|
<span class="identifier">alternatives_group</span><span class="plain">); </span> <span class="comment">make two sides of slash equiv</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">-</span><span class="element">>next</span><span class="plain">)</span>
|
|
<span class="identifier">ParseTree::annotate_int</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">-</span><span class="element">>next</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">, </span><span class="identifier">alternatives_group</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) &&</span>
|
|
<span class="plain">(</span><span class="identifier">Wordings::length</span><span class="plain">(</span><span class="identifier">ParseTree::get_text</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">-</span><span class="element">>next</span><span class="plain">)) == 1) &&</span>
|
|
<span class="plain">(</span><span class="identifier">Lexer::word</span><span class="plain">(</span><span class="identifier">Wordings::first_wn</span><span class="plain">(</span><span class="identifier">ParseTree::get_text</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">-</span><span class="element">>next</span><span class="plain">))) == </span><span class="identifier">DOUBLEDASH_V</span><span class="plain">)) { </span> <span class="comment">— follows:</span>
|
|
<span class="identifier">ParseTree::annotate_int</span><span class="plain">(</span><span class="identifier">class_start</span><span class="plain">, </span><span class="identifier">slash_dash_dash_ANNOT</span><span class="plain">, </span><span class="identifier">TRUE</span><span class="plain">);</span>
|
|
<span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">-</span><span class="element">>next</span><span class="plain">-</span><span class="element">>next</span><span class="plain">; </span> <span class="comment">excise slash and dash-dash</span>
|
|
<span class="plain">} </span><span class="reserved">else</span><span class="plain"> {</span>
|
|
<span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">-</span><span class="element">>next</span><span class="plain">; </span> <span class="comment">excise the slash from the token list</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">LOGIF</span><span class="plain">(</span><span class="identifier">GRAMMAR_CONSTRUCTION</span><span class="plain">, </span><span class="string">"Regrouped as:\</span><span class="plain">n</span><span class="string">$T"</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">);</span>
|
|
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">-></span><span class="identifier">down</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">)</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">) > 0) &&</span>
|
|
<span class="plain">(</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">grammar_token_literal_ANNOT</span><span class="plain">) == </span><span class="identifier">FALSE</span><span class="plain">)) {</span>
|
|
<span class="identifier">Problems::Issue::sentence_problem</span><span class="plain">(</span><span class="identifier">_p_</span><span class="plain">(</span><span class="identifier">PM_OverAmbitiousSlash</span><span class="plain">),</span>
|
|
<span class="string">"the slash '/' can only be used between single literal words"</span><span class="plain">,</span>
|
|
<span class="string">"so 'underneath/under/beneath' is allowed but "</span>
|
|
<span class="string">"'beneath/[florid ways to say under]/under' isn't."</span><span class="plain">);</span>
|
|
<span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain"> = 0;</span>
|
|
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">-></span><span class="identifier">down</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) {</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">i</span><span class="plain"> = </span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">i</span><span class="plain"> > 0)</span>
|
|
<span class="reserved">while</span><span class="plain"> ((</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) && (</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">) == </span><span class="identifier">i</span><span class="plain">))</span>
|
|
<span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain">++;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">LOGIF</span><span class="plain">(</span><span class="identifier">GRAMMAR_CONSTRUCTION</span><span class="plain">, </span><span class="string">"Slashed as:\</span><span class="plain">n</span><span class="string">$T"</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::slash_grammar_line is used in <a href="#SP12">§12</a>.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP14"></a><b>§14. Phase II: Determining Grammar. </b>Here there is substantial work to do both at the line list level and on
|
|
individual lines, and the latter does recurse down to token level too.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">The following routine calculates the type of the GL list as the union
|
|
of the types of the GLs within it, where union means the narrowest type
|
|
such that every GL in the list casts to it. We return null if there
|
|
are no GLs in the list, or if the GLs all return null types, or if
|
|
an error occurs. (Note that actions in command verb grammars are counted
|
|
as null for this purpose, since a grammar used for parsing the player's
|
|
commands is not also used to determine a value.)
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="functiontext">PL::Parsing::Lines::line_list_determine</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">,</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">depth</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">gv_is</span><span class="plain">, </span><span class="reserved">grammar_verb</span><span class="plain"> *</span><span class="identifier">gv</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">genuinely_verbal</span><span class="plain">) {</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">first_flag</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">spec_union</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="identifier">LOGIF</span><span class="plain">(</span><span class="identifier">GRAMMAR_CONSTRUCTION</span><span class="plain">, </span><span class="string">"Determining GL list for $G\</span><span class="plain">n</span><span class="string">"</span><span class="plain">, </span><span class="identifier">gv</span><span class="plain">);</span>
|
|
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">) {</span>
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">spec_of_line</span><span class="plain"> =</span>
|
|
<span class="functiontext">PL::Parsing::Lines::gl_determine</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">depth</span><span class="plain">, </span><span class="identifier">gv_is</span><span class="plain">, </span><span class="identifier">gv</span><span class="plain">, </span><span class="identifier">genuinely_verbal</span><span class="plain">);</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">first_flag</span><span class="plain">) { </span> <span class="comment">initially no expectations: <code class="display"><span class="extract">spec_union</span></code> is meaningless</span>
|
|
<span class="identifier">spec_union</span><span class="plain"> = </span><span class="identifier">spec_of_line</span><span class="plain">; </span> <span class="comment">so we set it to the first result</span>
|
|
<span class="identifier">first_flag</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
<span class="reserved">continue</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">spec_union</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) && (</span><span class="identifier">spec_of_line</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">))</span>
|
|
<span class="reserved">continue</span><span class="plain">; </span> <span class="comment">we expected to find no result, and did: so no problem</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">spec_union</span><span class="plain">) && (</span><span class="identifier">spec_of_line</span><span class="plain">)) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">Dash::compatible_with_description</span><span class="plain">(</span><span class="identifier">spec_union</span><span class="plain">, </span><span class="identifier">spec_of_line</span><span class="plain">) == </span><span class="identifier">ALWAYS_MATCH</span><span class="plain">) {</span>
|
|
<span class="identifier">spec_union</span><span class="plain"> = </span><span class="identifier">spec_of_line</span><span class="plain">; </span> <span class="comment">here <code class="display"><span class="extract">spec_of_line</span></code> was a wider type</span>
|
|
<span class="reserved">continue</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">Dash::compatible_with_description</span><span class="plain">(</span><span class="identifier">spec_of_line</span><span class="plain">, </span><span class="identifier">spec_union</span><span class="plain">) == </span><span class="identifier">ALWAYS_MATCH</span><span class="plain">) {</span>
|
|
<span class="reserved">continue</span><span class="plain">; </span> <span class="comment">here <code class="display"><span class="extract">spec_union</span></code> was already wide enough</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="functiontext">PL::Parsing::Verbs::allow_mixed_lines</span><span class="plain">(</span><span class="identifier">gv</span><span class="plain">)) </span><span class="reserved">continue</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">current_sentence</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>where_grammar_specified</span><span class="plain">;</span>
|
|
<span class="identifier">Problems::Issue::sentence_problem</span><span class="plain">(</span><span class="identifier">_p_</span><span class="plain">(</span><span class="identifier">PM_MixedOutcome</span><span class="plain">),</span>
|
|
<span class="string">"grammar tokens must have the same outcome whatever the way they are "</span>
|
|
<span class="string">"reached"</span><span class="plain">,</span>
|
|
<span class="string">"so writing a line like 'Understand \</span><span class="plain">"</span><span class="string">within\</span><span class="plain">"</span><span class="string"> or \</span><span class="plain">"</span><span class="string">next to "</span>
|
|
<span class="string">"[something]\</span><span class="plain">"</span><span class="string"> as \</span><span class="plain">"</span><span class="string">[my token]\</span><span class="plain">"</span><span class="string"> must be wrong: one way it produces "</span>
|
|
<span class="string">"a thing, the other way it doesn't."</span><span class="plain">);</span>
|
|
<span class="identifier">spec_union</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="reserved">break</span><span class="plain">; </span> <span class="comment">to prevent the problem being repeated for the same grammar</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">LOGIF</span><span class="plain">(</span><span class="identifier">GRAMMAR_CONSTRUCTION</span><span class="plain">, </span><span class="string">"Union: $P\</span><span class="plain">n</span><span class="string">"</span><span class="plain">);</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">spec_union</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::line_list_determine is used in 5/gv (<a href="5-gv.html#SP25">§25</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP15"></a><b>§15. </b>There are three tasks here: to determine the type of the GL, to issue a
|
|
problem if this type is impossibly large, and to calculate two numerical
|
|
quantities used in sorting GLs: the "general sorting bonus" and the
|
|
"understanding sorting bonus" (see below).
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="functiontext">PL::Parsing::Lines::gl_determine</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">depth</span><span class="plain">,</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">gv_is</span><span class="plain">, </span><span class="reserved">grammar_verb</span><span class="plain"> *</span><span class="identifier">gv</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">genuinely_verbal</span><span class="plain">) {</span>
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">spec</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">pn</span><span class="plain">, *</span><span class="identifier">pn2</span><span class="plain">;</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">nulls_count</span><span class="plain">, </span><span class="identifier">i</span><span class="plain">, </span><span class="identifier">nrv</span><span class="plain">, </span><span class="identifier">line_length</span><span class="plain">;</span>
|
|
<span class="identifier">current_sentence</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>where_grammar_specified</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>understanding_sort_bonus</span><span class="plain"> = 0;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain"> = 0;</span>
|
|
|
|
<span class="identifier">nulls_count</span><span class="plain"> = 0; </span> <span class="comment">number of tokens with null results</span>
|
|
|
|
<span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">-></span><span class="identifier">down</span><span class="plain">; </span> <span class="comment">start from first token</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">genuinely_verbal</span><span class="plain">) && (</span><span class="identifier">pn</span><span class="plain">)) </span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">; </span> <span class="comment">unless it's a command verb</span>
|
|
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">pn2</span><span class="plain">=</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">line_length</span><span class="plain">=0; </span><span class="identifier">pn2</span><span class="plain">; </span><span class="identifier">pn2</span><span class="plain"> = </span><span class="identifier">pn2</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) </span><span class="identifier">line_length</span><span class="plain">++;</span>
|
|
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">multiples</span><span class="plain"> = 0;</span>
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">i</span><span class="plain">=0; </span><span class="identifier">pn</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">, </span><span class="identifier">i</span><span class="plain">++) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">ParseTree::get_type</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">) != </span><span class="identifier">TOKEN_NT</span><span class="plain">)</span>
|
|
<span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"Bogus node types on grammar"</span><span class="plain">);</span>
|
|
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">score</span><span class="plain"> = 0;</span>
|
|
<span class="identifier">spec</span><span class="plain"> = </span><span class="functiontext">PL::Parsing::Tokens::determine</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">depth</span><span class="plain">, &</span><span class="identifier">score</span><span class="plain">);</span>
|
|
<span class="identifier">LOGIF</span><span class="plain">(</span><span class="identifier">GRAMMAR_CONSTRUCTION</span><span class="plain">, </span><span class="string">"Result of token <%W> is $P\</span><span class="plain">n</span><span class="string">"</span><span class="plain">, </span><span class="identifier">ParseTree::get_text</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">), </span><span class="identifier">spec</span><span class="plain">);</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">spec</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">Specifications::is_kind_like</span><span class="plain">(</span><span class="identifier">spec</span><span class="plain">)) &&</span>
|
|
<span class="plain">(</span><span class="identifier">Kinds::Compare::eq</span><span class="plain">(</span><span class="identifier">Specifications::to_kind</span><span class="plain">(</span><span class="identifier">spec</span><span class="plain">), </span><span class="identifier">K_understanding</span><span class="plain">))) { </span> <span class="comment">"[text]" token</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">usb_contribution</span><span class="plain"> = </span><span class="identifier">i</span><span class="plain"> - 100;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">usb_contribution</span><span class="plain"> >= 0) </span><span class="identifier">usb_contribution</span><span class="plain"> = -1;</span>
|
|
<span class="identifier">usb_contribution</span><span class="plain"> = 100*</span><span class="identifier">usb_contribution</span><span class="plain"> + (</span><span class="identifier">line_length</span><span class="plain">-1-</span><span class="identifier">i</span><span class="plain">);</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>understanding_sort_bonus</span><span class="plain"> += </span><span class="identifier">usb_contribution</span><span class="plain">; </span> <span class="comment">reduces!</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain"> +=</span>
|
|
<span class="functiontext">PL::Parsing::Tokens::Types::add_type</span><span class="plain">(&(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>gl_type</span><span class="plain">), </span><span class="identifier">spec</span><span class="plain">,</span>
|
|
<span class="functiontext">PL::Parsing::Tokens::is_multiple</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">), </span><span class="identifier">score</span><span class="plain">);</span>
|
|
<span class="plain">} </span><span class="reserved">else</span><span class="plain"> </span><span class="identifier">nulls_count</span><span class="plain">++;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="functiontext">PL::Parsing::Tokens::is_multiple</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">)) </span><span class="identifier">multiples</span><span class="plain">++;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">multiples</span><span class="plain"> > 1)</span>
|
|
<span class="identifier">Problems::Issue::sentence_problem</span><span class="plain">(</span><span class="identifier">_p_</span><span class="plain">(</span><span class="identifier">PM_MultipleMultiples</span><span class="plain">),</span>
|
|
<span class="string">"there can be at most one token in any line which can match "</span>
|
|
<span class="string">"multiple things"</span><span class="plain">,</span>
|
|
<span class="string">"so you'll have to remove one of the 'things' tokens and "</span>
|
|
<span class="string">"make it a 'something' instead."</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">nrv</span><span class="plain"> = </span><span class="functiontext">PL::Parsing::Tokens::Types::get_no_resulting_values</span><span class="plain">(&(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>gl_type</span><span class="plain">));</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">nrv</span><span class="plain"> == 0) </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain"> = 100*</span><span class="identifier">nulls_count</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gv_is</span><span class="plain"> == </span><span class="constant">GV_IS_COMMAND</span><span class="plain">) </span><span class="identifier">spec</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="reserved">else</span><span class="plain"> {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">nrv</span><span class="plain"> < 2) </span><span class="identifier">spec</span><span class="plain"> = </span><span class="functiontext">PL::Parsing::Tokens::Types::get_single_type</span><span class="plain">(&(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>gl_type</span><span class="plain">));</span>
|
|
<span class="reserved">else</span><span class="plain"> </span><span class="identifier">Problems::Issue::sentence_problem</span><span class="plain">(</span><span class="identifier">_p_</span><span class="plain">(</span><span class="identifier">PM_TwoValuedToken</span><span class="plain">),</span>
|
|
<span class="string">"there can be at most one varying part in the definition of a "</span>
|
|
<span class="string">"named token"</span><span class="plain">,</span>
|
|
<span class="string">"so 'Understand \</span><span class="plain">"</span><span class="string">button [a number]\</span><span class="plain">"</span><span class="string"> as \</span><span class="plain">"</span><span class="string">[button indication]\</span><span class="plain">"</span><span class="string">' "</span>
|
|
<span class="string">"is allowed but 'Understand \</span><span class="plain">"</span><span class="string">button [a number] on [something]\</span><span class="plain">"</span><span class="string"> "</span>
|
|
<span class="string">"as \</span><span class="plain">"</span><span class="string">[button indication]\</span><span class="plain">"</span><span class="string">' is not."</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">LOGIF</span><span class="plain">(</span><span class="identifier">GRAMMAR_CONSTRUCTION</span><span class="plain">,</span>
|
|
<span class="string">"Determined $g: lexeme count %d, sorting bonus %d, arguments %d, "</span>
|
|
<span class="string">"fixed initials %d, type $P\</span><span class="plain">n</span><span class="string">"</span><span class="plain">,</span>
|
|
<span class="identifier">gl</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain">, </span><span class="identifier">nrv</span><span class="plain">,</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>understanding_sort_bonus</span><span class="plain">, </span><span class="identifier">spec</span><span class="plain">);</span>
|
|
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">spec</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::gl_determine is used in <a href="#SP14">§14</a>.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP16"></a><b>§16. Phase III: Sort Grammar. </b>Insertion sort is used to take the linked list of GLs and construct a
|
|
separate, sorted version. This is not the controversial part.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="functiontext">PL::Parsing::Lines::list_sort</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">) {</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">, *</span><span class="identifier">gl2</span><span class="plain">, *</span><span class="identifier">gl3</span><span class="plain">, *</span><span class="identifier">sorted_head</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">list_head</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">sorted_head</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">;</span>
|
|
<span class="identifier">list_head</span><span class="plain">-</span><span class="element">>sorted_next_line</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">;</span>
|
|
<span class="reserved">while</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">) {</span>
|
|
<span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">;</span>
|
|
<span class="identifier">gl2</span><span class="plain"> = </span><span class="identifier">sorted_head</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="functiontext">PL::Parsing::Lines::grammar_line_must_precede</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">gl2</span><span class="plain">)) {</span>
|
|
<span class="identifier">sorted_head</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>sorted_next_line</span><span class="plain"> = </span><span class="identifier">gl2</span><span class="plain">;</span>
|
|
<span class="reserved">continue</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">while</span><span class="plain"> (</span><span class="identifier">gl2</span><span class="plain">) {</span>
|
|
<span class="identifier">gl3</span><span class="plain"> = </span><span class="identifier">gl2</span><span class="plain">;</span>
|
|
<span class="identifier">gl2</span><span class="plain"> = </span><span class="identifier">gl2</span><span class="plain">-</span><span class="element">>sorted_next_line</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl2</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) {</span>
|
|
<span class="identifier">gl3</span><span class="plain">-</span><span class="element">>sorted_next_line</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="functiontext">PL::Parsing::Lines::grammar_line_must_precede</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">gl2</span><span class="plain">)) {</span>
|
|
<span class="identifier">gl3</span><span class="plain">-</span><span class="element">>sorted_next_line</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>sorted_next_line</span><span class="plain"> = </span><span class="identifier">gl2</span><span class="plain">;</span>
|
|
<span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">sorted_head</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::list_sort is used in 5/gv (<a href="5-gv.html#SP30">§30</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP17"></a><b>§17. </b>This is the controversial part: the routine which decides whether one GL
|
|
takes precedence (i.e., is parsed earlier than and thus in preference to)
|
|
another GL. This algorithm has been hacked many times to try to reach a
|
|
position which pleases all designers: something of a lost cause. The
|
|
basic motivation is that we need to sort because the various parsers of
|
|
I7 grammar (<code class="display"><span class="extract">parse_name</span></code> routines, general parsing routines, the I6 command
|
|
parser itself) all work by returning the first match achieved. This means
|
|
that if grammar line L2 matches a superset of the texts which grammar line
|
|
L1 matches, then L1 should be tried first: trying them in the order L2, L1
|
|
would mean that L1 could never be matched, which is surely contrary to the
|
|
designer's intention. (Compare the rule-sorting algorithm, which has similar
|
|
motivation but is entirely distinct, though both use the same primitive
|
|
methods for comparing types of single values, i.e., at stages 5b1 and 5c1
|
|
below.)
|
|
</p>
|
|
|
|
<p class="inwebparagraph">Recall that each GL has a numerical USB (understanding sort bonus) and
|
|
GSB (general sort bonus). The following rules are applied in sequence:
|
|
</p>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<ul class="items"><li>(1) Higher USBs beat lower USBs.
|
|
</li></ul>
|
|
<ul class="items"><li>(2a) For sorting GLs in player-command grammar, shorter lines beat longer
|
|
lines, where length is calculated as the lexeme count.
|
|
</li></ul>
|
|
<ul class="items"><li>(2b) For sorting all other GLs, longer lines beat shorter lines.
|
|
</li></ul>
|
|
<ul class="items"><li>(3) Mistaken commands beat unmistaken commands.
|
|
</li></ul>
|
|
<ul class="items"><li>(4) Higher GSBs beat lower GSBs.
|
|
</li></ul>
|
|
<ul class="items"><li>(5a) Fewer resulting values beat more resulting values.
|
|
</li></ul>
|
|
<ul class="items"><li>(5b1) A narrower first result type beats a wider first result type, if
|
|
there is a first result.
|
|
</li></ul>
|
|
<ul class="items"><li>(5b2) A multiples-disallowed first result type beats a multiples-allowed
|
|
first result type, if there is a first result.
|
|
</li></ul>
|
|
<ul class="items"><li>(5c1) A narrower second result type beats a wider second result type, if
|
|
there is a second result.
|
|
</li></ul>
|
|
<ul class="items"><li>(5c2) A multiples-disallowed second result type beats a multiples-allowed
|
|
second result type, if there is a second result.
|
|
</li></ul>
|
|
<ul class="items"><li>(6) Conditional lines (with a "when" proviso, that is) beat
|
|
unconditional lines.
|
|
</li></ul>
|
|
<ul class="items"><li>(7) The grammar line defined earlier beats the one defined later.
|
|
</li></ul>
|
|
<p class="inwebparagraph">Rule 1 is intended to resolve awkward ambiguities involved with command
|
|
grammar which includes "[text]" tokens. Each such token subtracts 10000 from
|
|
the USB of a line but adds back 100 times the token position (which is at least
|
|
0 and which we can safely suppose is less than 99: we truncate just in case
|
|
so that every <code class="display"><span class="extract">"[text]"</span></code> certainly makes a negative contribution of at least
|
|
-100) and then subtracts off the number of tokens left on the line.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">Because a high USB gets priority, and "[text]" tokens make a negative
|
|
contribution, the effect is to relegate lines containing "[text]" tokens
|
|
to the bottom of the list — which is good because "[text]" voraciously
|
|
eats up words, matching more or less anything, so that any remotely
|
|
specific case ought to be tried first. The effect of the curious addition
|
|
back in of the token position is that later-placed "[text]" tokens are
|
|
tried before earlier-placed ones. Thus <code class="display"><span class="extract">"read chapter [text]"</span></code> has a USB
|
|
of -98, and takes precedence over <code class="display"><span class="extract">"read [text]"</span></code> with a USB of -99,
|
|
but both are beaten by just <code class="display"><span class="extract">"read [something]"</span></code> with a USB of 0.
|
|
The effect of the subtraction back of the number of tokens remaining
|
|
is to ensure that <code class="display"><span class="extract">"read [token] backwards"</span></code> takes priority over
|
|
<code class="display"><span class="extract">"read [token]"</span></code>.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">The voracity of <code class="display"><span class="extract">"[text]"</span></code>, and its tendency to block out all other
|
|
possibilities unless restrained, has to be addressed by this lexically
|
|
based numerical calculation because it works in a lexical sort of way:
|
|
playing with the types system to prefer <code class="display"><span class="extract">DESCRIPTION/UNDERSTANDING</span></code>
|
|
over, say, <code class="display"><span class="extract">VALUE/OBJECT</span></code> would not be sufficient.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">The most surprising point here is the asymmetry in rule 2, which basically
|
|
says that when parsing commands typed at the keyboard, shorter beats longer,
|
|
whereas in all other settings longer beats shorter. This arises because the
|
|
I6 parser, at run time, traditionally works that way: I6 command grammars
|
|
are normally stored with short forms first and long forms afterward. The
|
|
I6 parser can afford to do this because it is matching text of known length:
|
|
if parsing TAKE FROG FROM AQUARIUM, it will try TAKE FROG first but is able
|
|
to reject this as not matching the whole text. In other parsing settings,
|
|
we are trying to make a maximum-length match against a potentially infinite
|
|
stream of words, and it is therefore important to try to match WATERY
|
|
CASCADE EFFECT before WATERY CASCADE when looking at text like WATERY
|
|
CASCADE EFFECT IMPRESSES PEOPLE, given that the simplistic parsers we
|
|
compile generally return the first match found.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">Rule 3, that mistakes beat non-mistakes, was in fact rule 1 during 2006: it
|
|
seemed logical that since mistakes were exceptional cases, they would be
|
|
better checked earlier before moving on to general cases. However, an
|
|
example provided by Eric Eve showed that although this was logically correct,
|
|
the I6 parser would try to auto-complete lengthy mistakes and thus fail to
|
|
check subsequent commands. For this reason, <code class="display"><span class="extract">"look behind [something]"</span></code>
|
|
as a mistake needs to be checked after <code class="display"><span class="extract">"look"</span></code>, or else the I6 parser
|
|
will respond to the command LOOK by replying "What do you want to look
|
|
behind?" — and then saying that you are mistaken.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">Rule 4 is intended as a lexeme-based tiebreaker. We only get here if there
|
|
are the same number of lexemes in the two GLs being compared. Each is
|
|
given a GSB score as follows: a literal lexeme, which produces no result,
|
|
such as <code class="display"><span class="extract">"draw"</span></code> or <code class="display"><span class="extract">"in/inside/within"</span></code>, scores 100; all other lexemes
|
|
score as follows:
|
|
</p>
|
|
|
|
<p class="inwebparagraph">— <code class="display"><span class="extract">"[things inside]"</span></code> scores a GSB of 10 as the first parameter, 1 as the second;
|
|
</p>
|
|
|
|
<p class="inwebparagraph">— <code class="display"><span class="extract">"[things preferably held]"</span></code> similarly scores a GSB of 20 or 2;
|
|
</p>
|
|
|
|
<p class="inwebparagraph">— <code class="display"><span class="extract">"[other things]"</span></code> similarly scores a GSB of 20 or 2;
|
|
</p>
|
|
|
|
<p class="inwebparagraph">— <code class="display"><span class="extract">"[something preferably held]"</span></code> similarly scores a GSB of 30 or 3;
|
|
</p>
|
|
|
|
<p class="inwebparagraph">— any token giving a logical description of some class of objects, such as
|
|
<code class="display"><span class="extract">"[open container]"</span></code>, similarly scores a GSB of 50 or 5;
|
|
</p>
|
|
|
|
<p class="inwebparagraph">— and any remaining token (for instance, one matching a number or some other
|
|
kind of value) scores a GSB of 0.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">Literals score highly because they are structural, and differentiate
|
|
cases: under the superset rule, <code class="display"><span class="extract">"look up [thing]"</span></code> must be parsed before
|
|
<code class="display"><span class="extract">"look [direction] [thing]"</span></code>, and it is only the number of literals which
|
|
differentiates these cases. If two lines have an equal number of literals,
|
|
we now look at the first resultant lexeme. Here we find that a lexeme which
|
|
specifies an object (with a GSB of at least 10/1) beats a lexeme which only
|
|
specifies a value. Thus the same text will be parsed against objects in
|
|
preference to values, which is sensible since there are generally few
|
|
objects available to the player and they are generally likely to be the
|
|
things being referred to. Among possible object descriptions, the very
|
|
general catch-all special cases above are given lower GSB scores than
|
|
more specific ones, to enable the more specific cases to go first.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">Rule 5a is unlikely to have much effect: it is likely to be rare for GL
|
|
lists to contain GLs mixing different numbers of results. But Rule 5b1
|
|
is very significant: it causes <code class="display"><span class="extract">"draw [animal]"</span></code> to have precedence over
|
|
<code class="display"><span class="extract">"draw [thing]"</span></code>, for instance. Rule 5b2 ensures that <code class="display"><span class="extract">"draw [thing]"</span></code>
|
|
takes precedence over <code class="display"><span class="extract">"draw [things]"</span></code>, which may be useful to handle
|
|
multiple and single objects differently.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">The motivation for rule 6 is similar to the case of "when" clauses for
|
|
rules in rulebooks: it ensures that a match of <code class="display"><span class="extract">"draw [thing]"</span></code> when some
|
|
condition holds beats a match of <code class="display"><span class="extract">"draw [thing]"</span></code> at any time, and this is
|
|
necessary under the strict superset principle.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">To get to rule 7 looks difficult, given the number of things about the
|
|
grammar lines which must match up — same USB, GSB, number of lexemes,
|
|
number of resulting types, equivalent resulting types, same conditional
|
|
status — but in fact it isn't all that uncommon. Equivalent pairs produced
|
|
by the Standard Rules include:
|
|
</p>
|
|
|
|
<p class="inwebparagraph"><code class="display"><span class="extract">"get off [something]"</span></code> and <code class="display"><span class="extract">"get in/into/on/onto [something]"</span></code>
|
|
</p>
|
|
|
|
<p class="inwebparagraph"><code class="display"><span class="extract">"turn on [something]"</span></code> and <code class="display"><span class="extract">"turn [something] on"</span></code>
|
|
</p>
|
|
|
|
<p class="inwebparagraph">Only the second of these pairs leads to ambiguity, and even then only if
|
|
an object has a name like ON VISION ON — perhaps a book about the antique
|
|
BBC children's television programme "Vision On" — so that the command
|
|
TURN ON VISION ON would match both of the alternative GLs.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::grammar_line_must_precede</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">L1</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">L2</span><span class="plain">) {</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">cs</span><span class="plain">, </span><span class="identifier">a</span><span class="plain">, </span><span class="identifier">b</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">L1</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) || (</span><span class="identifier">L2</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">))</span>
|
|
<span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"tried to sort null GLs"</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain"> == -1) || (</span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain"> == -1))</span>
|
|
<span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"tried to sort unslashed GLs"</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain"> == </span><span class="constant">UNCALCULATED_BONUS</span><span class="plain">) ||</span>
|
|
<span class="plain">(</span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain"> == </span><span class="constant">UNCALCULATED_BONUS</span><span class="plain">))</span>
|
|
<span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"tried to sort uncalculated GLs"</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">L1</span><span class="plain"> == </span><span class="identifier">L2</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">a</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">; </span><span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>resulting_action</span><span class="plain">) || (</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain">)) </span><span class="identifier">a</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="identifier">b</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">; </span><span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>resulting_action</span><span class="plain">) || (</span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain">)) </span><span class="identifier">b</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">a</span><span class="plain"> != </span><span class="identifier">b</span><span class="plain">) {</span>
|
|
<span class="identifier">LOG</span><span class="plain">(</span><span class="string">"L1 = $g\</span><span class="plain">n</span><span class="string">L2 = $g\</span><span class="plain">n</span><span class="string">"</span><span class="plain">, </span><span class="identifier">L1</span><span class="plain">, </span><span class="identifier">L2</span><span class="plain">);</span>
|
|
<span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"tried to sort on incomparable GLs"</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>understanding_sort_bonus</span><span class="plain"> > </span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>understanding_sort_bonus</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>understanding_sort_bonus</span><span class="plain"> < </span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>understanding_sort_bonus</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">a</span><span class="plain">) { </span> <span class="comment">command grammar: shorter beats longer</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain"> < </span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain"> > </span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
<span class="plain">} </span><span class="reserved">else</span><span class="plain"> { </span> <span class="comment">all other grammars: longer beats shorter</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain"> < </span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain"> > </span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>lexeme_count</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain">) && (</span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain"> == </span><span class="identifier">FALSE</span><span class="plain">)) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain"> == </span><span class="identifier">FALSE</span><span class="plain">) && (</span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>mistaken</span><span class="plain">)) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain"> > </span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain"> < </span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>general_sort_bonus</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">cs</span><span class="plain"> = </span><span class="functiontext">PL::Parsing::Tokens::Types::must_precede</span><span class="plain">(&(</span><span class="identifier">L1</span><span class="plain">-</span><span class="element">>gl_type</span><span class="plain">), &(</span><span class="identifier">L2</span><span class="plain">-</span><span class="element">>gl_type</span><span class="plain">));</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">cs</span><span class="plain"> != </span><span class="identifier">NOT_APPLICABLE</span><span class="plain">) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">cs</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="functiontext">PL::Parsing::Lines::conditional</span><span class="plain">(</span><span class="identifier">L1</span><span class="plain">)) && (</span><span class="functiontext">PL::Parsing::Lines::conditional</span><span class="plain">(</span><span class="identifier">L2</span><span class="plain">) == </span><span class="identifier">FALSE</span><span class="plain">)) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="functiontext">PL::Parsing::Lines::conditional</span><span class="plain">(</span><span class="identifier">L1</span><span class="plain">) == </span><span class="identifier">FALSE</span><span class="plain">) && (</span><span class="functiontext">PL::Parsing::Lines::conditional</span><span class="plain">(</span><span class="identifier">L2</span><span class="plain">))) </span><span class="reserved">return</span><span class="plain"> </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::grammar_line_must_precede is used in <a href="#SP16">§16</a>.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP18"></a><b>§18. Phase IV: Compile Grammar. </b>At this level we compile the list of GLs in sorted order: this is what the
|
|
sorting was all for. In certain cases, we skip any GLs marked as "one word":
|
|
these are cases arising from, e.g., "Understand "frog" as the toad.",
|
|
where we noticed that the GL was a single word and included it in the <code class="display"><span class="extract">name</span></code>
|
|
property instead. This is faster and more flexible, besides writing tidier
|
|
code.
|
|
</p>
|
|
|
|
<p class="inwebparagraph">The need for this is not immediately obvious. After all, shouldn't we have
|
|
simply deleted the GL in the first place, rather than leaving it in but
|
|
marking it? The answer is no, because of the way inheritance works: values
|
|
of the <code class="display"><span class="extract">name</span></code> property accumulate from class to instance in I6, since
|
|
<code class="display"><span class="extract">name</span></code> is additive, but grammar doesn't.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::sorted_line_list_compile</span><span class="plain">(</span><span class="reserved">gpr_kit</span><span class="plain"> *</span><span class="identifier">gprk</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">,</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">gv_is</span><span class="plain">, </span><span class="reserved">grammar_verb</span><span class="plain"> *</span><span class="identifier">gv</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">genuinely_verbal</span><span class="plain">) {</span>
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>sorted_next_line</span><span class="plain">)</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>suppress_compilation</span><span class="plain"> == </span><span class="identifier">FALSE</span><span class="plain">)</span>
|
|
<span class="functiontext">PL::Parsing::Lines::compile_grammar_line</span><span class="plain">(</span><span class="identifier">gprk</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">gv_is</span><span class="plain">, </span><span class="identifier">gv</span><span class="plain">, </span><span class="identifier">genuinely_verbal</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::sorted_line_list_compile is used in 5/gv (<a href="5-gv.html#SP29">§29</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP19"></a><b>§19. </b>The following apparently global variables are used to provide a persistent
|
|
state for the routine below, but are not accessed elsewhere. The label
|
|
counter is reset at the start of each GV's compilation, though this is a
|
|
purely cosmetic effect.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">current_grammar_block</span><span class="plain"> = 0;</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">current_label</span><span class="plain"> = 1;</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">GV_IS_VALUE_instance_mode</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::reset_labels</span><span class="plain">(</span><span class="reserved">void</span><span class="plain">) {</span>
|
|
<span class="identifier">current_label</span><span class="plain"> = 1;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::reset_labels is used in 5/gv (<a href="5-gv.html#SP27">§27</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP20"></a><b>§20. </b>As fancy as the following routine may look, it contains very little.
|
|
What complexity there is comes from the fact that command GVs are compiled
|
|
very differently to all others (most grammars are compiled in "code mode",
|
|
generating procedural I6 statements, but command GVs are compiled to lines
|
|
in <code class="display"><span class="extract">Verb</span></code> directives) and that GLs resulting in actions (i.e., GLs in
|
|
command GVs) have not yet been type-checked, whereas all others have.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::compile_grammar_line</span><span class="plain">(</span><span class="reserved">gpr_kit</span><span class="plain"> *</span><span class="identifier">gprk</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">gv_is</span><span class="plain">, </span><span class="reserved">grammar_verb</span><span class="plain"> *</span><span class="identifier">gv</span><span class="plain">,</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">genuinely_verbal</span><span class="plain">) {</span>
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">pn</span><span class="plain">;</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">i</span><span class="plain">;</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">token_values</span><span class="plain">;</span>
|
|
<span class="identifier">kind</span><span class="plain"> *</span><span class="identifier">token_value_kinds</span><span class="plain">[2];</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">code_mode</span><span class="plain">, </span><span class="identifier">consult_mode</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">LOGIF</span><span class="plain">(</span><span class="identifier">GRAMMAR</span><span class="plain">, </span><span class="string">"Compiling grammar line: $g\</span><span class="plain">n</span><span class="string">"</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">current_sentence</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>where_grammar_specified</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gv_is</span><span class="plain"> == </span><span class="constant">GV_IS_COMMAND</span><span class="plain">) </span><span class="identifier">code_mode</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">; </span><span class="reserved">else</span><span class="plain"> </span><span class="identifier">code_mode</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gv_is</span><span class="plain"> == </span><span class="constant">GV_IS_CONSULT</span><span class="plain">) </span><span class="identifier">consult_mode</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">; </span><span class="reserved">else</span><span class="plain"> </span><span class="identifier">consult_mode</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">switch</span><span class="plain"> (</span><span class="identifier">gv_is</span><span class="plain">) {</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_COMMAND</span><span class="plain">:</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_TOKEN</span><span class="plain">:</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_CONSULT</span><span class="plain">:</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_OBJECT</span><span class="plain">:</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_VALUE</span><span class="plain">:</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_PROPERTY_NAME</span><span class="plain">:</span>
|
|
<span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="reserved">default</span><span class="plain">: </span><span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"tried to compile unknown GV type"</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">current_grammar_block</span><span class="plain">++;</span>
|
|
<span class="identifier">token_values</span><span class="plain"> = 0;</span>
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">i</span><span class="plain">=0; </span><span class="identifier">i</span><span class="plain"><2; </span><span class="identifier">i</span><span class="plain">++) </span><span class="identifier">token_value_kinds</span><span class="plain">[</span><span class="identifier">i</span><span class="plain">] = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">code_mode</span><span class="plain"> == </span><span class="identifier">FALSE</span><span class="plain">) </span><span class="identifier">Emit::array_iname_entry</span><span class="plain">(</span><span class="identifier">VERB_DIRECTIVE_DIVIDER_iname</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">inter_symbol</span><span class="plain"> *</span><span class="identifier">fail_label</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gprk</span><span class="plain">) {</span>
|
|
<span class="identifier">TEMPORARY_TEXT</span><span class="plain">(</span><span class="identifier">L</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE_TO</span><span class="plain">(</span><span class="identifier">L</span><span class="plain">, </span><span class="string">".Fail_%d"</span><span class="plain">, </span><span class="identifier">current_label</span><span class="plain">);</span>
|
|
<span class="identifier">fail_label</span><span class="plain"> = </span><span class="identifier">Produce::reserve_label</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">L</span><span class="plain">);</span>
|
|
<span class="identifier">DISCARD_TEXT</span><span class="plain">(</span><span class="identifier">L</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="functiontext">PL::Parsing::Lines::gl_compile_extra_token_for_condition</span><span class="plain">(</span><span class="identifier">gprk</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">gv_is</span><span class="plain">, </span><span class="identifier">fail_label</span><span class="plain">);</span>
|
|
<span class="functiontext">PL::Parsing::Lines::gl_compile_extra_token_for_mistake</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">gv_is</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>tokens</span><span class="plain">-></span><span class="identifier">down</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">genuinely_verbal</span><span class="plain">) && (</span><span class="identifier">pn</span><span class="plain">)) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">) != 0) {</span>
|
|
<span class="identifier">Problems::Issue::sentence_problem</span><span class="plain">(</span><span class="identifier">_p_</span><span class="plain">(</span><span class="identifier">PM_SlashedCommand</span><span class="plain">),</span>
|
|
<span class="string">"at present you're not allowed to use a / between command "</span>
|
|
<span class="string">"words at the start of a line"</span><span class="plain">,</span>
|
|
<span class="string">"so 'put/interpose/insert [something]' is out."</span><span class="plain">);</span>
|
|
<span class="reserved">return</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">; </span> <span class="comment">skip command word: the <code class="display"><span class="extract">Verb</span></code> header contains it already</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">gv_is</span><span class="plain"> == </span><span class="constant">GV_IS_VALUE</span><span class="plain">) && (</span><span class="identifier">GV_IS_VALUE_instance_mode</span><span class="plain">)) {</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">IF_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">EQ_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>instance_s</span><span class="plain">);</span>
|
|
<span class="functiontext">PL::Parsing::Tokens::Types::compile_to_string</span><span class="plain">(&(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>gl_type</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::code</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">pn_from</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">, *</span><span class="identifier">pn_to</span><span class="plain"> = </span><span class="identifier">pn_from</span><span class="plain">;</span>
|
|
<span class="reserved">for</span><span class="plain"> (; </span><span class="identifier">pn</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) </span><span class="identifier">pn_to</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">;</span>
|
|
|
|
<span class="functiontext">PL::Parsing::Lines::compile_token_line</span><span class="plain">(</span><span class="identifier">gprk</span><span class="plain">, </span><span class="identifier">code_mode</span><span class="plain">, </span><span class="identifier">pn_from</span><span class="plain">, </span><span class="identifier">pn_to</span><span class="plain">, </span><span class="identifier">gv_is</span><span class="plain">, </span><span class="identifier">consult_mode</span><span class="plain">, &</span><span class="identifier">token_values</span><span class="plain">, </span><span class="identifier">token_value_kinds</span><span class="plain">, </span><span class="identifier">NULL</span><span class="plain">, </span><span class="identifier">fail_label</span><span class="plain">);</span>
|
|
|
|
<span class="reserved">switch</span><span class="plain"> (</span><span class="identifier">gv_is</span><span class="plain">) {</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_COMMAND</span><span class="plain">:</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="functiontext">PL::Parsing::Lines::gl_compile_result_of_mistake</span><span class="plain">(</span><span class="identifier">gprk</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">)) </span><span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="identifier">Emit::array_iname_entry</span><span class="plain">(</span><span class="identifier">VERB_DIRECTIVE_RESULT_iname</span><span class="plain">);</span>
|
|
<span class="identifier">Emit::array_action_entry</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>resulting_action</span><span class="plain">);</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>reversed</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">token_values</span><span class="plain"> < 2) {</span>
|
|
<span class="identifier">Problems::Issue::sentence_problem</span><span class="plain">(</span><span class="identifier">_p_</span><span class="plain">(</span><span class="identifier">PM_CantReverseOne</span><span class="plain">),</span>
|
|
<span class="string">"you can't use a 'reversed' action when you supply fewer "</span>
|
|
<span class="string">"than two values for it to apply to"</span><span class="plain">,</span>
|
|
<span class="string">"since reversal is the process of exchanging them."</span><span class="plain">);</span>
|
|
<span class="reserved">return</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">kind</span><span class="plain"> *</span><span class="identifier">swap</span><span class="plain"> = </span><span class="identifier">token_value_kinds</span><span class="plain">[0];</span>
|
|
<span class="identifier">token_value_kinds</span><span class="plain">[0] = </span><span class="identifier">token_value_kinds</span><span class="plain">[1];</span>
|
|
<span class="identifier">token_value_kinds</span><span class="plain">[1] = </span><span class="identifier">swap</span><span class="plain">;</span>
|
|
<span class="identifier">Emit::array_iname_entry</span><span class="plain">(</span><span class="identifier">VERB_DIRECTIVE_REVERSE_iname</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="functiontext">PL::Actions::check_types_for_grammar</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>resulting_action</span><span class="plain">, </span><span class="identifier">token_values</span><span class="plain">,</span>
|
|
<span class="identifier">token_value_kinds</span><span class="plain">);</span>
|
|
<span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_PROPERTY_NAME</span><span class="plain">:</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_TOKEN</span><span class="plain">:</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">RETURN_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>rv_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::place_label</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">fail_label</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>rv_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">GPR_PREPOSITION_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">WN_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>original_wn_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_CONSULT</span><span class="plain">:</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">IF_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">OR_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">EQ_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>range_words_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::val</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_number</span><span class="plain">, </span><span class="identifier">LITERAL_IVAL</span><span class="plain">, 0);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">EQ_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">MINUS_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">WN_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>range_from_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>range_words_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::code</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">RETURN_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>rv_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
|
|
<span class="identifier">Produce::place_label</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">fail_label</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>rv_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">GPR_PREPOSITION_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">WN_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>original_wn_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_OBJECT</span><span class="plain">:</span>
|
|
<span class="functiontext">PL::Parsing::Tokens::General::after_gl_failed</span><span class="plain">(</span><span class="identifier">gprk</span><span class="plain">, </span><span class="identifier">fail_label</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>pluralised</span><span class="plain">);</span>
|
|
<span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="reserved">case</span><span class="plain"> </span><span class="constant">GV_IS_VALUE</span><span class="plain">:</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">PARSED_NUMBER_HL</span><span class="plain">));</span>
|
|
<span class="functiontext">PL::Parsing::Tokens::Types::compile_to_string</span><span class="plain">(&(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>gl_type</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">RETURN_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_object</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">GPR_NUMBER_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::place_label</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">fail_label</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">WN_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>original_wn_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">gv_is</span><span class="plain"> == </span><span class="constant">GV_IS_VALUE</span><span class="plain">) && (</span><span class="identifier">GV_IS_VALUE_instance_mode</span><span class="plain">)) {</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">current_label</span><span class="plain">++;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::compile_token_line</span><span class="plain">(</span><span class="reserved">gpr_kit</span><span class="plain"> *</span><span class="identifier">gprk</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">code_mode</span><span class="plain">, </span><span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">parse_node</span><span class="plain"> *</span><span class="identifier">pn_to</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">gv_is</span><span class="plain">, </span><span class="reserved">int</span><span class="plain"> </span><span class="identifier">consult_mode</span><span class="plain">,</span>
|
|
<span class="reserved">int</span><span class="plain"> *</span><span class="identifier">token_values</span><span class="plain">, </span><span class="identifier">kind</span><span class="plain"> **</span><span class="identifier">token_value_kinds</span><span class="plain">, </span><span class="identifier">inter_symbol</span><span class="plain"> *</span><span class="identifier">group_wn_s</span><span class="plain">, </span><span class="identifier">inter_symbol</span><span class="plain"> *</span><span class="identifier">fail_label</span><span class="plain">) {</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">lexeme_equivalence_class</span><span class="plain"> = 0;</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">alternative_number</span><span class="plain"> = 0;</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">empty_text_allowed_in_lexeme</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
|
|
<span class="identifier">inter_symbol</span><span class="plain"> *</span><span class="identifier">next_reserved_label</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="identifier">inter_symbol</span><span class="plain"> *</span><span class="identifier">eog_reserved_label</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="reserved">for</span><span class="plain"> (; </span><span class="identifier">pn</span><span class="plain">; </span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="functiontext">PL::Parsing::Tokens::is_text</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">)) && (</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) &&</span>
|
|
<span class="plain">(</span><span class="functiontext">PL::Parsing::Tokens::is_literal</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) == </span><span class="identifier">FALSE</span><span class="plain">)) {</span>
|
|
<span class="identifier">Problems::Issue::sentence_problem</span><span class="plain">(</span><span class="identifier">_p_</span><span class="plain">(</span><span class="identifier">PM_TextFollowedBy</span><span class="plain">),</span>
|
|
<span class="string">"a '[text]' token must either match the end of some text, or "</span>
|
|
<span class="string">"be followed by definitely known wording"</span><span class="plain">,</span>
|
|
<span class="string">"since otherwise the run-time parser isn't good enough to "</span>
|
|
<span class="string">"make sense of things."</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">ParseTree::get_grammar_token_relation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">)) && (</span><span class="identifier">gv_is</span><span class="plain"> != </span><span class="constant">GV_IS_OBJECT</span><span class="plain">)) {</span>
|
|
<span class="identifier">Problems::Issue::sentence_problem</span><span class="plain">(</span><span class="identifier">_p_</span><span class="plain">(</span><span class="identifier">PM_GrammarObjectlessRelation</span><span class="plain">),</span>
|
|
<span class="string">"a grammar token in an 'Understand...' can only be based "</span>
|
|
<span class="string">"on a relation if it is to understand the name of a room or thing"</span><span class="plain">,</span>
|
|
<span class="string">"since otherwise there is nothing for the relation to be with."</span><span class="plain">);</span>
|
|
<span class="reserved">continue</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">first_token_in_lexeme</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">, </span><span class="identifier">last_token_in_lexeme</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">) != 0) { </span> <span class="comment">in a multi-token lexeme</span>
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) ||</span>
|
|
<span class="plain">(</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">) !=</span>
|
|
<span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">)))</span>
|
|
<span class="identifier">last_token_in_lexeme</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">) != </span><span class="identifier">lexeme_equivalence_class</span><span class="plain">) {</span>
|
|
<span class="identifier">first_token_in_lexeme</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="identifier">empty_text_allowed_in_lexeme</span><span class="plain"> =</span>
|
|
<span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_dash_dash_ANNOT</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">lexeme_equivalence_class</span><span class="plain"> = </span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">first_token_in_lexeme</span><span class="plain">) </span><span class="identifier">alternative_number</span><span class="plain"> = 1;</span>
|
|
<span class="reserved">else</span><span class="plain"> </span><span class="identifier">alternative_number</span><span class="plain">++;</span>
|
|
<span class="plain">} </span><span class="reserved">else</span><span class="plain"> { </span> <span class="comment">in a single-token lexeme</span>
|
|
<span class="identifier">lexeme_equivalence_class</span><span class="plain"> = 0;</span>
|
|
<span class="identifier">first_token_in_lexeme</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="identifier">last_token_in_lexeme</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="identifier">empty_text_allowed_in_lexeme</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
<span class="identifier">alternative_number</span><span class="plain"> = 1;</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="identifier">inter_symbol</span><span class="plain"> *</span><span class="identifier">jump_on_fail</span><span class="plain"> = </span><span class="identifier">fail_label</span><span class="plain">;</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">lexeme_equivalence_class</span><span class="plain"> > 0) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">code_mode</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">first_token_in_lexeme</span><span class="plain">) {</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>group_wn_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">WN_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">next_reserved_label</span><span class="plain">) </span><span class="identifier">Produce::place_label</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">next_reserved_label</span><span class="plain">);</span>
|
|
<span class="identifier">TEMPORARY_TEXT</span><span class="plain">(</span><span class="identifier">L</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE_TO</span><span class="plain">(</span><span class="identifier">L</span><span class="plain">, </span><span class="string">".group_%d_%d_%d"</span><span class="plain">, </span><span class="identifier">current_grammar_block</span><span class="plain">, </span><span class="identifier">lexeme_equivalence_class</span><span class="plain">, </span><span class="identifier">alternative_number</span><span class="plain">+1);</span>
|
|
<span class="identifier">next_reserved_label</span><span class="plain"> = </span><span class="identifier">Produce::reserve_label</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">L</span><span class="plain">);</span>
|
|
<span class="identifier">DISCARD_TEXT</span><span class="plain">(</span><span class="identifier">L</span><span class="plain">);</span>
|
|
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">WN_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>group_wn_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">last_token_in_lexeme</span><span class="plain"> == </span><span class="identifier">FALSE</span><span class="plain">) || (</span><span class="identifier">empty_text_allowed_in_lexeme</span><span class="plain">)) {</span>
|
|
<span class="identifier">jump_on_fail</span><span class="plain"> = </span><span class="identifier">next_reserved_label</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> ((</span><span class="identifier">empty_text_allowed_in_lexeme</span><span class="plain">) && (</span><span class="identifier">code_mode</span><span class="plain"> == </span><span class="identifier">FALSE</span><span class="plain">)) {</span>
|
|
<span class="reserved">slash_gpr</span><span class="plain"> *</span><span class="identifier">sgpr</span><span class="plain"> = </span><span class="identifier">CREATE</span><span class="plain">(</span><span class="reserved">slash_gpr</span><span class="plain">);</span>
|
|
<span class="identifier">sgpr</span><span class="plain">-</span><span class="element">>first_choice</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">;</span>
|
|
<span class="reserved">while</span><span class="plain"> ((</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">) &&</span>
|
|
<span class="plain">(</span><span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">) ==</span>
|
|
<span class="identifier">ParseTree::int_annotation</span><span class="plain">(</span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">slash_class_ANNOT</span><span class="plain">))) </span><span class="identifier">pn</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">-</span><span class="element">>next</span><span class="plain">;</span>
|
|
<span class="identifier">sgpr</span><span class="plain">-</span><span class="element">>last_choice</span><span class="plain"> = </span><span class="identifier">pn</span><span class="plain">;</span>
|
|
<span class="identifier">package_request</span><span class="plain"> *</span><span class="identifier">PR</span><span class="plain"> = </span><span class="identifier">Hierarchy::local_package</span><span class="plain">(</span><span class="identifier">SLASH_TOKENS_HAP</span><span class="plain">);</span>
|
|
<span class="identifier">sgpr</span><span class="plain">-</span><span class="element">>sgpr_iname</span><span class="plain"> = </span><span class="identifier">Hierarchy::make_iname_in</span><span class="plain">(</span><span class="identifier">SLASH_FN_HL</span><span class="plain">, </span><span class="identifier">PR</span><span class="plain">);</span>
|
|
<span class="identifier">Emit::array_iname_entry</span><span class="plain">(</span><span class="identifier">sgpr</span><span class="plain">-</span><span class="element">>sgpr_iname</span><span class="plain">);</span>
|
|
<span class="identifier">last_token_in_lexeme</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="plain">} </span><span class="reserved">else</span><span class="plain"> {</span>
|
|
<span class="identifier">kind</span><span class="plain"> *</span><span class="identifier">grammar_token_kind</span><span class="plain"> =</span>
|
|
<span class="functiontext">PL::Parsing::Tokens::compile</span><span class="plain">(</span><span class="identifier">gprk</span><span class="plain">, </span><span class="identifier">pn</span><span class="plain">, </span><span class="identifier">code_mode</span><span class="plain">, </span><span class="identifier">jump_on_fail</span><span class="plain">, </span><span class="identifier">consult_mode</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">grammar_token_kind</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">token_values</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (*</span><span class="identifier">token_values</span><span class="plain"> == 2) {</span>
|
|
<span class="identifier">internal_error</span><span class="plain">(</span>
|
|
<span class="string">"There can be at most two value-producing tokens and this "</span>
|
|
<span class="string">"should have been detected earlier."</span><span class="plain">);</span>
|
|
<span class="reserved">return</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">token_value_kinds</span><span class="plain">[(*</span><span class="identifier">token_values</span><span class="plain">)++] = </span><span class="identifier">grammar_token_kind</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">lexeme_equivalence_class</span><span class="plain"> > 0) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">code_mode</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">last_token_in_lexeme</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">empty_text_allowed_in_lexeme</span><span class="plain">) {</span>
|
|
<<span class="cwebmacro">Jump to end of group</span> <span class="cwebmacronumber">20.1</span>><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">next_reserved_label</span><span class="plain">)</span>
|
|
<span class="identifier">Produce::place_label</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">next_reserved_label</span><span class="plain">);</span>
|
|
<span class="identifier">next_reserved_label</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">STORE_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::ref_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">WN_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::val_symbol</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">gprk</span><span class="plain">-</span><span class="element">>group_wn_s</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">eog_reserved_label</span><span class="plain">) </span><span class="identifier">Produce::place_label</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">eog_reserved_label</span><span class="plain">);</span>
|
|
<span class="identifier">eog_reserved_label</span><span class="plain"> = </span><span class="identifier">NULL</span><span class="plain">;</span>
|
|
<span class="plain">} </span><span class="reserved">else</span><span class="plain"> {</span>
|
|
<<span class="cwebmacro">Jump to end of group</span> <span class="cwebmacronumber">20.1</span>><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">} </span><span class="reserved">else</span><span class="plain"> {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">last_token_in_lexeme</span><span class="plain"> == </span><span class="identifier">FALSE</span><span class="plain">) </span><span class="identifier">Emit::array_iname_entry</span><span class="plain">(</span><span class="identifier">VERB_DIRECTIVE_SLASH_iname</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">pn</span><span class="plain"> == </span><span class="identifier">pn_to</span><span class="plain">) </span><span class="reserved">break</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::compile_grammar_line is used in <a href="#SP18">§18</a>.</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::compile_token_line is used in <a href="#SP21">§21</a>.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP20_1"></a><b>§20.1. </b><code class="display">
|
|
<<span class="cwebmacrodefn">Jump to end of group</span> <span class="cwebmacronumber">20.1</span>> =
|
|
</code></p>
|
|
|
|
|
|
<pre class="displaydefn">
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">eog_reserved_label</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) {</span>
|
|
<span class="identifier">TEMPORARY_TEXT</span><span class="plain">(</span><span class="identifier">L</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE_TO</span><span class="plain">(</span><span class="identifier">L</span><span class="plain">, </span><span class="string">".group_%d_%d_end"</span><span class="plain">,</span>
|
|
<span class="identifier">current_grammar_block</span><span class="plain">, </span><span class="identifier">lexeme_equivalence_class</span><span class="plain">);</span>
|
|
<span class="identifier">eog_reserved_label</span><span class="plain"> = </span><span class="identifier">Produce::reserve_label</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">L</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">JUMP_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::lab</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">eog_reserved_label</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">This code is used in <a href="#SP20">§20</a> (twice).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP21"></a><b>§21. </b></p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::compile_slash_gprs</span><span class="plain">(</span><span class="reserved">void</span><span class="plain">) {</span>
|
|
<span class="reserved">slash_gpr</span><span class="plain"> *</span><span class="identifier">sgpr</span><span class="plain">;</span>
|
|
<span class="identifier">LOOP_OVER</span><span class="plain">(</span><span class="identifier">sgpr</span><span class="plain">, </span><span class="reserved">slash_gpr</span><span class="plain">) {</span>
|
|
<span class="identifier">packaging_state</span><span class="plain"> </span><span class="identifier">save</span><span class="plain"> = </span><span class="identifier">Routines::begin</span><span class="plain">(</span><span class="identifier">sgpr</span><span class="plain">-</span><span class="element">>sgpr_iname</span><span class="plain">);</span>
|
|
<span class="reserved">gpr_kit</span><span class="plain"> </span><span class="identifier">gprk</span><span class="plain"> = </span><span class="functiontext">PL::Parsing::Tokens::Values::new_kit</span><span class="plain">();</span>
|
|
<span class="functiontext">PL::Parsing::Tokens::Values::add_original</span><span class="plain">(&</span><span class="identifier">gprk</span><span class="plain">);</span>
|
|
<span class="functiontext">PL::Parsing::Tokens::Values::add_standard_set</span><span class="plain">(&</span><span class="identifier">gprk</span><span class="plain">);</span>
|
|
|
|
<span class="functiontext">PL::Parsing::Lines::compile_token_line</span><span class="plain">(&</span><span class="identifier">gprk</span><span class="plain">, </span><span class="identifier">TRUE</span><span class="plain">, </span><span class="identifier">sgpr</span><span class="plain">-</span><span class="element">>first_choice</span><span class="plain">, </span><span class="identifier">sgpr</span><span class="plain">-</span><span class="element">>last_choice</span><span class="plain">, </span><span class="constant">GV_IS_TOKEN</span><span class="plain">, </span><span class="identifier">FALSE</span><span class="plain">, </span><span class="identifier">NULL</span><span class="plain">, </span><span class="identifier">NULL</span><span class="plain">, </span><span class="identifier">gprk</span><span class="element">.group_wn_s</span><span class="plain">, </span><span class="identifier">NULL</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::inv_primitive</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">RETURN_BIP</span><span class="plain">);</span>
|
|
<span class="identifier">Produce::down</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Produce::val_iname</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">(), </span><span class="identifier">K_value</span><span class="plain">, </span><span class="identifier">Hierarchy::find</span><span class="plain">(</span><span class="identifier">GPR_PREPOSITION_HL</span><span class="plain">));</span>
|
|
<span class="identifier">Produce::up</span><span class="plain">(</span><span class="identifier">Emit::tree</span><span class="plain">());</span>
|
|
<span class="identifier">Routines::end</span><span class="plain">(</span><span class="identifier">save</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::compile_slash_gprs is used in 5/gv (<a href="5-gv.html#SP26">§26</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP22"></a><b>§22. Indexing by grammar. </b>This is the more obvious form of indexing: we show the grammar lines which
|
|
make up an individual GL. (For instance, this is used in the Actions index
|
|
to show the grammar for an individual command word, by calling the routine
|
|
below for that command word's GV.) Such an index list is done in sorted
|
|
order, so that the order of appearance in the index corresponds to the
|
|
order of parsing — this is what the reader of the index is interested in.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::sorted_list_index_normal</span><span class="plain">(</span><span class="identifier">OUTPUT_STREAM</span><span class="plain">,</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">, </span><span class="identifier">text_stream</span><span class="plain"> *</span><span class="identifier">headword</span><span class="plain">) {</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>sorted_next_line</span><span class="plain">)</span>
|
|
<span class="functiontext">PL::Parsing::Lines::gl_index_normal</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">headword</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::gl_index_normal</span><span class="plain">(</span><span class="identifier">OUTPUT_STREAM</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">, </span><span class="identifier">text_stream</span><span class="plain"> *</span><span class="identifier">headword</span><span class="plain">) {</span>
|
|
<span class="reserved">action_name</span><span class="plain"> *</span><span class="identifier">an</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>resulting_action</span><span class="plain">;</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">an</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) </span><span class="reserved">return</span><span class="plain">;</span>
|
|
<span class="identifier">Index::anchor</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">, </span><span class="identifier">headword</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="functiontext">PL::Actions::is_out_of_world</span><span class="plain">(</span><span class="identifier">an</span><span class="plain">))</span>
|
|
<span class="identifier">HTML::begin_colour</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">, </span><span class="identifier">I</span><span class="string">"800000"</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE</span><span class="plain">(</span><span class="string">"&quot;"</span><span class="plain">);</span>
|
|
<span class="functiontext">PL::Actions::Index::verb_definition</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">, </span><span class="identifier">Lexer::word_text</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>original_text</span><span class="plain">),</span>
|
|
<span class="identifier">headword</span><span class="plain">, </span><span class="identifier">EMPTY_WORDING</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE</span><span class="plain">(</span><span class="string">"&quot;"</span><span class="plain">);</span>
|
|
<span class="identifier">Index::link</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>original_text</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE</span><span class="plain">(</span><span class="string">" - <i>%+W"</span><span class="plain">, </span><span class="identifier">an</span><span class="plain">-</span><span class="element">>present_name</span><span class="plain">);</span>
|
|
<span class="identifier">Index::detail_link</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">, </span><span class="string">"A"</span><span class="plain">, </span><span class="identifier">an</span><span class="plain">-></span><span class="identifier">allocation_id</span><span class="plain">, </span><span class="identifier">TRUE</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>reversed</span><span class="plain">) </span><span class="identifier">WRITE</span><span class="plain">(</span><span class="string">" (reversed)"</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE</span><span class="plain">(</span><span class="string">"</i>"</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="functiontext">PL::Actions::is_out_of_world</span><span class="plain">(</span><span class="identifier">an</span><span class="plain">))</span>
|
|
<span class="identifier">HTML::end_colour</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">);</span>
|
|
<span class="identifier">HTML_TAG</span><span class="plain">(</span><span class="string">"br"</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::sorted_list_index_normal is used in 5/gv (<a href="5-gv.html#SP12">§12</a>).</p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::gl_index_normal appears nowhere else.</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP23"></a><b>§23. Indexing by action. </b>Grammar lines are typically indexed twice: the other time is when all
|
|
grammar lines belonging to a given action are tabulated. Special linked
|
|
lists are kept for this purpose, and this is where we unravel them and
|
|
print to the index. The question of sorted vs unsorted is meaningless
|
|
here, since the GLs appearing in such a list will typically belong to
|
|
several different GVs. (As it happens, they appear in order of creation,
|
|
i.e., in source text order.)
|
|
</p>
|
|
|
|
<p class="inwebparagraph">Tiresomely, all of this means that we need to store "uphill" pointers
|
|
in GLs: back up to the GVs that own them. The following routine does
|
|
this for a whole list of GLs:
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::list_assert_ownership</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">, </span><span class="reserved">grammar_verb</span><span class="plain"> *</span><span class="identifier">gv</span><span class="plain">) {</span>
|
|
<span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="reserved">for</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain">; </span><span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>next_line</span><span class="plain">)</span>
|
|
<span class="identifier">gl</span><span class="plain">-</span><span class="element">>belongs_to_gv</span><span class="plain"> = </span><span class="identifier">gv</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::list_assert_ownership is used in 5/gv (<a href="5-gv.html#SP29">§29</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP24"></a><b>§24. </b>And this routine accumulates the per-action lists of GLs:
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::list_with_action_add</span><span class="plain">(</span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">list_head</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">list_head</span><span class="plain"> == </span><span class="identifier">NULL</span><span class="plain">) </span><span class="identifier">internal_error</span><span class="plain">(</span><span class="string">"tried to add to null action list"</span><span class="plain">);</span>
|
|
<span class="reserved">while</span><span class="plain"> (</span><span class="identifier">list_head</span><span class="plain">-</span><span class="element">>next_with_action</span><span class="plain">)</span>
|
|
<span class="identifier">list_head</span><span class="plain"> = </span><span class="identifier">list_head</span><span class="plain">-</span><span class="element">>next_with_action</span><span class="plain">;</span>
|
|
<span class="identifier">list_head</span><span class="plain">-</span><span class="element">>next_with_action</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::list_with_action_add is used in 4/act (<a href="4-act.html#SP34">§34</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP25"></a><b>§25. </b>Finally, here we index an action list of GLs, each getting a line in
|
|
the HTML index.
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::index_list_with_action</span><span class="plain">(</span><span class="identifier">OUTPUT_STREAM</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">) {</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">said_something</span><span class="plain"> = </span><span class="identifier">FALSE</span><span class="plain">;</span>
|
|
<span class="reserved">while</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain"> != </span><span class="identifier">NULL</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>belongs_to_gv</span><span class="plain">) {</span>
|
|
<span class="identifier">wording</span><span class="plain"> </span><span class="identifier">VW</span><span class="plain"> = </span><span class="functiontext">PL::Parsing::Verbs::get_verb_text</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>belongs_to_gv</span><span class="plain">);</span>
|
|
<span class="identifier">TEMPORARY_TEXT</span><span class="plain">(</span><span class="identifier">trueverb</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">Wordings::nonempty</span><span class="plain">(</span><span class="identifier">VW</span><span class="plain">))</span>
|
|
<span class="identifier">WRITE_TO</span><span class="plain">(</span><span class="identifier">trueverb</span><span class="plain">, </span><span class="string">"%W"</span><span class="plain">, </span><span class="identifier">Wordings::one_word</span><span class="plain">(</span><span class="identifier">Wordings::first_wn</span><span class="plain">(</span><span class="identifier">VW</span><span class="plain">)));</span>
|
|
<span class="identifier">HTMLFiles::open_para</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">, 2, </span><span class="string">"hanging"</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE</span><span class="plain">(</span><span class="string">"&quot;"</span><span class="plain">);</span>
|
|
<span class="functiontext">PL::Actions::Index::verb_definition</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">,</span>
|
|
<span class="identifier">Lexer::word_text</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>original_text</span><span class="plain">), </span><span class="identifier">trueverb</span><span class="plain">, </span><span class="identifier">VW</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE</span><span class="plain">(</span><span class="string">"&quot;"</span><span class="plain">);</span>
|
|
<span class="identifier">Index::link</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>original_text</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>reversed</span><span class="plain">) </span><span class="identifier">WRITE</span><span class="plain">(</span><span class="string">" <i>reversed</i>"</span><span class="plain">);</span>
|
|
<span class="identifier">HTML_CLOSE</span><span class="plain">(</span><span class="string">"p"</span><span class="plain">);</span>
|
|
<span class="identifier">said_something</span><span class="plain"> = </span><span class="identifier">TRUE</span><span class="plain">;</span>
|
|
<span class="identifier">DISCARD_TEXT</span><span class="plain">(</span><span class="identifier">trueverb</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>next_with_action</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="reserved">return</span><span class="plain"> </span><span class="identifier">said_something</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::index_list_with_action is used in 4/act (<a href="4-act.html#SP39">§39</a>).</p>
|
|
|
|
<p class="inwebparagraph"><a id="SP26"></a><b>§26. </b>And the same, but more simply:
|
|
</p>
|
|
|
|
|
|
<pre class="display">
|
|
<span class="reserved">void</span><span class="plain"> </span><span class="functiontext">PL::Parsing::Lines::index_list_for_token</span><span class="plain">(</span><span class="identifier">OUTPUT_STREAM</span><span class="plain">, </span><span class="reserved">grammar_line</span><span class="plain"> *</span><span class="identifier">gl</span><span class="plain">) {</span>
|
|
<span class="reserved">int</span><span class="plain"> </span><span class="identifier">k</span><span class="plain"> = 0;</span>
|
|
<span class="reserved">while</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain"> != </span><span class="identifier">NULL</span><span class="plain">) {</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>belongs_to_gv</span><span class="plain">) {</span>
|
|
<span class="identifier">wording</span><span class="plain"> </span><span class="identifier">VW</span><span class="plain"> = </span><span class="functiontext">PL::Parsing::Verbs::get_verb_text</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>belongs_to_gv</span><span class="plain">);</span>
|
|
<span class="identifier">TEMPORARY_TEXT</span><span class="plain">(</span><span class="identifier">trueverb</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">Wordings::nonempty</span><span class="plain">(</span><span class="identifier">VW</span><span class="plain">))</span>
|
|
<span class="identifier">WRITE_TO</span><span class="plain">(</span><span class="identifier">trueverb</span><span class="plain">, </span><span class="string">"%W"</span><span class="plain">, </span><span class="identifier">Wordings::one_word</span><span class="plain">(</span><span class="identifier">Wordings::first_wn</span><span class="plain">(</span><span class="identifier">VW</span><span class="plain">)));</span>
|
|
<span class="identifier">HTMLFiles::open_para</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">, 2, </span><span class="string">"hanging"</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">k</span><span class="plain">++ == 0) </span><span class="identifier">WRITE</span><span class="plain">(</span><span class="string">"="</span><span class="plain">); </span><span class="reserved">else</span><span class="plain"> </span><span class="identifier">WRITE</span><span class="plain">(</span><span class="string">"or"</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE</span><span class="plain">(</span><span class="string">" &quot;"</span><span class="plain">);</span>
|
|
<span class="functiontext">PL::Actions::Index::verb_definition</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">,</span>
|
|
<span class="identifier">Lexer::word_text</span><span class="plain">(</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>original_text</span><span class="plain">), </span><span class="identifier">trueverb</span><span class="plain">, </span><span class="identifier">EMPTY_WORDING</span><span class="plain">);</span>
|
|
<span class="identifier">WRITE</span><span class="plain">(</span><span class="string">"&quot;"</span><span class="plain">);</span>
|
|
<span class="identifier">Index::link</span><span class="plain">(</span><span class="identifier">OUT</span><span class="plain">, </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>original_text</span><span class="plain">);</span>
|
|
<span class="reserved">if</span><span class="plain"> (</span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>reversed</span><span class="plain">) </span><span class="identifier">WRITE</span><span class="plain">(</span><span class="string">" <i>reversed</i>"</span><span class="plain">);</span>
|
|
<span class="identifier">HTML_CLOSE</span><span class="plain">(</span><span class="string">"p"</span><span class="plain">);</span>
|
|
<span class="identifier">DISCARD_TEXT</span><span class="plain">(</span><span class="identifier">trueverb</span><span class="plain">);</span>
|
|
<span class="plain">}</span>
|
|
<span class="identifier">gl</span><span class="plain"> = </span><span class="identifier">gl</span><span class="plain">-</span><span class="element">>sorted_next_line</span><span class="plain">;</span>
|
|
<span class="plain">}</span>
|
|
<span class="plain">}</span>
|
|
</pre>
|
|
|
|
<p class="inwebparagraph"></p>
|
|
|
|
<p class="endnote">The function PL::Parsing::Lines::index_list_for_token is used in 5/gv (<a href="5-gv.html#SP14">§14</a>).</p>
|
|
|
|
<hr class="tocbar">
|
|
<ul class="toc"><li><a href="5-gv.html">Back to 'Grammar Verbs'</a></li><li><a href="5-gt.html">Continue with 'Grammar Types'</a></li></ul><hr class="tocbar">
|
|
<!--End of weave-->
|
|
</body>
|
|
</html>
|
|
|