backtrackParseUpToError method
void
backtrackParseUpToError(
- int initial_token,
- int error_token
)
Implementation
void backtrackParseUpToError(int initial_token, int error_token) {
//
// Allocate configuration stack.
//
var configuration_stack = ConfigurationStack(prs);
//
// Keep parsing until we successfully reach the end of file or
// an error is encountered. The list of actions executed will
// be stored in the "action" tuple.
//
var start_token = tokStream.peek(),
curtok = (initial_token > 0 ? initial_token : tokStream.getToken()),
current_kind = tokStream.getKind(curtok),
act = tAction(stateStack[stateStackTop], current_kind);
tokens.add(curtok);
locationStack[stateStackTop] = tokens.size();
actionStack[stateStackTop] = action.size();
for (;;) {
//
// if the parser needs to stop processing,
// it may do so here.
//
if (monitor != null && monitor!.isCancelled()) return;
if (act <= NUM_RULES) {
action.add(act); // save this reduce action
stateStackTop--;
act = process_backtrack_reductions(act);
} else if (act > ERROR_ACTION) {
action.add(act); // save this shift-reduce action
curtok = tokStream.getToken();
current_kind = tokStream.getKind(curtok);
tokens.add(curtok);
act = process_backtrack_reductions(act - ERROR_ACTION);
} else if (act < ACCEPT_ACTION) {
action.add(act); // save this shift action
curtok = tokStream.getToken();
current_kind = tokStream.getKind(curtok);
tokens.add(curtok);
} else if (act == ERROR_ACTION) {
if (curtok != error_token) {
var configuration = configuration_stack.pop();
if (configuration == null) {
act = ERROR_ACTION;
} else {
action.reset(configuration.action_length);
act = configuration.act;
var next_token_index = configuration.curtok;
tokens.reset(next_token_index);
curtok = tokens.get(next_token_index - 1);
current_kind = tokStream.getKind(curtok);
tokStream.reset(curtok == initial_token
? start_token
: tokStream.getNext(curtok));
stateStackTop = configuration.stack_top;
configuration.retrieveStack(stateStack);
locationStack[stateStackTop] = tokens.size();
actionStack[stateStackTop] = action.size();
continue;
}
}
break;
} else if (act > ACCEPT_ACTION) {
if (configuration_stack.findConfiguration(
stateStack, stateStackTop, tokens.size())) {
act = ERROR_ACTION;
} else {
configuration_stack.push(
stateStack, stateStackTop, act + 1, tokens.size(), action.size());
act = prs.baseAction(act);
}
continue;
} else {
break;
} // assert(act == ACCEPT_ACTION);
stateStack[++stateStackTop] = act; // no need to check if out of bounds
locationStack[stateStackTop] = tokens.size();
actionStack[stateStackTop] = action.size();
act = tAction(act, current_kind);
}
// assert(curtok == error_token);
return;
}