acceptRecovery method

void acceptRecovery(
  1. int error_token
)

Implementation

void acceptRecovery(int error_token) {
  //
  //
  //
  // int action_size = action.size();

  //
  // Simulate parsing actions required for this sequence of scope
  // recoveries.
  // TODO: need to add action and fix the location_stack?
  //
  var recovery_action = IntTuple();
  for (var k = 0; k <= scopeStackTop; k++) {
    var scope_index = scopeIndex[k], la = scopeLa(scope_index);

    //
    // Compute the action (or set of actions in case of conflicts) that
    // can be executed on the scope lookahead symbol. Save the action(s)
    // in the action tuple.
    //
    recovery_action.reset();
    var act = tAction(stateStack[stateStackTop], la);
    if (act > ACCEPT_ACTION && act < ERROR_ACTION) // conflicting actions?
    {
      do {
        recovery_action.add(baseAction(act++));
      } while (baseAction(act) != 0);
    } else {
      recovery_action.add(act);
    }

    //
    // For each action defined on the scope lookahead symbol,
    // try scope recovery. At least one action should succeed!
    //
    var start_action_size = action.size();
    int index;
    for (index = 0; index < recovery_action.size(); index++) {
      //
      // Reset the action tuple each time through this loop
      // to clear previous actions that may have been added
      // because of a failed call to completeScope.
      //
      action.reset(start_action_size);
      tokStream.reset(error_token);
      tempStackTop = stateStackTop - 1;
      var max_pos = stateStackTop;

      act = recovery_action.get(index);
      while (act <= NUM_RULES) {
        action.add(act); // save this reduce action
        //
        // ... Process all goto-reduce actions following
        // reduction, until a goto action is computed ...
        //
        do {
          var lhs_symbol = lhs(act);
          tempStackTop -= (rhs(act) - 1);
          act = (tempStackTop > max_pos
              ? tempStack[tempStackTop]
              : stateStack[tempStackTop]);
          act = ntAction(act, lhs_symbol);
        } while (act <= NUM_RULES);
        if (tempStackTop + 1 >= stateStack.length) reallocateStacks();
        max_pos = max_pos < tempStackTop ? max_pos : tempStackTop;
        tempStack[tempStackTop + 1] = act;
        act = tAction(act, la);
      }

      //
      // If the lookahead symbol is parsable, then we check
      // whether or not we have a match between the scope
      // prefix and the transition symbols corresponding to
      // the states on top of the stack.
      //
      if (act != ERROR_ACTION) {
        nextStackTop = ++tempStackTop;
        for (var i = 0; i <= max_pos; i++) {
          nextStack[i] = stateStack[i];
        }

        //
        // NOTE that we do not need to update location_stack and
        // actionStack here because, once the rules associated with
        // these scopes are reduced, all these states will be popped
        // from the stack.
        //
        for (var i = max_pos + 1; i <= tempStackTop; i++) {
          nextStack[i] = tempStack[i];
        }
        if (completeScope(action, scopeSuffix(scope_index))) {
          for (var i = scopeSuffix(scopeIndex[k]); scopeRhs(i) != 0; i++) {
            // System.err.println("(*) adding token for
            // nonterminal at location " + tokens.size());
            tokens.add((tokStream as IPrsStream).makeErrorToken(
                error_token,
                tokStream.getPrevious(error_token),
                error_token,
                scopeRhs(i)));
          }

          reportError(scopeIndex[k], tokStream.getPrevious(error_token));

          break;
        }
      }
    }
    // assert (index < recovery_action.size()); // sanity check!
    stateStackTop = nextStackTop;
    ArrayList.copy(nextStack, 0, stateStack, 0, stateStackTop + 1);
  }

  return;
}