The ALE debugger is loosely based on the procedural box model of execution that the SICStus command-line debugger uses. There are four kinds of ports, call, exit, redo, and fail. The ALE debugger does not support exception ports. A call port occurs at every initial invocation of a step that ALE takes in parsing or definite clause resolution, a list of which is given below. An exit port occurs at the successful completion of such a step; a redo port occurs when a subsequent step has failed and ALE backtracks into the current step to find more solutions, and a fail port occurs when a step has failed to produce any or any more solutions.
Consider, for example, what happens when ALE applies the following description to a feature structure that occurs in the lexical entry for the word, foo
foo --->(a ;f:b), g:c.The first port we encounter is when ALE tries to add the type a. This is a call port:
Call: add type, a, to lex entry?If this succeeds, then an exit port occurs:
Exit: add type, a, to lex entry?and processing moves on to g:c. If this fails, then we must backtrack through adding a for more solutions (for example, if there is a disjunctive constraint on that type):
Redo: add type, a, to lex entry?If there is another solution, then another exit port occurs. Otherwise, the next port is fail port:
Fail: add type, a, to lex entry?and processing continues with the other disjunct, f:b. Certain steps in ALE, notably the depth-first rule application of the chart parser, are failure-driven loops. To indicate that these ``failures'' are actually a normal part of execution, they are displayed as, e.g.:
Finished:close chart edge under rule application?
Enforcing descriptions at a feature also counts as a step:
Call: enforce description on f value of lex entry?If we agree to this, then the next step would be to add the type b
Call: add type, b, to value at f?and so on.
The steps in a description whose ports the ALE debugger keeps track of are given in Figure 7.1:
There are other kinds of steps besides description-level ones, that pertain to ALE's built-in control for parsing and definite clause resolution. These steps, along with their kind, are given in the table in Figure 7.2. The steps for generation are given in Figure 7.3. Almost all of these involve sub-steps that enforce descriptions. Some, such as chart-edge closure, involve other sub-steps such as rule selection. Lexical rule application includes input and output morph application, as well as morph condition (given in a when clause) application. The one generation step of kind, lr, takes place when the pivot template is matched against a (base or derived) lexical entry. Unlike the compiled generator, the debugger does not compile lexical rules into the non-chain-rule selection step, so that the user can see their application. Instead, a base lexical entry is first selected without reference to the pivot template, then zero or more lexical rules are applied bottom up, until a derived entry is eventually unified with the pivot template. Lexical rules are, thus, treated as a special kind of unary chain rule. The length of these special chains is still controlled by lex_rule_depth/1, not chain_length/1.