Recover:
PROC = {
ModeMap: ARRAY Position OF ParsingMode = [$aTree, $bTree];
stack: StackRep;
treeLimit ¬ treeSize - checkSize;
hashTable ¬ ALL[nullIndex];
rTop ¬ nullIndex; nextNode ¬ maxNode ¬ 1;
best.nAccepted ¬ 0; best.nPassed ¬ 1; best.mode ¬ $aTree;
scanBuffer[0] ¬ lastToken;
scanBuffer[1] ¬ MobP1.Token[inputSymbol, inputValue, inputLoc];
scanBase ¬ 1; scanLimit ¬ 2;
THROUGH [1 .. maxScanLimit) DO Advance[] ENDLOOP;
FOR i:
NAT
IN [0 .. top)
DO
rTop ¬ Allocate[rTop, rTop, 0, s[i]];
IF track THEN DisplayNode[rTop];
ENDLOOP;
parseMode ¬ $bTree;
levelStart[$before][0] ¬ rTop ¬ FindNode[rTop, rTop, s[top]];
tree[rTop].bLeaf ¬ TRUE;
levelEnd[$before][0] ¬ nextNode;
parseMode ¬ $aTree;
stack ¬ ParseStep[[leaf:rTop, extension:nullState], lastToken.class];
rTop ¬ FindNode[stack.leaf, rTop, stack.extension];
tree[rTop].symbol ¬ lastToken.class;
tree[rTop].aLeaf ¬ tree[rTop].bLeaf ¬ TRUE;
levelStart[$after][0] ¬ rTop; levelEnd[$after][0] ¬ nextNode;
IF track THEN DisplayNode[rTop];
FOR level: Length
IN [1 .. Length.
LAST]
DO
FOR place: Position
IN Position
DO
parseMode ¬ ModeMap[place];
IF place = $before THEN UnDiscard[];
try simple insertion (inserts=level)
levelStart[place][level] ¬ nextNode;
IF GrowTree[place, level ! TreeFull => {CONTINUE}] THEN GO TO found;
levelEnd[place][level] ¬ nextNode;
try discards followed by 0 or more insertions
THROUGH [1 .. level)
DO
Discard[]; IF CheckTree[place, level] THEN GO TO found ENDLOOP;
Discard[];
IF place = $after THEN Advance[];
FOR inserts:
NAT
IN [0 .. level]
DO
IF CheckTree[place, inserts] THEN GO TO found ENDLOOP;
undo discards at this level
THROUGH [1..level] DO UnDiscard[] ENDLOOP;
IF place = $before THEN Discard[];
ENDLOOP;
REPEAT
found => NULL;
FINISHED => {
threshold: NAT ¬ (minScanLimit+maxScanLimit)/2;
THROUGH [1..Length.LAST] DO Discard[]; Advance[] ENDLOOP;
UNTIL scanBase > discardLimit
DO
IF best.nAccepted >= threshold THEN GO TO found;
Discard[];
FOR inserts:
NAT
IN Length
DO
FOR place: Position
IN Position
DO
parseMode ¬ ModeMap[place];
IF place = $before THEN UnDiscard[];
IF CheckTree[place, inserts] THEN GO TO found;
IF place = $before THEN Discard[];
ENDLOOP;
ENDLOOP;
Advance[];
threshold ¬ IF threshold > minScanLimit THEN threshold-1 ELSE minScanLimit;
REPEAT
found => NULL;
FINISHED =>
IF best.nAccepted < minScanLimit THEN {best.mode ¬ $aTree; best.nPassed ¬ 1};
ENDLOOP};
ENDLOOP};
}.