§1. The following set of functions is an API for the main compiler to consult
with the plugins; put another way, it is also an API for the plugins to
@@ -529,8 +529,12 @@ regions plugin does with the "region" kind.
PLUGINS_CALL(SET_SUBKIND_NOTIFY_PLUG, sub, super);}
-
§34. Influencing if. If the actions plugin is not active, then the following will never be called.
-It warn plugins that a new action name has been created.
+
§34. Influencing the actions plugin. We now have a whole run of functions called only by the actions plugin, and
+therefore only when it is active.
+
+
+
Called from Actions Plugin (in if) to signal that a new action has been
+created. For example, the going plugin uses this to spot the arrival of "going".
enumNEW_ACTION_NOTIFY_PLUG
@@ -540,9 +544,10 @@ It warn plugins that a new action name has been created.
PLUGINS_CALL(NEW_ACTION_NOTIFY_PLUG, an);}
-
§35. If the actions plugin is not active, then the following will never be called.
-It invites plugins to change the action pattern clause ID associated with a
-given action variable.
+
§35. Called from Action Pattern Clauses (in if) to invite plugins to change the
+action pattern clause ID associated with a given action variable. This may be
+needed in order to cross-reference between multiple such clauses, as with
+the going action variables.
§36. If the actions plugin is not active, then the following will never be called.
-It should print a helpful name for the debugging log for the clause ID C,
-if C is a new clause ID created by the plugin.
+
§36. Called from Action Pattern Clauses (in if) to ask plugins to print a helpful
+name for the debugging log for any new clause ID C which they have created.
enumWRITE_AP_CLAUSE_ID_PLUG
@@ -565,9 +569,9 @@ if C is a new c
PLUGINS_CALL(WRITE_AP_CLAUSE_ID_PLUG, OUT, C);}
-
§37. If the actions plugin is not active, then the following will never be called.
-It should return a *_APCA aspect for the clause ID C, if C is a new
-clause ID created by the plugin.
+
§37. Called from Action Pattern Clauses (in if) to ask for the *_APCA aspect
+for the clause ID C, where C is a new clause ID created by the plugin. If
+this is not given, then the aspect will be MISC_APCA.
enumASPECT_OF_AP_CLAUSE_ID_PLUG
@@ -577,14 +581,22 @@ clause ID created by the plugin.
PLUGINS_CALL(ASPECT_OF_AP_CLAUSE_ID_PLUG, C, A);}
-
§38. If the actions plugin is not active, then the following will never be called.
-If it recognises the patterns as ways to describe an action it knows about,
-then the plugin can choose to take the decision, storing either 1 or -1 in
+
§38. Called from Action Pattern Clauses (in if) to give plugins a chance to
+decide which AP is more specific, on the basis of the extra clauses defined
+in the plugin.
+
+
+
If the plugin recognises the patterns as ways to describe an action it knows
+about, it can choose to take the decision, storing either 1 or -1 in
rv, and returning TRUE. If it instead stores 0 in rv, it can also
choose to set ignore_in, which tells the usual machinery not to judge on the
basis of the [in: ...] clause in the pattern.
+
If the plugin sees nothing relevant about the patterns, it should return FALSE
+to let the usual machinery take its course.
+
+
enumCOMPARE_AP_SPECIFICITY_PLUG
@@ -593,16 +605,57 @@ basis of the [in: ...]PLUGINS_CALL(COMPARE_AP_SPECIFICITY_PLUG, ap1, ap2, rv, ignore_in);}
-
§39.
+
§39. Called from Action Pattern Clauses (in if) to notify plugins that a clause
+matching an action variable has just been added to an action pattern.
+
§40. Called from Parse Clauses (in if) to give plugins a chance to intervene in
+the normal process of evaluating the meaning of text in an action pattern
+clause: for example, in parsing "going nowhere", the going plugin uses this
+to detect that the NOUN_AP_CLAUSE, with text "nowhere", should not be parsed
+normally. What it does it to set a bit in the bitmap bits, which it will pick
+up again and act upon when reacting to ACT_ON_ANL_ENTRY_OPTIONS_PLUG.
+
+
+
If the plugin does not set a bit in bits, the normal machinery parses the
+text of the clause in the normal way.
+
+
+
enumPARSE_AP_CLAUSE_PLUG
+
+
+intPluginCalls::parse_AP_clause(action_name *an, anl_clause *c, int *bits) {
+PLUGINS_CALL(PARSE_AP_CLAUSE_PLUG, an, c, bits);
+}
+
+
§41. Called from Parse Clauses (in if) to give plugins a chance to intervene in
+the type-checking process for a clause. Ordinarily, this would just check that
+the contents have the right kind: if matching an action variable of kind K
+then it must be a value compatible with K or a description of such.
+
+
+
By returning TRUE, a plugin can instead take responsibility for the decision
+itself, bypassing that. The outcome should then be set TRUE (it's valid)
+or FALSE (it isn't).
+
+
+
enumVALIDATE_AP_CLAUSE_PLUG
+
+
+intPluginCalls::validate_AP_clause(action_name *an, anl_clause *c, int *outcome) {
+PLUGINS_CALL(VALIDATE_AP_CLAUSE_PLUG, an, c, outcome);
+}
+
+
§42. Called from Parse Clauses (in if) to deal with the options bitmap set
+previously by a PARSE_AP_CLAUSE_PLUG call: see above.
+
enumACT_ON_ANL_ENTRY_OPTIONS_PLUG
@@ -611,7 +664,32 @@ basis of the [in: ...]PLUGINS_CALL(ACT_ON_ANL_ENTRY_OPTIONS_PLUG, entry, entry_options, fail);}
-
§43. Called from Action Patterns (in runtime) when assembling the requirement
+clauses for compiling a mattern match; this gives plugins a chance to act
+extra stipulations, which are not explicit in clauses already in the pattern.
+
§45. Influencing index. Called from Index Physical World (in index) to add something (if it wishes)
to the index description of an instance in the spatial model. For example,
the regions plugin uses this to put colour chips next to names of regions.
@@ -623,7 +701,7 @@ the regions plugin uses this to put colour chips next to names of regions.
PLUGINS_CALL(ADD_TO_WORLD_INDEX_PLUG, OUT, O);}
-
§46. Called from Index Physical World (in index) to add something (if it wishes)
to the textual description of an instance in the spatial model. For example,
the mapping plugin uses this to say where a door leads.
diff --git a/docs/if-module/1-im.html b/docs/if-module/1-im.html
index f370c47f3..af2c7c9f0 100644
--- a/docs/if-module/1-im.html
+++ b/docs/if-module/1-im.html
@@ -190,7 +190,7 @@ nothing except to be a parent to them; it has no activation function.
times_plugin = PluginManager::new(TimesOfDay::start, I"times of day", ifp);actions_plugin = PluginManager::new(&ActionsPlugin::start, I"actions", ifp);
-going_plugin = PluginManager::new(&Going::start, I"going", actions_plugin);
+going_plugin = PluginManager::new(&GoingPlugin::start, I"going", actions_plugin);parsing_plugin = PluginManager::new(&ParsingPlugin::start, I"command", ifp);showme_plugin = PluginManager::new(&RTShowmeCommand::start, I"showme", parsing_plugin);
diff --git a/docs/if-module/4-ac.html b/docs/if-module/4-ac.html
index 8aae78177..565aabd65 100644
--- a/docs/if-module/4-ac.html
+++ b/docs/if-module/4-ac.html
@@ -80,10 +80,10 @@ a test of what the current action is.
This is represented in the parse tree as the twig:
-
TEST_VALUE_NT
- CONSTANT_NT
-
-
+
+ TEST_VALUE_NT
+ CONSTANT_NT
+
where the constant below is the action seen as a noun — linguistically, a
"gerund". It will always have the kind K_stored_action or K_description_of_action,
depending on whether the test is against an explicit action or something vaguer.
@@ -96,7 +96,7 @@ depending on whether the test is against an explicit action or something vaguer.
parse_node *AConditions::new_action_TEST_VALUE(action_pattern *ap, wordingW) {if (ap == NULL) internal_error("null action pattern");parse_node *spec = Node::new_with_words(TEST_VALUE_NT, W);
-spec->down = ARvalues::from_action_pattern(ap);
+spec->down = ARvalues::from_action_pattern(ap);Node::set_text(spec->down, W);returnspec;}
@@ -117,8 +117,8 @@ depending on whether the test is against an explicit action or something vaguer.
intAConditions::is_action_TEST_VALUE(parse_node *spec) {if ((Node::is(spec, TEST_VALUE_NT)) &&
- ((ARvalues::to_action_pattern(spec->down)) ||
- (ARvalues::to_explicit_action(spec->down)))) returnTRUE;
+ ((ARvalues::to_action_pattern(spec->down)) ||
+ (ARvalues::to_explicit_action(spec->down)))) returnTRUE;returnFALSE;}
@@ -136,7 +136,7 @@ reconstruct the original action pattern which led to this condition:
action_pattern *AConditions::pattern_from_action_TEST_VALUE(parse_node *spec) {if (AConditions::is_action_TEST_VALUE(spec)) {parse_node *gerund = AConditions::gerund_from_TEST_VALUE(spec);
-action_pattern *ap = ARvalues::to_action_pattern(gerund);
+action_pattern *ap = ARvalues::to_action_pattern(gerund);if (ap == NULL) {explicit_action *ea = Node::get_constant_explicit_action(gerund);if (ea) ap = ea->as_described;
@@ -160,7 +160,7 @@ reconstruct the original action pattern which led to this condition:
}
diff --git a/docs/if-module/4-act.html b/docs/if-module/4-act.html
index 3cbc703e5..1f594eb07 100644
--- a/docs/if-module/4-act.html
+++ b/docs/if-module/4-act.html
@@ -213,7 +213,7 @@ have to correspond to names referenced in }
§6. When text is parsed to an action pattern, the result can be stored as a
+
§5. When text is parsed to an action pattern, the result can be stored as a
constant in two ways. If the pattern unambiguously describes a single explicit
action, the result has the kind "stored action" and corresponds to an
explicit_action object; if the pattern is looser than that, the result
@@ -156,7 +154,7 @@ or "taking the golden telephone in the presence of Mr Wu" would all be
explicit_action *ARvalues::to_explicit_action(parse_node *spec) {CONV_TO(explicit_action) }
-
§7. Finally, for a named action pattern, constant values correspond to
+
§6. Finally, for a named action pattern, constant values correspond to
named_action_pattern objects. These are actually never used at run-time
and do not appear as rvalues in any permanent way inside the compiler, so
the kind K_description_of_action is given to them only on principle. If
@@ -169,7 +167,7 @@ they were used as values, this is the kind we would probably give them.
named_action_pattern *ARvalues::to_named_action_pattern(parse_node *spec) {CONV_TO(named_action_pattern) }
-
§8. It's not useful to be able to compare description of action constants for
+
§7. It's not useful to be able to compare description of action constants for
equality in this sense. There would be a case for doing so with stored actions,
but in practice there seems little need, so for the moment we do not.
@@ -178,7 +176,7 @@ but in practice there seems little need, so for the moment we do not.
intARvalues::compare_CONSTANT(parse_node *spec1, parse_node *spec2, int *rv) {kind *K = Node::get_kind_of_value(spec1);if (Kinds::eq(K, K_action_name)) {
-if (ARvalues::to_action_name(spec1) == ARvalues::to_action_name(spec2)) {
+if (ARvalues::to_action_name(spec1) == ARvalues::to_action_name(spec2)) { *rv = TRUE; } *rv = FALSE;
@@ -188,7 +186,7 @@ but in practice there seems little need, so for the moment we do not.
}
diff --git a/docs/if-module/4-anaa.html b/docs/if-module/4-anaa.html
index 63ccf3a4c..97db665a5 100644
--- a/docs/if-module/4-anaa.html
+++ b/docs/if-module/4-anaa.html
@@ -275,7 +275,7 @@ so that it can indeed be used as a value.
if (Node::get_type(py) == ACTION_NT) {action_pattern *ap = Node::get_action_meaning(py);if (ap) {
-parse_node *val = ARvalues::from_action_pattern(ap);
+parse_node *val = ARvalues::from_action_pattern(ap);if (Rvalues::is_CONSTANT_of_kind(val, K_stored_action)) {Refiner::give_spec_to_noun(py, val);returnTRUE;
@@ -286,7 +286,7 @@ so that it can indeed be used as a value.
}
diff --git a/docs/if-module/4-anl.html b/docs/if-module/4-anl.html
index 122655813..afd68737a 100644
--- a/docs/if-module/4-anl.html
+++ b/docs/if-module/4-anl.html
@@ -453,7 +453,7 @@ in the final AP.
structparse_node *evaluation;} anl_clause;
-
The structure anl_clause is accessed in 4/apc, 4/gng, 4/pc and here.
+
The structure anl_clause is accessed in 4/apc, 4/pc, 4/gng and here.
§16. And this is convenient for looking through them:
-anl_entry *ActionNameLists::nap_entry(named_action_pattern *nap, wordingW, wordingTW) {
+anl_entry *ActionNameLists::nap_entry(named_action_pattern *nap, wordingW, wordingTW) {anl_entry *entry = ActionNameLists::new_entry_at(W);entry->item.nap_listed = nap;if (Wordings::nonempty(TW))
@@ -927,7 +931,6 @@ in the Laboratory", we get the following set of
-LOGIF(ACTION_PATTERN_PARSING, "Parsing ANL from %W (tense %d)\n", W, anl_parsing_tense);anl_entry *trial_entry = ActionNameLists::new_entry_at(EMPTY_WORDING);action_name *an;LOOP_OVER(an, action_name) {
@@ -939,7 +942,6 @@ in the Laboratory", we get the following set of Include the trial entry33.1.4;NoMatch: ; }
-LOGIF(ACTION_PATTERN_PARSING, "Parsing ANL from %W resulted in:\n$8\n", W, results);
§33.1.1. Ready the trial entry for another test33.1.1 =
@@ -1068,7 +1070,7 @@ sub-clauses. For example, our unramified set of results
Note that the TAIL_AP_CLAUSE clauses, which were just temporary holders
for leftover text, have gone entirely. Had it been impossible to break them
-into legal subclauses, they would have caused the result to be struct out
+into legal subclauses, they would have caused the result to be struck out
altogether. For example, this:
-voidActionNameLists::explode(anl_entry *entry) {
+voidActionNameLists::explode(anl_entry *entry) {inttc = -1;if (ActionNameLists::has_clause(entry, TAIL_AP_CLAUSE)) tc = TAIL_AP_CLAUSE;elseif (ActionNameLists::has_clause(entry, SECOND_AP_CLAUSE)) tc = SECOND_AP_CLAUSE;
@@ -1136,7 +1138,7 @@ maybe it's just "banjo" and there is then a second clause "in the Conservatoire"
anl_entry *currently_exploding_entry = NULL;intcurrently_exploding_clause = -1;intexplosions_count = 0;
-voidActionNameLists::explode_clause(anl_entry *entry, inttc, intfrom_wn) {
+voidActionNameLists::explode_clause(anl_entry *entry, inttc, intfrom_wn) {anl_entry *saved = currently_exploding_entry;intsaved_C = currently_exploding_clause;currently_exploding_entry = entry;
@@ -1249,12 +1251,13 @@ clause twice, and also means that pathological text like "in in in in in
in in in in in in in in in in in in in in in in in in in in in in in in in"
cannot cause a combinatorial nightmare; because each clause appears at
most once in any entry, the number of entries produced by ramification is
-capped at \(2^n\), where \(n\) is the number of clauses whose matching words
-appear somewhere in the text.
+capped at \(2^n\), where \(n\) is the number of different clauses whose matching
+words appear somewhere in the text. As Inform ships with only seven different
+clauses anyway, this will never be too bad.
diff --git a/docs/if-module/4-ap.html b/docs/if-module/4-ap.html
index c154b9ca8..21637e2e3 100644
--- a/docs/if-module/4-ap.html
+++ b/docs/if-module/4-ap.html
@@ -97,23 +97,23 @@ something". Action patterns become values of the kind action_pattern and named_action_pattern.
● A "past action pattern", which can never in any way be a value, is a
-description of an action which have happened in the past: for example, "dropped
-the hat". These are just a special case of action patterns.
+description of an action which may have happened in the past: for example,
+"dropped the hat". These are just a special case of action patterns.
§3. These are recognised by their English names when defined by the Standard Rules.
+
§3. This is recognised by its English name when defined by the Standard Rules.
(So there is no need to translate this to other languages.)
@@ -179,7 +179,7 @@ a "specification" text as one, and have to make their own arrangements:
intActionsPlugin::actions_offered_specification(parse_node *owner, wordingW) {if (Rvalues::is_CONSTANT_of_kind(owner, K_action_name)) {IXActions::actions_set_specification_text(
-ARvalues::to_action_name(owner), Wordings::first_wn(W));
+ARvalues::to_action_name(owner), Wordings::first_wn(W));returnTRUE; }returnFALSE;
@@ -487,7 +487,7 @@ to nothing".
}
diff --git a/docs/if-module/4-as.html b/docs/if-module/4-as.html
index 0a65be0f8..51fe74cad 100644
--- a/docs/if-module/4-as.html
+++ b/docs/if-module/4-as.html
@@ -227,11 +227,11 @@ preferred way to do that is to use activities for selecting missing parameters.
returnan->semantics.second_access;}
-kind *ActionSemantics::kind_of_noun(action_name *an) {
+kind *ActionSemantics::kind_of_noun(action_name *an) {returnan->semantics.noun_kind;}
-kind *ActionSemantics::kind_of_second(action_name *an) {
+kind *ActionSemantics::kind_of_second(action_name *an) {returnan->semantics.second_kind;}
@@ -356,7 +356,7 @@ clear from the implementation in }
diff --git a/docs/if-module/4-av.html b/docs/if-module/4-av.html
index ed06846f6..287d4f58f 100644
--- a/docs/if-module/4-av.html
+++ b/docs/if-module/4-av.html
@@ -81,7 +81,7 @@ into creations of action variables:
intActionVariables::actions_offered_property(kind *K, parse_node *owner, parse_node *prop) {if (Kinds::eq(K, K_action_name)) {
-action_name *an = ARvalues::to_action_name(owner);
+action_name *an = ARvalues::to_action_name(owner);if (an == NULL) internal_error("failed to extract action-name structure");if (global_pass_state.pass == 1) {Require the variable to have an explicit name1.1;
@@ -302,7 +302,7 @@ action patterns. For example, the Standard Rules define:
}
diff --git a/docs/if-module/4-ea.html b/docs/if-module/4-ea.html
index 865947b63..0a40a9c5f 100644
--- a/docs/if-module/4-ea.html
+++ b/docs/if-module/4-ea.html
@@ -97,7 +97,7 @@ position of being neither too specific, nor too unspecific:
defineOVERSPECIFIC_EA_FAILURE2
-explicit_action *ExplicitActions::from_action_pattern(action_pattern *ap, int *reason) {
+explicit_action *ExplicitActions::from_action_pattern(action_pattern *ap, int *reason) {if (ExplicitActions::ap_underspecific(ap)) { *reason = UNDERSPECIFIC_EA_FAILURE; returnNULL; }if (ExplicitActions::ap_overspecific(ap)) { *reason = OVERSPECIFIC_EA_FAILURE; returnNULL; } *reason = 0;
@@ -155,7 +155,7 @@ action (example: "taking") or it does specify them, but too vaguely (example:
}
diff --git a/docs/if-module/4-gng.html b/docs/if-module/4-gng.html
index 9e9bc5b66..f7e2207e9 100644
--- a/docs/if-module/4-gng.html
+++ b/docs/if-module/4-gng.html
@@ -76,19 +76,29 @@ function togglePopup(material_id) {
§1. The "going" action, allowing actors to move from room to room in the spatial
map of the world model, is by far the most intricately implemented. Reflecting
that, we provide quite a lot of hard-wired compiler support for it, in the form
-of a plugin. If the actions plugin is not also active, none of the functions
-below will ever be called, whether or not going is active.
+of this plugin.
+
+
+
Note that if the actions plugin is not also active, none of the functions
+below will ever be called.
§2. Firstly, we have to recognise the action we will treat differently, which
@@ -104,7 +114,7 @@ we do by its (English) name in the Standard Rules:
action_name *going_action = NULL;
-intGoing::new_action_notify(action_name *an) {
+intGoingPlugin::new_action_notify(action_name *an) {if (<going-action>(ActionNameNames::tensed(an, IS_TENSE))) going_action = an;returnFALSE;}
@@ -113,7 +123,7 @@ we do by its (English) name in the Standard Rules:
-intGoing::id(void) {
+intGoingPlugin::id(void) {if (going_action == NULL) return0;returnRTActions::action_variable_set_ID(going_action);}
@@ -130,7 +140,7 @@ aspect, and the other three share a new one.
enumGOING_APCA
-intGoing::write_clause_ID(OUTPUT_STREAM, intC) {
+intGoingPlugin::write_clause_ID(OUTPUT_STREAM, intC) {switch (C) {caseGOING_FROM_AP_CLAUSE:WRITE("going-from"); returnTRUE;caseGOING_TO_AP_CLAUSE:WRITE("going-to"); returnTRUE;
@@ -141,7 +151,7 @@ aspect, and the other three share a new one.
returnFALSE;}
-intGoing::aspect(intC, int *A) {
+intGoingPlugin::aspect(intC, int *A) {switch (C) {caseGOING_FROM_AP_CLAUSE: *A = IN_APCA; returnTRUE;caseGOING_TO_AP_CLAUSE: *A = IN_APCA; returnTRUE;
@@ -163,10 +173,10 @@ a special ID number of our choice.
§14. Each clause can be within one of up to two kinds, or else can be "nothing"
@@ -298,7 +308,7 @@ or unspecified:
parse_node *PM_GoingWrongKind_issued_at = NULL;parse_node *PM_GoingWithoutObject_issued_at = NULL;
-intGoing::check_clause(parse_node *spec, char *keyword, kind *ka, kind *kb) {
+intGoingPlugin::check_clause(parse_node *spec, char *keyword, kind *ka, kind *kb) {if (spec == NULL) returnTRUE;if (Rvalues::is_nothing_object_constant(spec)) returnTRUE;if (Specifications::is_description_like(spec)) {
@@ -345,7 +355,7 @@ to make sure it actually exists. So this can be used to see if the need arises:
@@ -178,7 +178,7 @@ if and only if it appears in one of the patterns in the list:
}
diff --git a/docs/if-module/4-pap.html b/docs/if-module/4-pap.html
index bd9dd94dc..8fe83f4f9 100644
--- a/docs/if-module/4-pap.html
+++ b/docs/if-module/4-pap.html
@@ -88,12 +88,12 @@ because it fails this one does not mean it is wrong.) To improve our chances,
the code below sets the following global variable on each failure.
-
§9. Note that the three present-tense cases all allow the abbreviated form
@@ -476,8 +476,8 @@ name; so we needn't spend any further time.
if (Wordings::empty(W)) internal_error("PAP on illegal word range");if (Lexer::word(Wordings::first_wn(W)) == OPENBRACE_V) returnNULL;unsignedintd = Vocabulary::disjunction_of_flags(W);
-if (((ParseActionPatterns::current_tense() == IS_TENSE) && ((d & (ACTION_PARTICIPLE_MC+NAMED_AP_MC)) == 0))) {
-LOGIF(ACTION_PATTERN_PARSING, "No participle found in: %W\n", W);
+if (((ParseActionPatterns::current_tense() == IS_TENSE) &&
+ ((d & (ACTION_PARTICIPLE_MC+NAMED_AP_MC)) == 0))) {pap_failure_reason = NOPARTICIPLE_PAPF;returnNULL; }
@@ -527,12 +527,37 @@ special clause of its own.
<ap-five>::=
-<ap-six>when/while<ap-five-condition>|==> { 0, RP[1] }; action_pattern *ap = *XP; APClauses::set_spec(ap, WHEN_AP_CLAUSE, RP[2]); if (pap_failure_reason == MISC_PAPF) pap_failure_reason = WHENOKAY_PAPF;
-<ap-six>|==> { 0, RP[1] };
-...when/while<ap-five-condition>|==> { 0, NULL }; pap_failure_reason = WHENOKAY_PAPF; return FALSE; used only to diagnose problems
-...when/while...==> { 0, NULL }; if (pap_failure_reason != WHENOKAY_PAPF) pap_failure_reason = WHEN_PAPF; return FALSE; used only to diagnose problems
+<ap-six>when/while<ap-five-condition>|==>Succeed with when okay14.1;
+<ap-six>|==> { pass 1 };
+...when/while<ap-five-condition>|==>Fail with when okay14.2;
+...when/while...==>Fail with when not okay14.3;
§15. <ap-five-condition> is really just <s-condition> in disguise — i.e.,
it matches a standard Inform condition — but it's implemented as an internal
to enable Inform to set up a stack frame if there isn't one already, and so on.
@@ -546,16 +571,16 @@ to enable Inform to set up a stack frame if there isn't one already, and so on.
Frames::get_stvol(),all_nonempty_stacked_action_vars);LOGIF(ACTION_PATTERN_PARSING, "A when clause <%W> is suspected.\n", W);
-parse_node *wts = NULL;
+parse_node *when_cond = NULL;ints = pap_failure_reason;intsaved = ParseActionPatterns::exit_mode(PERMIT_TRYING_OMISSION);
-if (<s-condition>(W)) wts = <<rp>>;
+if (<s-condition>(W)) when_cond = <<rp>>;pap_failure_reason = s;ParseActionPatterns::restore_mode(saved);if (phsf) Frames::remove_nonphrase_stack_frame();
-if ((wts) && (Dash::validate_conditional_clause(wts))) {
-LOGIF(ACTION_PATTERN_PARSING, "When clause validated: $P.\n", wts);
- ==> { -, wts };
+if ((when_cond) && (Dash::validate_conditional_clause(when_cond))) {
+LOGIF(ACTION_PATTERN_PARSING, "When clause validated: $P.\n", when_cond);
+ ==> { -, when_cond };returnTRUE; } ==> { failnonterminal };
@@ -589,7 +614,7 @@ so what's left can't very efficiently be written in Preform.
§1.1.1. Now each clause's text must be evaluated: for example, on the clause
+[in-presence: hans] we will have to evaluate "Hans".
+
+
+
Note the special case for actions whose second noun has the kind K_understanding,
+meaning that they hold topics of conversation ("ask Hans about cosmic rays").
+There is ordinarily no way in Inform to write a literal of this kind, but here
+we are allowed to write a text literal instead, and it is automatically converted.
+
+
+
Parse the clauses1.1.1 =
intsaved_pap = pap_failure_reason;LOOP_THROUGH_ANL_CLAUSES(c, entry) {
+if (fail) break;
+LOG_INDENT;
+if (Log::aspect_switched_on(ACTION_PATTERN_PARSING_DA)) {
+LOG("parsing "); ActionNameLists::log_clause(c); LOG(" - ");
+ }if (Wordings::nonempty(c->clause_text)) {
-intopts = Going::divert_clause_parsing(an, c);
-if (opts >= 0) {
+intopts = 0; PluginCalls::parse_AP_clause(an, c, &opts);
+if (opts != 0) {entry_options |= opts; } elseif ((c->clause_ID == SECOND_AP_CLAUSE) && (an) && (K_understanding) && (Kinds::eq(ActionSemantics::kind_of_second(an), K_understanding)) &&
@@ -202,15 +217,48 @@ crucial: options near the top of the list are preferred to those lower down.
if ((K_understanding) && (Rvalues::is_CONSTANT_of_kind(c->evaluation, K_text)))Node::set_kind_of_value(c->evaluation, K_understanding); }
+if (Log::aspect_switched_on(ACTION_PATTERN_PARSING_DA)) {
+if (fail) LOG("fail\n");
+elseLOG("$P\n", c->evaluation);
+ }
+LOG_OUTDENT; }pap_failure_reason = saved_pap;
§1.1.2. Typecheck or otherwise validate the clauses1.1.2 =
+
§1.1.2. The "operands" of an action pattern are the nouns to which it applies: for
+example, in "Kevin taking or dropping something", the operand is "something".
+We treat words like "something" specially to avoid them being read as
+"some thing" and thus forcing the kind of the operand to be "thing".
+
§1.1.3. Supposing that we managed to find values for each clause, we might still
+have impossible ones: "putting 101 on false", say, where the noun seems to
+be the number 101 and the second noun the truth state "false". So we need
+to typecheck each clause.
+
+
+
Typecheck or otherwise validate the clauses1.1.3 =
§1.2. Reject the resulting list if two or more entries contain clauses1.2 =
+
§1.2. This is where heterogenous patterns like "dropping a thing or taking a
+container" are thrown out: only the last-placed action is allowed to have
+clauses.
+
+
+
Reject the resulting list if two or more entries contain clauses1.2 =
@@ -249,11 +321,27 @@ crucial: options near the top of the list are preferred to those lower down.
N++;if (N > 1) {pap_failure_reason = MIXEDNOUNS_PAPF;
+LOGIF(ACTION_PATTERN_PARSING, "Rejecting with mixed nouns\n");returnNULL; }
§1.3. Reject the resulting list if, given the clauses, two actions are immiscible1.3 =
+
§1.3. And this is where impossible mixtures of actions are thrown out: for
+example, if there is an action "setting" whose noun is a number, then
+"taking or setting 50" will be thrown out because the two actions here
+disagree about the meaning of the noun.
+
+
+
Similarly, "looking or taking a vehicle" is thrown out because looking has
+no noun.
+
+
+
This is done in the interests of having a type-safe way to compile the
+pattern check, but really it also avoids allowing action patterns which
+look like syllepses.
+
+
+
Reject the resulting list if, given the clauses, two actions are immiscible1.3 =
@@ -303,11 +391,15 @@ crucial: options near the top of the list are preferred to those lower down.
if (immiscible) {pap_failure_reason = IMMISCIBLE_PAPF;
+LOGIF(ACTION_PATTERN_PARSING, "Rejecting with immiscible actions\n");returnNULL; }
§1.4. Produce and return an action pattern from what survives of the list1.4 =
+
§1.4. Fanfares and trumpets voluntary:
+
+
+
Produce and return an action pattern from what survives of the list1.4 =
@@ -316,7 +408,8 @@ crucial: options near the top of the list are preferred to those lower down.
if ((first) && ((first->action_listed) || (first->nap_listed))) ap->action_list = list;LOOP_THROUGH_ANL(entry, list)LOOP_THROUGH_ANL_CLAUSES(c, entry) {
-LOGIF(ACTION_PATTERN_PARSING, "Writing %d '%W'\n", c->clause_ID, c->clause_text);
+LOGIF(ACTION_PATTERN_PARSING,
+"Succeeds with clause %d = '%W'\n", c->clause_ID, c->clause_text);if (c->stv_to_match)APClauses::set_action_variable_spec(ap, c->stv_to_match, c->evaluation);else
@@ -325,25 +418,8 @@ crucial: options near the top of the list are preferred to those lower down.
returnap;
§2. The "operands" of an action pattern are the nouns to which it applies: for
-example, in "Kevin taking or dropping something", the operand is "something".
-We treat words like "something" specially to avoid them being read as
-"some thing" and thus forcing the kind of the operand to be "thing".
-
diff --git a/docs/if-module/index.html b/docs/if-module/index.html
index 1ccfdb91b..67b369248 100644
--- a/docs/if-module/index.html
+++ b/docs/if-module/index.html
@@ -243,11 +243,6 @@
Action Pattern Clauses -
Pattern-matches on individual nouns in an action are called clauses.
-
-
+ A plugin to provide a little extra support for the "going" action.
+
diff --git a/docs/imperative-module/3-pu.html b/docs/imperative-module/3-pu.html
index 3f9579420..577506f7f 100644
--- a/docs/imperative-module/3-pu.html
+++ b/docs/imperative-module/3-pu.html
@@ -1291,7 +1291,7 @@ might have gone wrong.
NAP_problem_explained = TRUE;returnTRUE; }
-if (form == ACTOR_EXPLICITLY_PLAYER) {
+if (form == ACTOR_EXP_PLAYER) {Problems::issue_problem_segment("'%4' would have been okay except for using the word 'trying', ""which isn't allowed in a list like this; ");
diff --git a/docs/runtime-module/2-emt.html b/docs/runtime-module/2-emt.html
index a53fbdf28..bb9272ce8 100644
--- a/docs/runtime-module/2-emt.html
+++ b/docs/runtime-module/2-emt.html
@@ -84,7 +84,7 @@ function togglePopup(material_id) {
inter_tree *I7_generation_tree = NULL;
-inter_tree *Emit::tree(void) {
+inter_tree *Emit::tree(void) {returnI7_generation_tree;}
diff --git a/docs/runtime-module/2-hrr.html b/docs/runtime-module/2-hrr.html
index 46ddbe194..f7824b58b 100644
--- a/docs/runtime-module/2-hrr.html
+++ b/docs/runtime-module/2-hrr.html
@@ -1723,7 +1723,7 @@ function togglePopup(material_id) {
§4.
-inter_name *Hierarchy::find(intid) {
+inter_name *Hierarchy::find(intid) {returnHierarchyLocations::find(Emit::tree(), id);}
diff --git a/docs/runtime-module/4-tv.html b/docs/runtime-module/4-tv.html
index c633de0b8..704fa0041 100644
--- a/docs/runtime-module/4-tv.html
+++ b/docs/runtime-module/4-tv.html
@@ -123,7 +123,7 @@ hacky constructs which only the SR should ever refer to.
returni6_glob_VAR;}
-nonlocal_variable *RTTemporaryVariables::from_nve(nonlocal_variable_emissionnve, kind *K) {
+nonlocal_variable *RTTemporaryVariables::from_nve(nonlocal_variable_emissionnve, kind *K) {RTVariables::set_I6_identifier(i6_glob_VAR, FALSE, nve);RTVariables::set_I6_identifier(i6_glob_VAR, TRUE, nve);NonlocalVariables::set_kind(i6_glob_VAR, K);
diff --git a/docs/runtime-module/4-vrb.html b/docs/runtime-module/4-vrb.html
index 4b7ecef33..8cad6cecd 100644
--- a/docs/runtime-module/4-vrb.html
+++ b/docs/runtime-module/4-vrb.html
@@ -143,7 +143,7 @@ function togglePopup(material_id) {
returnnve;}
-nonlocal_variable_emissionRTVariables::nve_from_mstack(intN, intindex, intallow_outside) {
+nonlocal_variable_emissionRTVariables::nve_from_mstack(intN, intindex, intallow_outside) {nonlocal_variable_emissionnve = RTVariables::new_nve();if (allow_outside)WRITE_TO(nve.textual_form, "(MStack-->MstVON(%d,%d))", N, index);
diff --git a/docs/runtime-module/5-act.html b/docs/runtime-module/5-act.html
index 5f1fd73cd..7909624b5 100644
--- a/docs/runtime-module/5-act.html
+++ b/docs/runtime-module/5-act.html
@@ -502,7 +502,7 @@ infrastructure, and we access it with a single call.
}
diff --git a/docs/runtime-module/5-ap.html b/docs/runtime-module/5-ap.html
index 948de5f49..935dfd6c3 100644
--- a/docs/runtime-module/5-ap.html
+++ b/docs/runtime-module/5-ap.html
@@ -167,10 +167,10 @@ exceptional case where the clause doesn't act on a single I6 global,
and in this case we therefore ignore I6_global_name.
-intRTActionPatterns::compile_pattern_match_clause(intf,
-value_holster *VH, nonlocal_variable *I6_global_variable,
+voidRTActionPatterns::compile_pattern_match_clause(value_holster *VH,
+nonlocal_variable *I6_global_variable,parse_node *spec, kind *verify_as_kind, intadapt_region) {
-if (spec == NULL) returnf;
+if (spec == NULL) return;parse_node *I6_var_TS = NULL;if (I6_global_variable)
@@ -179,16 +179,16 @@ and in this case we therefore ignore intis_parameter = FALSE;if (I6_global_variable == parameter_object_VAR) is_parameter = TRUE;
-returnRTActionPatterns::compile_pattern_match_clause_inner(f,
-VH, I6_var_TS, is_parameter, spec, verify_as_kind, adapt_region);
+RTActionPatterns::compile_pattern_match_clause_inner(VH,
+I6_var_TS, is_parameter, spec, verify_as_kind, adapt_region);}
-intRTActionPatterns::compile_pattern_match_clause_inner(intf,
-value_holster *VH, parse_node *I6_var_TS, intis_parameter,
+voidRTActionPatterns::compile_pattern_match_clause_inner(value_holster *VH,
+parse_node *I6_var_TS, intis_parameter,parse_node *spec, kind *verify_as_kind, intadapt_region) {intforce_proposition = FALSE;
-if (spec == NULL) returnf;
+if (spec == NULL) return;LOGIF(ACTION_PATTERN_COMPILATION, "[MPE on $P: $P]\n", I6_var_TS, spec);kind *K = Specifications::to_kind(spec);
@@ -200,7 +200,7 @@ and in this case we therefore ignore "say 'Instead of taking a value: ...' because the taking action ""applies to objects; the vaguest you're allowed to be is 'Instead ""of taking an object: ...'.");
-returnTRUE;
+return; }wordingC = Descriptions::get_calling(spec);
@@ -336,7 +336,6 @@ and in this case we therefore ignore if (Wordings::nonempty(C)) {Produce::up(Emit::tree()); }
-returnTRUE;}
§5.
@@ -394,6 +393,8 @@ and in this case we therefore ignore enumREQUESTER_DOESNT_EXIST_CPMCenumACTOR_MATCHES_CPMCenumACTION_MATCHES_CPMC
+enumSET_SELF_TO_ACTOR_CPMC
+enumWHEN_CONDITION_HOLDS_CPMCenumNOUN_EXISTS_CPMCenumNOUN_IS_INP1_CPMCenumSECOND_EXISTS_CPMC
@@ -407,15 +408,10 @@ and in this case we therefore ignore enumACTOR_LOCATION_MATCHES_CPMCenumPARAMETER_MATCHES_CPMCenumOPTIONAL_CLAUSE_CPMC
-enumNOWHERE_CPMC
-enumSOMEWHERE_CPMC
-enumNOT_NOWHERE_CPMCenumPRESENCE_OF_MATCHES_CPMCenumPRESENCE_OF_IN_SCOPE_CPMCenumLOOP_OVER_SCOPE_WITH_CALLING_CPMCenumLOOP_OVER_SCOPE_WITHOUT_CALLING_CPMC
-enumSET_SELF_TO_ACTOR_CPMC
-enumWHEN_CONDITION_HOLDS_CPMCdefineMAX_CPM_CLAUSES256defineCPMC_NEEDED(C, A) {if (cpm_count >= MAX_CPM_CLAUSES) internal_error("action pattern grossly overcomplex");
@@ -529,13 +525,7 @@ and in this case we therefore ignore CPMC_NEEDED(OPTIONAL_CLAUSE_CPMC, apoc); }
-if (Going::going_nowhere(ap)) {
-CPMC_NEEDED(NOWHERE_CPMC, NULL);
- } elseif (Going::going_somewhere(ap)) {
-CPMC_NEEDED(SOMEWHERE_CPMC, NULL);
- } elseif (Going::need_to_check_destination_exists(ap)) {
-CPMC_NEEDED(NOT_NOWHERE_CPMC, NULL);
- }
+PluginCalls::set_pattern_match_requirements(ap, &cpm_count, needed, needed_apoc);if (APClauses::spec(ap, IN_THE_PRESENCE_OF_AP_CLAUSE) != NULL) {instance *to_be_present =
@@ -577,10 +567,9 @@ and in this case we therefore ignore intranges_from[4], ranges_to[4], ranges_count[4];CPMC_RANGE(0, ACTOR_IS_PLAYER_CPMC, ACTOR_MATCHES_CPMC);CPMC_RANGE(1, ACTION_MATCHES_CPMC, ACTION_MATCHES_CPMC);
-CPMC_RANGE(2, NOUN_EXISTS_CPMC, LOOP_OVER_SCOPE_WITHOUT_CALLING_CPMC);
+CPMC_RANGE(2, NOUN_EXISTS_CPMC, NO_DEFINED_CPMC_VALUES);CPMC_RANGE(3, SET_SELF_TO_ACTOR_CPMC, WHEN_CONDITION_HOLDS_CPMC);
-intf = FALSE;intrange_to_compile = 0;LocalVariables::begin_condition_emit();
@@ -693,6 +682,7 @@ and in this case we therefore ignore WRITE_TO(C, "So %d", cpmc);Emit::code_comment(C);DISCARD_TEXT(C)
+if (PluginCalls::compile_pattern_match_clause(VH, ap, cpmc) == FALSE)switch (cpmc) {caseACTOR_IS_PLAYER_CPMC:Produce::inv_primitive(Emit::tree(), EQ_BIP);
@@ -719,7 +709,7 @@ and in this case we therefore ignore Produce::up(Emit::tree());break;caseACTOR_MATCHES_CPMC:
-RTActionPatterns::compile_pattern_match_clause(f, VH, I6_actor_VAR, APClauses::spec(ap, ACTOR_AP_CLAUSE), K_object, FALSE);
+RTActionPatterns::compile_pattern_match_clause(VH, I6_actor_VAR, APClauses::spec(ap, ACTOR_AP_CLAUSE), K_object, FALSE);break;caseACTION_MATCHES_CPMC:RTActions::emit_anl(ap->action_list);
@@ -745,25 +735,25 @@ and in this case we therefore ignore Produce::up(Emit::tree());break;caseNOUN_MATCHES_AS_OBJECT_CPMC:
-RTActionPatterns::compile_pattern_match_clause(f, VH, I6_noun_VAR, APClauses::spec(ap, NOUN_AP_CLAUSE),
+RTActionPatterns::compile_pattern_match_clause(VH, I6_noun_VAR, APClauses::spec(ap, NOUN_AP_CLAUSE),kind_of_noun, FALSE);break;caseNOUN_MATCHES_AS_VALUE_CPMC:
-RTActionPatterns::compile_pattern_match_clause(f, VH,
+RTActionPatterns::compile_pattern_match_clause(VH,RTTemporaryVariables::from_iname(Hierarchy::find(PARSED_NUMBER_HL), kind_of_noun),APClauses::spec(ap, NOUN_AP_CLAUSE), kind_of_noun, FALSE);break;caseSECOND_MATCHES_AS_OBJECT_CPMC:
-RTActionPatterns::compile_pattern_match_clause(f, VH, I6_second_VAR, APClauses::spec(ap, SECOND_AP_CLAUSE),
+RTActionPatterns::compile_pattern_match_clause(VH, I6_second_VAR, APClauses::spec(ap, SECOND_AP_CLAUSE),kind_of_second, FALSE);break;caseSECOND_MATCHES_AS_VALUE_CPMC:
-RTActionPatterns::compile_pattern_match_clause(f, VH,
+RTActionPatterns::compile_pattern_match_clause(VH,RTTemporaryVariables::from_iname(Hierarchy::find(PARSED_NUMBER_HL), kind_of_second),APClauses::spec(ap, SECOND_AP_CLAUSE), kind_of_second, FALSE);break;casePLAYER_LOCATION_MATCHES_CPMC:
-RTActionPatterns::compile_pattern_match_clause(f, VH, real_location_VAR, APClauses::spec(ap, IN_AP_CLAUSE), K_object, TRUE);
+RTActionPatterns::compile_pattern_match_clause(VH, real_location_VAR, APClauses::spec(ap, IN_AP_CLAUSE), K_object, TRUE);break;caseACTOR_IN_RIGHT_PLACE_CPMC:Produce::inv_primitive(Emit::tree(), STORE_BIP);
@@ -776,66 +766,28 @@ and in this case we therefore ignore Produce::up(Emit::tree());break;caseACTOR_LOCATION_MATCHES_CPMC:
-RTActionPatterns::compile_pattern_match_clause(f,
-VH, actor_location_VAR, APClauses::spec(ap, IN_AP_CLAUSE), K_object, TRUE);
+RTActionPatterns::compile_pattern_match_clause(VH, actor_location_VAR,
+APClauses::spec(ap, IN_AP_CLAUSE), K_object, TRUE);break;casePARAMETER_MATCHES_CPMC: {kind *saved_kind = NonlocalVariables::kind(parameter_object_VAR);NonlocalVariables::set_kind(parameter_object_VAR, ap->parameter_kind);
-RTActionPatterns::compile_pattern_match_clause(f, VH,
+RTActionPatterns::compile_pattern_match_clause(VH,parameter_object_VAR, APClauses::spec(ap, PARAMETRIC_AP_CLAUSE), ap->parameter_kind, FALSE);NonlocalVariables::set_kind(parameter_object_VAR, saved_kind);break; }caseOPTIONAL_CLAUSE_CPMC: {kind *K = StackedVariables::get_kind(apoc->stv_to_match);
-RTActionPatterns::compile_pattern_match_clause(f, VH,
+RTActionPatterns::compile_pattern_match_clause(VH,RTTemporaryVariables::from_existing_variable(apoc->stv_to_match->underlying_var, K),apoc->clause_spec, K, APClauses::opt(apoc, ALLOW_REGION_AS_ROOM_APCOPT));break; }
-caseNOWHERE_CPMC:
-Produce::inv_primitive(Emit::tree(), EQ_BIP);
-Produce::down(Emit::tree());
-Produce::inv_primitive(Emit::tree(), LOOKUP_BIP);
-Produce::down(Emit::tree());
-Produce::val_iname(Emit::tree(), K_value, Hierarchy::find(MSTACK_HL));
-Produce::inv_call_iname(Emit::tree(), Hierarchy::find(MSTVON_HL));
-Produce::down(Emit::tree());
-Produce::val(Emit::tree(), K_number, LITERAL_IVAL, (unsignedint) Going::id());
-Produce::val(Emit::tree(), K_number, LITERAL_IVAL, 1);
-Produce::up(Emit::tree());
-Produce::up(Emit::tree());
-Produce::val(Emit::tree(), K_number, LITERAL_IVAL, 0);
-Produce::up(Emit::tree());
-break;
-caseSOMEWHERE_CPMC: {
-parse_node *somewhere = Specifications::from_kind(K_room);
-RTActionPatterns::compile_pattern_match_clause(f, VH,
-RTTemporaryVariables::from_nve(RTVariables::nve_from_mstack(Going::id(), 1, TRUE),
-K_object),
-somewhere, K_object, FALSE);
-break;
- }
-caseNOT_NOWHERE_CPMC:
-Produce::inv_primitive(Emit::tree(), NE_BIP);
-Produce::down(Emit::tree());
-Produce::inv_primitive(Emit::tree(), LOOKUP_BIP);
-Produce::down(Emit::tree());
-Produce::val_iname(Emit::tree(), K_value, Hierarchy::find(MSTACK_HL));
-Produce::inv_call_iname(Emit::tree(), Hierarchy::find(MSTVON_HL));
-Produce::down(Emit::tree());
-Produce::val(Emit::tree(), K_number, LITERAL_IVAL, (unsignedint) Going::id());
-Produce::val(Emit::tree(), K_number, LITERAL_IVAL, 1);
-Produce::up(Emit::tree());
-Produce::up(Emit::tree());
-Produce::val(Emit::tree(), K_number, LITERAL_IVAL, 0);
-Produce::up(Emit::tree());
-break;casePRESENCE_OF_MATCHES_CPMC: {instance *to_be_present =Specifications::object_exactly_described_if_any(APClauses::spec(ap, IN_THE_PRESENCE_OF_AP_CLAUSE));
-RTActionPatterns::compile_pattern_match_clause(FALSE, VH,
+RTActionPatterns::compile_pattern_match_clause(VH,RTTemporaryVariables::from_iname(RTInstances::iname(to_be_present), K_object),APClauses::spec(ap, IN_THE_PRESENCE_OF_AP_CLAUSE), K_object, FALSE);break;
@@ -959,7 +911,7 @@ and in this case we therefore ignore
-
+ Tweaks to compiling APs for the going action.
+
diff --git a/docs/values-module/2-dsh.html b/docs/values-module/2-dsh.html
index 0e2a99ab3..c03f2c99f 100644
--- a/docs/values-module/2-dsh.html
+++ b/docs/values-module/2-dsh.html
@@ -4165,7 +4165,6 @@ only when resolving ambiguities, in (4A) above.
intDash::validate_conditional_clause(parse_node *spec) {
-LOGIF(ACTION_PATTERN_PARSING, "Validating conditional clause: $P\n", spec);if (spec == NULL) returnTRUE;if (Node::is(spec, UNKNOWN_NT)) returnFALSE;if (Dash::check_condition(spec) == NEVER_MATCH) returnFALSE;
@@ -4208,7 +4207,6 @@ into treating it as such.
parse_node *vts;kind *kind_found = NULL;if (spec == NULL) returnTRUE;
-LOGIF(ACTION_PATTERN_PARSING, "Validating parameter in action pattern: $P (%u)\n", spec, K);if (Node::is(spec, UNKNOWN_NT)) gotoDontValidate;if (Specifications::is_description(spec)) {
@@ -4241,9 +4239,6 @@ into treating it as such.
returnTRUE;DontValidate:
-LOGIF(ACTION_PATTERN_PARSING,
-"Fails to validate for type-checking reasons: wanted %u, found %u\n",
-K, kind_found);last_spec_failing_to_validate = Node::duplicate(spec);last_kind_failing_to_validate = K;last_kind_found_failing_to_validate = kind_found;
diff --git a/inform7/Downloads/preform-diagnostics.txt b/inform7/Downloads/preform-diagnostics.txt
index ce82e3c00..097ce8535 100644
--- a/inform7/Downloads/preform-diagnostics.txt
+++ b/inform7/Downloads/preform-diagnostics.txt
@@ -1,6 +1,6 @@
internal nti 23 constraint (none) extremes [1, 1]
- internal hits 1165/6388 nti 24 constraint (none) extremes [0, 0]
+ internal hits 1170/6408 nti 24 constraint (none) extremes [0, 0]
internal hits 3873/7958 nti 25 constraint (none) extremes [0, 0]
@@ -4728,7 +4728,7 @@
twelfth
constraint CS = {27} extremes [1, 1]
- internal hits 200/22402 nti r0 constraint CS = {r0} extremes [1, 1]
+ internal hits 200/22422 nti r0 constraint CS = {r0} extremes [1, 1]
internal nti r1 constraint CS = {r1} extremes [1, 1]
@@ -4736,12 +4736,12 @@
internal hits 0/258 nti 22 constraint (none) extremes [1, infinity)
- hits 36284/72568 nti 18 constraint (none) extremes [1, infinity)
+ hits 36283/72566 nti 18 constraint (none) extremes [1, infinity)
English:
{...}
- (hits 7821/36284) (matched long text) constraint (none) extremes [2, infinity)
+ (hits 7821/36283) (matched long text) constraint (none) extremes [2, infinity)
{...}
- (hits 28463/28463) (matched long text) constraint (none) extremes [1, infinity)
+ (hits 28462/28462) (matched long text) constraint (none) extremes [1, infinity)
nti 19 constraint (none) extremes [1, infinity)
English:
@@ -4750,21 +4750,21 @@
{...}
constraint (none) extremes [1, infinity)
- hits 82856/165712 nti 20 constraint (none) extremes [1, infinity)
+ hits 82853/165706 nti 20 constraint (none) extremes [1, infinity)
English:
{...}
- (hits 16066/47391) (matched long text) constraint (none) extremes [2, infinity)
+ (hits 16065/47390) (matched long text) constraint (none) extremes [2, infinity)
{...}
- (hits 66790/66790) (matched long text) constraint (none) extremes [1, infinity)
+ (hits 66788/66788) (matched long text) constraint (none) extremes [1, infinity)
nti 21 constraint (none) extremes [2, infinity)
English:
{...}
constraint (none) extremes [2, infinity)
- internal hits 16517/98332 nti r2 constraint (none) extremes [1, 1]
+ internal hits 16515/98328 nti r2 constraint (none) extremes [1, 1]
- internal hits 20294/236390 nti r2 constraint (none) extremes [1, 1]
+ internal hits 20294/236382 nti r2 constraint (none) extremes [1, 1]
internal hits 2012/40436 nti r2 constraint (none) extremes [1, 1]
@@ -4917,7 +4917,7 @@
internal hits 1/8288 nti 8 constraint FS = {8} extremes [1, infinity)
- internal hits 0/1486 nti 9 constraint FS = {9} extremes [1, infinity)
+ internal hits 0/1478 nti 9 constraint FS = {9} extremes [1, infinity)
internal nti 10 constraint FS = {10} extremes [1, infinity)
@@ -5271,7 +5271,7 @@
grammatical case
(hits 1/1) (matched: 'grammatical case') constraint CS = {7} extremes [2, 2]
- internal hits 2474/41942 nti 31 constraint (none) extremes [0, 0]
+ internal hits 2474/41934 nti 31 constraint (none) extremes [0, 0]
internal hits 164/328 nti 6 constraint (none) extremes [1, infinity)
@@ -5297,16 +5297,16 @@
(hits 5/5) (matched: 'value of kind k') constraint (none) extremes [1, infinity)
- hits 5788/103654 nti r5 constraint (none) extremes [1, infinity)
+ hits 5786/103650 nti r5 constraint (none) extremes [1, infinity)
English:
( )
(hits 0/2064) constraint DS = {r5} & CW = {r2, r5} extremes [3, infinity)
^
- (hits 1589/11280) (matched: 'k') constraint CW = {r2, r5} extremes [1, infinity)
+ (hits 1589/11278) (matched: 'k') constraint CW = {r2, r5} extremes [1, infinity)
- (hits 201/9691) (matched: 'sayable value of kind k') constraint CW = {r2, r5} extremes [1, infinity)
+ (hits 201/9689) (matched: 'sayable value of kind k') constraint CW = {r2, r5} extremes [1, infinity)
- (hits 3637/9490) (matched: 'an ice cream cone') constraint CW = {r2, r5} extremes [1, infinity)
+ (hits 3635/9488) (matched: 'an ice cream cone') constraint CW = {r2, r5} extremes [1, infinity)
(hits 2/16092) (matched: 'object-based rulebook') constraint DS = {r5} extremes [2, infinity)
@@ -5326,7 +5326,7 @@
of kind
(hits 81/315) (matched: 'sayable value of kind k') constraint DS = {r5} & CW = {r2, r5} extremes [4, infinity)
- internal hits 3637/18980 nti r5 constraint CW = {r2, r5} extremes [1, infinity)
+ internal hits 3635/18976 nti r5 constraint CW = {r2, r5} extremes [1, infinity)
hits 2/32184 nti r5 constraint DS = {r5} extremes [2, infinity)
English:
@@ -5402,7 +5402,7 @@
(hits 100/224) (matched: 'sayable value') constraint (none) extremes [1, infinity)
- internal hits 1589/20086 nti r5 constraint CW = {r2, r5} extremes [1, 1]
+ internal hits 1589/20082 nti r5 constraint CW = {r2, r5} extremes [1, 1]
internal hits 220/1414 nti r5 constraint CW = {r2, r5} extremes [1, 1]
@@ -5477,29 +5477,29 @@
hits 199/10188 nti 11 constraint DW = {11, 12} extremes [2, infinity)
English:
- (hits 191/3180) (matched long text) constraint DS = {11} extremes [2, infinity)
+ (hits 191/3190) (matched long text) constraint DS = {11} extremes [2, infinity)
- (hits 8/3533) (matched long text) constraint DS = {12} extremes [3, infinity)
+ (hits 8/3516) (matched long text) constraint DS = {12} extremes [3, infinity)
- hits 191/2302 nti 11 constraint DS = {11} extremes [2, infinity)
+ hits 191/2312 nti 11 constraint DS = {11} extremes [2, infinity)
English:
volume {...}
- (hits 6/1151) (matched long text) constraint DS = {11} extremes [2, infinity)
+ (hits 6/1156) (matched long text) constraint DS = {11} extremes [2, infinity)
book {...}
- (hits 0/1145) constraint DS = {11} extremes [2, infinity)
+ (hits 0/1150) constraint DS = {11} extremes [2, infinity)
part {...}
- (hits 14/1145) (matched: 'part two - the physical world model') constraint DS = {11} extremes [2, infinity)
+ (hits 14/1150) (matched: 'part two - the physical world model') constraint DS = {11} extremes [2, infinity)
chapter {...}
- (hits 20/1131) (matched long text) constraint DS = {11} extremes [2, infinity)
+ (hits 20/1136) (matched long text) constraint DS = {11} extremes [2, infinity)
section {...}
- (hits 151/1111) (matched long text) constraint DS = {11} extremes [2, infinity)
+ (hits 151/1116) (matched long text) constraint DS = {11} extremes [2, infinity)
- hits 8/7066 nti 12 constraint DS = {12} extremes [3, infinity)
+ hits 8/7032 nti 12 constraint DS = {12} extremes [3, infinity)
English:
{...} begin/begins here
- (hits 4/3533) (matched long text) constraint DS = {12} extremes [3, infinity)
+ (hits 4/3516) (matched long text) constraint DS = {12} extremes [3, infinity)
{...} end/ends here
- (hits 4/3529) (matched: 'the standard rules end here') constraint DS = {12} extremes [3, infinity)
+ (hits 4/3512) (matched: 'the standard rules end here') constraint DS = {12} extremes [3, infinity)
hits 32/12958 nti 14 constraint (none) extremes [1, infinity)
English:
@@ -5722,9 +5722,9 @@
hits 756/14584 nti 7 constraint DS = {7} extremes [2, infinity)
English:
say {...}
- (hits 584/3129) (matched: 'say run paragraph on with special look spacing') constraint DS = {7} extremes [2, infinity)
+ (hits 584/3126) (matched: 'say run paragraph on with special look spacing') constraint DS = {7} extremes [2, infinity)
now {...}
- (hits 172/2545) (matched long text) constraint DS = {7} extremes [2, infinity)
+ (hits 172/2542) (matched long text) constraint DS = {7} extremes [2, infinity)
hits 2306/7528 nti 8 constraint DS = {8} extremes [3, infinity)
English:
@@ -5734,9 +5734,9 @@
hits 30/9858 nti 9 constraint DS = {9} extremes [2, infinity)
English:
instead {...}
- (hits 0/1698) constraint DS = {9} extremes [2, infinity)
+ (hits 0/1697) constraint DS = {9} extremes [2, infinity)
{...} instead
- (hits 30/1698) (matched long text) constraint DS = {9} extremes [2, infinity)
+ (hits 30/1697) (matched long text) constraint DS = {9} extremes [2, infinity)
hits 0/880 nti 10 constraint DS = {10} extremes [2, infinity)
English:
@@ -7016,7 +7016,7 @@
(hits 171/171) (matched: '100') constraint CS = {r0} extremes [1, 1]
minus
- (hits 0/1872) constraint DS = {12} extremes [2, 2]
+ (hits 0/1864) constraint DS = {12} extremes [2, 2]
( )
(hits 273/840) (matched: '"[current item from the multiple object list]: [run paragraph on]" ( a )') constraint DS = {12} extremes [4, 4]
@@ -7031,7 +7031,7 @@
(hits 0/1468) constraint DS = {8} extremes [2, infinity)
unicode
- (hits 0/4232) constraint DS = {12} extremes [2, infinity)
+ (hits 0/4220) constraint DS = {12} extremes [2, infinity)
(hits 0/2190) constraint DW = {9, 10, 11} extremes [2, 5]
@@ -7068,27 +7068,27 @@
hits 0/4380 nti 11 constraint DW = {9, 10, 11} extremes [2, 5]
English:
minus
- (hits 0/802) constraint DS = {9, 11} extremes [3, 5]
+ (hits 0/796) constraint DS = {9, 11} extremes [3, 5]
- (hits 0/864) constraint DS = {9} extremes [2, 4]
+ (hits 0/854) constraint DS = {9} extremes [2, 4]
- (hits 0/242) constraint DS = {10} extremes [2, 2]
+ (hits 0/252) constraint DS = {10} extremes [2, 2]
- hits 0/1728 nti 9 constraint DS = {9} extremes [2, 4]
+ hits 0/1708 nti 9 constraint DS = {9} extremes [2, 4]
English:
hour/hours
- (hits 0/189) constraint DS = {9} extremes [2, 2]
+ (hits 0/197) constraint DS = {9} extremes [2, 2]
minute/minutes
- (hits 0/189) constraint DS = {9} extremes [2, 2]
+ (hits 0/197) constraint DS = {9} extremes [2, 2]
hour/hours minute/minutes
- (hits 0/392) constraint DS = {9} extremes [4, 4]
+ (hits 0/374) constraint DS = {9} extremes [4, 4]
- hits 0/484 nti 31 constraint DS = {10} extremes [2, 2]
+ hits 0/504 nti 31 constraint DS = {10} extremes [2, 2]
English:
- (hits 0/242) constraint DS = {10} extremes [2, 2]
+ (hits 0/252) constraint DS = {10} extremes [2, 2]
- (hits 0/242) constraint DS = {10} extremes [2, 2]
+ (hits 0/252) constraint DS = {10} extremes [2, 2]
nti 10 constraint CS = {10} extremes [1, 1]
English:
@@ -7097,7 +7097,7 @@
pm
constraint CS = {10} extremes [1, 1]
- internal hits 0/484 nti 6 constraint (none) extremes [1, 1]
+ internal hits 0/504 nti 6 constraint (none) extremes [1, 1]
internal nti 7 constraint (none) extremes [1, 1]
@@ -7152,16 +7152,16 @@
internal hits 4/8 nti 15 constraint (none) extremes [1, infinity)
- internal hits 1964/5228 nti 16 constraint (none) extremes [1, infinity)
+ internal hits 1962/5224 nti 16 constraint (none) extremes [1, infinity)
internal hits 1272/3058 nti 17 constraint (none) extremes [1, infinity)
internal hits 529/1072 nti 18 constraint (none) extremes [1, infinity)
- hits 243/1728 nti 19 constraint (none) extremes [1, infinity)
+ hits 241/1724 nti 19 constraint (none) extremes [1, infinity)
English:
- (hits 191/794) (matched long text) constraint (none) extremes [1, infinity)
+ (hits 189/792) (matched long text) constraint (none) extremes [1, infinity)
(hits 52/603) (matched long text) constraint (none) extremes [1, infinity)
@@ -7370,21 +7370,21 @@
internal hits 288/62770 nti 21 constraint (none) extremes [1, infinity)
- hits 1949/4834 nti 22 constraint (none) extremes [1, infinity)
+ hits 1947/4830 nti 22 constraint (none) extremes [1, infinity)
English:
- (hits 119/399) (matched long text) constraint (none) extremes [2, infinity)
+ (hits 118/398) (matched long text) constraint (none) extremes [2, infinity)
- (hits 1830/2298) (matched long text) constraint (none) extremes [1, infinity)
+ (hits 1829/2297) (matched long text) constraint (none) extremes [1, infinity)
- hits 3127/7784 nti 31 constraint (none) extremes [1, infinity)
+ hits 3125/7780 nti 31 constraint (none) extremes [1, infinity)
English:
variable/variables
(hits 2/460) (matched: 'text variables') constraint DS = {31} extremes [2, infinity)
that/which vary/varies
(hits 59/374) (matched: 'action name based rule producing nothing that varies') constraint DS = {31} extremes [3, infinity)
- (hits 2443/3831) (matched long text) constraint (none) extremes [1, infinity)
+ (hits 2441/3829) (matched long text) constraint (none) extremes [1, infinity)
(hits 221/1388) (matched: 'Represents geographical locations, both indoor
and outdoor, which are not necessarily areas in a building. A player in one
@@ -7520,11 +7520,11 @@
(hits 173/565) (matched: 'the second noun') constraint (none) extremes [1, infinity)
- internal hits 1137/27364 nti 6 constraint (none) extremes [1, infinity)
+ internal hits 1137/27360 nti 6 constraint (none) extremes [1, infinity)
internal hits 897/18706 nti 7 constraint (none) extremes [1, infinity)
- internal hits 2296/19730 nti 8 constraint (none) extremes [1, infinity)
+ internal hits 2296/19726 nti 8 constraint (none) extremes [1, infinity)
hits 105/18392 nti 7 constraint DS = {7} extremes [3, infinity)
English:
@@ -7563,7 +7563,7 @@
hits 2149/6658 nti 13 constraint (none) extremes [2, infinity)
English:
- (hits 0/670) constraint DS = {29} & FS = {9} extremes [4, infinity)
+ (hits 0/666) constraint DS = {29} & FS = {9} extremes [4, infinity)
(hits 224/1827) (matched long text) constraint DS = {14} & FS = {6} extremes [3, infinity)
@@ -7667,7 +7667,7 @@
(hits 0/1091) constraint DS = {11} extremes [3, infinity)
- (hits 0/882) constraint DS = {12} extremes [4, infinity)
+ (hits 0/880) constraint DS = {12} extremes [4, infinity)
(hits 28/1373) (matched long text) constraint (none) extremes [1, infinity)
@@ -8276,23 +8276,23 @@
hits 400/800 nti 11 constraint (none) extremes [1, infinity)
English:
( arithmetic operation )
- (hits 16/344) (matched long text) constraint DS = {11} extremes [6, infinity)
+ (hits 16/345) (matched long text) constraint DS = {11} extremes [6, infinity)
( assignment operation )
- (hits 6/337) (matched long text) constraint DS = {11} extremes [5, infinity)
+ (hits 6/338) (matched long text) constraint DS = {11} extremes [5, infinity)
{let ... be given by ...}
- (hits 2/322) (matched long text) constraint DS = {11} extremes [6, infinity)
+ (hits 2/323) (matched long text) constraint DS = {11} extremes [6, infinity)
{let ...}
- (hits 4/345) (matched long text) constraint DS = {11} extremes [2, infinity)
+ (hits 4/346) (matched long text) constraint DS = {11} extremes [2, infinity)
{...} -- end
- (hits 0/339) constraint DS = {11} extremes [3, infinity)
+ (hits 0/340) constraint DS = {11} extremes [3, infinity)
{...} -- end conditional
- (hits 3/334) (matched long text) constraint DS = {11} extremes [4, infinity)
+ (hits 3/335) (matched long text) constraint DS = {11} extremes [4, infinity)
{...} -- end loop
- (hits 9/331) (matched long text) constraint DS = {11} extremes [4, infinity)
+ (hits 9/332) (matched long text) constraint DS = {11} extremes [4, infinity)
{...} -- in loop
- (hits 2/322) (matched: 'break -- in loop') constraint DS = {11} extremes [4, infinity)
+ (hits 2/323) (matched: 'break -- in loop') constraint DS = {11} extremes [4, infinity)
{...} -- in {###}
- (hits 0/320) constraint DS = {11} extremes [4, infinity)
+ (hits 0/321) constraint DS = {11} extremes [4, infinity)
{...}
(hits 358/358) (matched long text) constraint (none) extremes [1, infinity)
@@ -9199,12 +9199,12 @@
English:
(hits 0/703) constraint (none) extremes [1, infinity)
-
+
(hits 0/703) constraint (none) extremes [1, infinity)
(hits 595/703) (matched long text) constraint (none) extremes [1, infinity)
- internal hits 0/1406 nti 29 constraint (none) extremes [1, infinity)
+ internal hits 0/1406 nti 29 constraint (none) extremes [1, infinity)
internal hits 595/1406 nti 30 constraint (none) extremes [1, infinity)
@@ -9226,34 +9226,22 @@
internal hits 0/662 nti 31 constraint (none) extremes [1, infinity)
- hits 1/180 nti 7 constraint CS = {7} extremes [1, 1]
- English:
- going
- (hits 1/1) (matched: 'going') constraint CS = {7} extremes [1, 1]
-
- hits 0/16 nti 8 constraint CS = {8} extremes [1, 1]
- English:
- nowhere
- constraint CS = {8} extremes [1, 1]
- somewhere
- constraint CS = {8} extremes [1, 1]
-
internal hits 1197/31612 nti 6 constraint (none) extremes [0, 0]
- internal hits 1272/2544 nti 7 constraint (none) extremes [0, 0]
+ internal hits 1268/2536 nti 7 constraint (none) extremes [0, 0]
- hits 302/1272 nti 8 constraint (none) extremes [1, infinity)
+ hits 300/1268 nti 8 constraint (none) extremes [1, infinity)
English:
^
- (hits 0/636) constraint (none) extremes [1, infinity)
+ (hits 0/634) constraint (none) extremes [1, infinity)
^
- (hits 0/636) constraint (none) extremes [1, infinity)
+ (hits 0/634) constraint (none) extremes [1, infinity)
- (hits 25/636) (matched: 'the current working sack') constraint (none) extremes [1, infinity)
+ (hits 25/634) (matched: 'the current working sack') constraint (none) extremes [1, infinity)
- (hits 42/611) (matched: 'the second noun') constraint (none) extremes [1, infinity)
+ (hits 42/609) (matched: 'the second noun') constraint (none) extremes [1, infinity)
- (hits 235/569) (matched long text) constraint (none) extremes [1, infinity)
+ (hits 233/567) (matched long text) constraint (none) extremes [1, infinity)
internal hits 3/19982 nti 9 constraint (none) extremes [1, infinity)
@@ -9272,23 +9260,23 @@
(hits 0/1091) constraint DS = {11} extremes [3, infinity)
- hits 0/1764 nti 13 constraint DS = {12} extremes [4, infinity)
+ hits 0/1760 nti 13 constraint DS = {12} extremes [4, infinity)
English:
- (hits 0/882) constraint DS = {12} extremes [4, infinity)
+ (hits 0/880) constraint DS = {12} extremes [4, infinity)
hits 556/21330 nti 7 constraint (none) extremes [1, infinity)
English:
asking to try
(hits 0/1023) constraint DS = {7} extremes [5, infinity)
trying
- (hits 23/2486) (matched long text) constraint DS = {7} extremes [3, infinity)
+ (hits 23/2484) (matched long text) constraint DS = {7} extremes [3, infinity)
an actor trying
- (hits 0/1828) constraint DS = {7} extremes [4, infinity)
+ (hits 0/1826) constraint DS = {7} extremes [4, infinity)
an actor
- (hits 408/2463) (matched long text) constraint DS = {7} extremes [3, infinity)
+ (hits 408/2461) (matched long text) constraint DS = {7} extremes [3, infinity)
trying
- (hits 0/3398) constraint DS = {7} extremes [2, infinity)
+ (hits 0/3391) constraint DS = {7} extremes [2, infinity)
(hits 60/10234) (matched long text) constraint (none) extremes [1, infinity)
@@ -9355,7 +9343,7 @@
we have
(hits 0/1091) constraint DS = {11} extremes [3, infinity)
- hits 0/1764 nti 12 constraint DS = {12} extremes [4, infinity)
+ hits 0/1760 nti 12 constraint DS = {12} extremes [4, infinity)
English:
we have not asked to try
(hits 0/136) constraint DS = {12} extremes [8, infinity)
@@ -9368,7 +9356,7 @@
we have not tried
(hits 0/537) constraint DS = {12} extremes [5, infinity)
we have not
- (hits 0/882) constraint DS = {12} extremes [4, infinity)
+ (hits 0/880) constraint DS = {12} extremes [4, infinity)
internal hits 94/13090 nti 14 constraint (none) extremes [1, infinity)
@@ -9376,44 +9364,56 @@
internal nti 16 constraint (none) extremes [1, infinity)
- hits 0/1390 nti 9 constraint CS = {9} extremes [2, 2]
+ hits 0/1390 nti 7 constraint CS = {7} extremes [2, 2]
English:
doing it
- constraint CS = {9} extremes [2, 2]
+ constraint CS = {7} extremes [2, 2]
- hits 584/1390 nti 10 constraint (none) extremes [1, infinity)
+ hits 584/1390 nti 8 constraint (none) extremes [1, infinity)
English:
when/while
- (hits 11/129) (matched long text) constraint DS = {10} extremes [3, infinity)
+ (hits 11/116) (matched long text) constraint DS = {8} extremes [3, infinity)
(hits 573/684) (matched long text) constraint (none) extremes [1, infinity)
{...} when/while
- (hits 0/44) constraint DS = {10} extremes [3, infinity)
+ (hits 0/37) constraint DS = {8} extremes [3, infinity)
{...} when/while {...}
- (hits 0/44) constraint DS = {10} extremes [3, infinity)
+ (hits 0/37) constraint DS = {8} extremes [3, infinity)
internal hits 19/38 nti 17 constraint (none) extremes [1, infinity)
internal hits 584/1406 nti 18 constraint (none) extremes [1, infinity)
- hits 202/410 nti 11 constraint (none) extremes [1, infinity)
+ hits 200/406 nti 9 constraint (none) extremes [1, infinity)
English:
something/anything
- (hits 79/79) (matched: 'something') constraint CS = {11} extremes [1, 1]
+ (hits 79/79) (matched: 'something') constraint CS = {9} extremes [1, 1]
something/anything else
- constraint CS = {11} extremes [2, 2]
+ (hits 0/1) constraint CS = {9} extremes [2, 2]
- (hits 123/126) (matched long text) constraint (none) extremes [1, infinity)
+ (hits 121/124) (matched long text) constraint (none) extremes [1, infinity)
- hits 5/10 nti 12 constraint CS = {12} extremes [1, 1]
+ hits 5/10 nti 10 constraint CS = {10} extremes [1, 1]
English:
something/anything
- (hits 4/5) (matched: 'something') constraint CS = {12} extremes [1, 1]
+ (hits 4/5) (matched: 'something') constraint CS = {10} extremes [1, 1]
it
- (hits 1/1) (matched: 'it') constraint CS = {12} extremes [1, 1]
+ (hits 1/1) (matched: 'it') constraint CS = {10} extremes [1, 1]
internal hits 0/4000 nti 19 constraint (none) extremes [1, infinity)
+ hits 1/180 nti 11 constraint CS = {11} extremes [1, 1]
+ English:
+ going
+ (hits 1/1) (matched: 'going') constraint CS = {11} extremes [1, 1]
+
+ hits 0/16 nti 12 constraint CS = {12} extremes [1, 1]
+ English:
+ nowhere
+ (hits 0/3) constraint CS = {12} extremes [1, 1]
+ somewhere
+ (hits 0/3) constraint CS = {12} extremes [1, 1]
+
hits 21/186 nti 13 constraint DS = {13} extremes [1, infinity)
English:
understood
diff --git a/inform7/Figures/memory-diagnostics.txt b/inform7/Figures/memory-diagnostics.txt
index 9d6ec6e36..95e5a39f6 100644
--- a/inform7/Figures/memory-diagnostics.txt
+++ b/inform7/Figures/memory-diagnostics.txt
@@ -1,13 +1,13 @@
Total memory consumption was 259375K = 253 MB
-62.6% was used for 1340373 objects, in 278899 frames in 203 x 800K = 162400K = 158 MB:
+62.6% was used for 1340372 objects, in 278898 frames in 203 x 800K = 162400K = 158 MB:
9.7% inter_tree_node_array 36 x 8192 = 294912 objects, 25953408 bytes
5.5% text_stream_array 2595 x 100 = 259500 objects, 14615040 bytes
- 3.9% parse_node 130241 objects, 10419280 bytes
+ 3.9% parse_node 130236 objects, 10418880 bytes
2.7% verb_conjugation 160 objects, 7425280 bytes
2.6% parse_node_annotation_array 432 x 500 = 216000 objects, 6925824 bytes
- 2.4% linked_list 11789 objects, 6601840 bytes
+ 2.4% linked_list 11793 objects, 6604080 bytes
2.3% inter_symbol_array 70 x 1024 = 71680 objects, 6310080 bytes
1.2% pcalc_prop_array 24 x 1000 = 24000 objects, 3264768 bytes
1.1% map_data 670 objects, 3178480 bytes
@@ -247,5 +247,5 @@ Total memory consumption was 259375K = 253 MB
---- emitter array storage 12320 bytes in 8 claims
---- code generation workspace for objects 9200 bytes in 9 claims
-20.2% was overhead - 53889776 bytes = 52626K = 51 MB
+20.2% was overhead - 53887936 bytes = 52624K = 51 MB
diff --git a/inform7/Figures/preform-summary.txt b/inform7/Figures/preform-summary.txt
index 518960f72..e94d21e57 100644
--- a/inform7/Figures/preform-summary.txt
+++ b/inform7/Figures/preform-summary.txt
@@ -3,7 +3,7 @@
(@1)=1
(hits 171/171) (matched: '100') constraint CS = {r0} extremes [1, 1]
(@1)minus (@2)=1
- (hits 0/1872) constraint DS = {12} extremes [2, 2]
+ (hits 0/1864) constraint DS = {12} extremes [2, 2]
(@1)=1 (@2)( (@3)=2 (@4))
(hits 273/840) (matched: '"[current item from the multiple object list]: [run paragraph on]" ( a )') constraint DS = {12} extremes [4, 4]
(@1)=1
@@ -18,7 +18,7 @@
=1
(hits 0/1468) constraint DS = {8} extremes [2, infinity)
(@1)unicode =1
- (hits 0/4232) constraint DS = {12} extremes [2, infinity)
+ (hits 0/4220) constraint DS = {12} extremes [2, infinity)
=1
(hits 0/2190) constraint DW = {9, 10, 11} extremes [2, 5]
=1
diff --git a/inform7/Figures/timings-diagnostics.txt b/inform7/Figures/timings-diagnostics.txt
index 7cc3b329e..5c47ea210 100644
--- a/inform7/Figures/timings-diagnostics.txt
+++ b/inform7/Figures/timings-diagnostics.txt
@@ -1,29 +1,29 @@
100.0% in inform7 run
- 67.1% in compilation to Inter
- 25.9% in //Phrases::Manager::compile_first_block//
- 8.4% in //Phrases::Manager::compile_as_needed//
- 6.9% in //Strings::compile_responses//
- 6.2% in //InferenceSubjects::emit_all//
- 4.2% in //MajorNodes::pre_pass//
- 3.3% in //MajorNodes::pass_1//
+ 67.0% in compilation to Inter
+ 25.8% in //Phrases::Manager::compile_first_block//
+ 8.5% in //Phrases::Manager::compile_as_needed//
+ 7.1% in //Strings::compile_responses//
+ 6.1% in //InferenceSubjects::emit_all//
+ 4.1% in //MajorNodes::pre_pass//
+ 3.4% in //MajorNodes::pass_1//
2.0% in //Phrases::Manager::RulePrintingRule_routine//
1.8% in //Phrases::Manager::rulebooks_array//
- 1.0% in //RTVerbs::ConjugateVerb//
- 0.8% in //Phrases::Manager::traverse//
- 0.5% in //Phrases::Manager::compile_rulebooks//
- 0.5% in //Phrases::Manager::parse_rule_parameters//
+ 0.9% in //Phrases::Manager::traverse//
+ 0.9% in //RTVerbs::ConjugateVerb//
0.5% in //World::stage_V//
0.3% in //MajorNodes::pass_2//
+ 0.3% in //Phrases::Manager::compile_rulebooks//
+ 0.3% in //Phrases::Manager::parse_rule_parameters//
0.3% in //RTRelations::compile_defined_relations//
0.1% in //PL::Parsing::Verbs::compile_all//
0.1% in //RTKinds::compile_data_type_support_routines//
0.1% in //Task::make_built_in_kind_constructors//
0.1% in //World::stages_II_and_III//
- 3.4% not specifically accounted for
- 30.5% in running Inter pipeline
- 10.7% in step preparation
- 9.7% in inter step 2/12: link
- 7.2% in inter step 12/12: generate inform6 -> auto.inf
+ 3.3% not specifically accounted for
+ 30.6% in running Inter pipeline
+ 9.8% in step preparation
+ 9.6% in inter step 2/12: link
+ 7.1% in inter step 12/12: generate inform6 -> auto.inf
0.3% in inter step 9/12: make-identifiers-unique
0.1% in inter step 10/12: reconcile-verbs
0.1% in inter step 11/12: eliminate-redundant-labels
@@ -32,6 +32,6 @@
0.1% in inter step 6/12: assimilate
0.1% in inter step 7/12: resolve-external-symbols
0.1% in inter step 8/12: inspect-plugs
- 1.2% not specifically accounted for
+ 2.4% not specifically accounted for
2.0% in supervisor
0.4% not specifically accounted for
diff --git a/inform7/core-module/Chapter 3/Plugin Calls.w b/inform7/core-module/Chapter 3/Plugin Calls.w
index d63b9d266..7e4a5656f 100644
--- a/inform7/core-module/Chapter 3/Plugin Calls.w
+++ b/inform7/core-module/Chapter 3/Plugin Calls.w
@@ -422,9 +422,12 @@ int PluginCalls::set_subkind_notify(kind *sub, kind *super) {
PLUGINS_CALL(SET_SUBKIND_NOTIFY_PLUG, sub, super);
}
-@h Influencing if.
-If the actions plugin is not active, then the following will never be called.
-It warn plugins that a new action name has been created.
+@h Influencing the actions plugin.
+We now have a whole run of functions called only by the actions plugin, and
+therefore only when it is active.
+
+Called from //if: Actions Plugin// to signal that a new action has been
+created. For example, the going plugin uses this to spot the arrival of "going".
@e NEW_ACTION_NOTIFY_PLUG
@@ -433,9 +436,10 @@ int PluginCalls::new_action_notify(action_name *an) {
PLUGINS_CALL(NEW_ACTION_NOTIFY_PLUG, an);
}
-@ If the actions plugin is not active, then the following will never be called.
-It invites plugins to change the action pattern clause ID associated with a
-given action variable.
+@ Called from //if: Action Pattern Clauses// to invite plugins to change the
+action pattern clause ID associated with a given action variable. This may be
+needed in order to cross-reference between multiple such clauses, as with
+the going action variables.
@e DIVERT_AP_CLAUSE_PLUG
@@ -445,9 +449,8 @@ int PluginCalls::divert_AP_clause_ID(stacked_variable *stv, int *id) {
PLUGINS_CALL(DIVERT_AP_CLAUSE_PLUG, stv, id);
}
-@ If the actions plugin is not active, then the following will never be called.
-It should print a helpful name for the debugging log for the clause ID |C|,
-if |C| is a new clause ID created by the plugin.
+@ Called from //if: Action Pattern Clauses// to ask plugins to print a helpful
+name for the debugging log for any new clause ID |C| which they have created.
@e WRITE_AP_CLAUSE_ID_PLUG
@@ -456,9 +459,9 @@ int PluginCalls::write_AP_clause_ID(OUTPUT_STREAM, int C) {
PLUGINS_CALL(WRITE_AP_CLAUSE_ID_PLUG, OUT, C);
}
-@ If the actions plugin is not active, then the following will never be called.
-It should return a |*_APCA| aspect for the clause ID |C|, if |C| is a new
-clause ID created by the plugin.
+@ Called from //if: Action Pattern Clauses// to ask for the |*_APCA| aspect
+for the clause ID |C|, where |C| is a new clause ID created by the plugin. If
+this is not given, then the aspect will be |MISC_APCA|.
@e ASPECT_OF_AP_CLAUSE_ID_PLUG
@@ -467,13 +470,19 @@ int PluginCalls::aspect_of_AP_clause_ID(int C, int *A) {
PLUGINS_CALL(ASPECT_OF_AP_CLAUSE_ID_PLUG, C, A);
}
-@ If the actions plugin is not active, then the following will never be called.
-If it recognises the patterns as ways to describe an action it knows about,
-then the plugin can choose to take the decision, storing either 1 or -1 in
+@ Called from //if: Action Pattern Clauses// to give plugins a chance to
+decide which AP is more specific, on the basis of the extra clauses defined
+in the plugin.
+
+If the plugin recognises the patterns as ways to describe an action it knows
+about, it can choose to take the decision, storing either 1 or -1 in
|rv|, and returning |TRUE|. If it instead stores 0 in |rv|, it can also
choose to set |ignore_in|, which tells the usual machinery not to judge on the
basis of the |[in: ...]| clause in the pattern.
+If the plugin sees nothing relevant about the patterns, it should return |FALSE|
+to let the usual machinery take its course.
+
@e COMPARE_AP_SPECIFICITY_PLUG
=
@@ -482,16 +491,50 @@ int PluginCalls::compare_AP_specificity(action_pattern *ap1, action_pattern *ap2
PLUGINS_CALL(COMPARE_AP_SPECIFICITY_PLUG, ap1, ap2, rv, ignore_in);
}
-@
+@ Called from //if: Action Pattern Clauses// to notify plugins that a clause
+matching an action variable has just been added to an action pattern.
@e NEW_AP_CLAUSE_PLUG
=
-int PluginCalls::new_AP_clause(action_pattern *ap, ap_clause *apoc) {
+int PluginCalls::new_action_variable_clause(action_pattern *ap, ap_clause *apoc) {
PLUGINS_CALL(NEW_AP_CLAUSE_PLUG, ap, apoc);
}
-@
+@ Called from //if: Parse Clauses// to give plugins a chance to intervene in
+the normal process of evaluating the meaning of text in an action pattern
+clause: for example, in parsing "going nowhere", the going plugin uses this
+to detect that the |NOUN_AP_CLAUSE|, with text "nowhere", should not be parsed
+normally. What it does it to set a bit in the bitmap |bits|, which it will pick
+up again and act upon when reacting to |ACT_ON_ANL_ENTRY_OPTIONS_PLUG|.
+
+If the plugin does not set a bit in |bits|, the normal machinery parses the
+text of the clause in the normal way.
+
+@e PARSE_AP_CLAUSE_PLUG
+
+int PluginCalls::parse_AP_clause(action_name *an, anl_clause *c, int *bits) {
+ PLUGINS_CALL(PARSE_AP_CLAUSE_PLUG, an, c, bits);
+}
+
+@ Called from //if: Parse Clauses// to give plugins a chance to intervene in
+the type-checking process for a clause. Ordinarily, this would just check that
+the contents have the right kind: if matching an action variable of kind |K|
+then it must be a value compatible with |K| or a description of such.
+
+By returning |TRUE|, a plugin can instead take responsibility for the decision
+itself, bypassing that. The |outcome| should then be set |TRUE| (it's valid)
+or |FALSE| (it isn't).
+
+@e VALIDATE_AP_CLAUSE_PLUG
+
+=
+int PluginCalls::validate_AP_clause(action_name *an, anl_clause *c, int *outcome) {
+ PLUGINS_CALL(VALIDATE_AP_CLAUSE_PLUG, an, c, outcome);
+}
+
+@ Called from //if: Parse Clauses// to deal with the options bitmap set
+previously by a |PARSE_AP_CLAUSE_PLUG| call: see above.
@e ACT_ON_ANL_ENTRY_OPTIONS_PLUG
@@ -500,6 +543,29 @@ int PluginCalls::act_on_ANL_entry_options(anl_entry *entry, int entry_options, i
PLUGINS_CALL(ACT_ON_ANL_ENTRY_OPTIONS_PLUG, entry, entry_options, fail);
}
+@ Called from //runtime: Action Patterns// when assembling the requirement
+clauses for compiling a mattern match; this gives plugins a chance to act
+extra stipulations, which are not explicit in clauses already in the pattern.
+
+@e SET_PATTERN_MATCH_REQUIREMENTS_PLUG
+
+=
+int PluginCalls::set_pattern_match_requirements(action_pattern *ap, int *cpm,
+ int needed[MAX_CPM_CLAUSES], ap_clause *needed_apoc[MAX_CPM_CLAUSES]) {
+ PLUGINS_CALL(SET_PATTERN_MATCH_REQUIREMENTS_PLUG, ap, cpm, needed, needed_apoc);
+}
+
+@ Called from //runtime: Action Patterns// when compiling any additional
+requirements set by |SET_PATTERN_MATCH_REQUIREMENTS_PLUG|.
+
+@e COMPILE_PATTERN_MATCH_CLAUSE_PLUG
+
+=
+int PluginCalls::compile_pattern_match_clause(value_holster *VH, action_pattern *ap,
+ int cpmc) {
+ PLUGINS_CALL(COMPILE_PATTERN_MATCH_CLAUSE_PLUG, VH, ap, cpmc);
+}
+
@h Influencing index.
Called from //index: Index Physical World// to add something (if it wishes)
to the index description of an instance in the spatial model. For example,
diff --git a/inform7/if-module/Chapter 1/IF Module.w b/inform7/if-module/Chapter 1/IF Module.w
index be67ed83a..e61a3ea55 100644
--- a/inform7/if-module/Chapter 1/IF Module.w
+++ b/inform7/if-module/Chapter 1/IF Module.w
@@ -100,7 +100,7 @@ void IFModule::create_plugins(void) {
times_plugin = PluginManager::new(TimesOfDay::start, I"times of day", ifp);
actions_plugin = PluginManager::new(&ActionsPlugin::start, I"actions", ifp);
- going_plugin = PluginManager::new(&Going::start, I"going", actions_plugin);
+ going_plugin = PluginManager::new(&GoingPlugin::start, I"going", actions_plugin);
parsing_plugin = PluginManager::new(&ParsingPlugin::start, I"command", ifp);
showme_plugin = PluginManager::new(&RTShowmeCommand::start, I"showme", parsing_plugin);
diff --git a/inform7/if-module/Chapter 4/Action Conditions.w b/inform7/if-module/Chapter 4/Action Conditions.w
index 66c20da32..8d0260af2 100644
--- a/inform7/if-module/Chapter 4/Action Conditions.w
+++ b/inform7/if-module/Chapter 4/Action Conditions.w
@@ -7,10 +7,10 @@ write "if taking or dropping something", for example, and this is implicitly
a test of what the current action is.
This is represented in the parse tree as the twig:
-
+= (text)
TEST_VALUE_NT
CONSTANT_NT
-
+=
where the constant below is the action seen as a noun -- linguistically, a
"gerund". It will always have the kind |K_stored_action| or |K_description_of_action|,
depending on whether the test is against an explicit action or something vaguer.
diff --git a/inform7/if-module/Chapter 4/Action Kinds.w b/inform7/if-module/Chapter 4/Action Kinds.w
index 3fe91ecae..d2be551eb 100644
--- a/inform7/if-module/Chapter 4/Action Kinds.w
+++ b/inform7/if-module/Chapter 4/Action Kinds.w
@@ -13,7 +13,7 @@ kind *K_description_of_action = NULL;
@ These are created by a Neptune file inside //WorldModelKit//, and are
recognised by their Inter identifiers:
-@ =
+=
int ARvalues::new_base_kind_notify(kind *new_base, text_stream *name, wording W) {
if (Str::eq_wide_string(name, L"ACTION_NAME_TY")) {
K_action_name = new_base; return TRUE;
diff --git a/inform7/if-module/Chapter 4/Action Name Lists.w b/inform7/if-module/Chapter 4/Action Name Lists.w
index cc9abb206..1b81a0663 100644
--- a/inform7/if-module/Chapter 4/Action Name Lists.w
+++ b/inform7/if-module/Chapter 4/Action Name Lists.w
@@ -578,13 +578,17 @@ void ActionNameLists::log_entry(anl_entry *entry) {
ActionNameLists::log_entry_briefly(entry);
LOOP_THROUGH_ANL_CLAUSES(c, entry)
if (Wordings::nonempty(c->clause_text)) {
- LOG(" [");
- APClauses::write_clause_ID(DL, c->clause_ID, c->stv_to_match);
- LOG(": %W]", c->clause_text);
+ LOG(" "); ActionNameLists::log_clause(c);
}
}
}
+void ActionNameLists::log_clause(anl_clause *c) {
+ LOG("[");
+ APClauses::write_clause_ID(DL, c->clause_ID, c->stv_to_match);
+ LOG(": %W]", c->clause_text);
+}
+
void ActionNameLists::log_briefly(action_name_list *list) {
if (list == NULL) {
LOG("");
@@ -704,11 +708,11 @@ action_name_list *ActionNameLists::parse(wording W, int tense, int *sense) {
=
::=
- | ==> { -, ActionNameLists::nap_entry(RP[1], W, EMPTY_WORDING) }
- | ==> { pass 1 }
- ==> { pass 1 }
+ | ==> { -, ActionNameLists::nap_entry(RP[1], W, EMPTY_WORDING) }
+ | ==> { pass 1 }
+ ==> { pass 1 }
- internal {
+ internal {
for (int i=Wordings::first_wn(W); i<= Wordings::last_wn(W) - 1; i++) {
if ((Wordings::up_to(W, i))) {
==> { -, ActionNameLists::nap_entry(<