/*
* Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
* All rights reserved.
* This component and the accompanying materials are made available
* under the terms of the License "Eclipse Public License v1.0"
* which accompanies this distribution, and is available
* at the URL "http://www.eclipse.org/legal/epl-v10.html".
*
* Initial Contributors:
* Nokia Corporation - initial contribution.
*
* Contributors:
*
* Description: 
*
*/
/* Generated By:JavaCC: Do not edit this line. PreParserCore.java */
package com.nokia.carbide.internal.cpp.epoc.engine.parser.generated;

import com.nokia.carbide.internal.api.cpp.epoc.engine.dom.*;
import com.nokia.carbide.internal.cpp.epoc.engine.parser.*;

import java.util.List;
import java.util.ArrayList;

public class PreParserCore extends ParserBase implements PreParserCoreConstants {

    public IASTTranslationUnit parse() {
        this.tokenLocation = ((BaseTokenManager)token_source).getTokenLocation();
                IASTTranslationUnit tu = null;;
                try {
                        tu = TranslationUnit();
                } catch (ParseException e) {
                        // should not reach
                }
                return tu;
    }

  final public IASTTranslationUnit TranslationUnit() throws ParseException {
        IASTListNode<IASTTopLevelNode> topLevelNodes = null;
        Token eof;
    topLevelNodes = TopLevelNodes();
    eof = jj_consume_token(0);
                IASTTranslationUnit tu = ASTFactory.createTranslationUnit(topLevelNodes);
                if (topLevelNodes != null) {
                        ParserUtils.setSourceRangeForListNode(null, tu.getNodes(), eof);
                        ParserUtils.copySourceInfo(tu, tu.getNodes());
                } else {
                        ParserUtils.setSourceRangeFromTokenSpan(tu.getNodes(), eof, eof);
                        ParserUtils.setSourceRangeFromTokenSpan(tu, eof, eof);
                }
                {if (true) return tu;}
    throw new Error("Missing return statement in function");
  }

  IASTListNode<IASTTopLevelNode> TopLevelNodes() throws ParseException {
        IASTListNode<IASTTopLevelNode> nodes = null;
        while (((jj_ntk==-1)?jj_ntk():jj_ntk) != EOF) {
                try {
                        IASTTopLevelNode node = TopLevelNode();
                        if (node != null) {
                                if (nodes == null) {
                                        nodes = ASTFactory.createTopLevelNodeListNode();
                                }
                                nodes.add(node);
                        }
                } catch (ParseException e) {
                        hadErrors = true;
                        getNextToken();
                }
        }
        return nodes;
  }

  final public IASTTopLevelNode TopLevelNode() throws ParseException {
        IASTTopLevelNode node=null;
        Token start = token;
    try {
      switch ((jj_ntk==-1)?jj_ntk():jj_ntk) {
      case POUND:
        node = Directive();
        break;
      default:
        jj_la1[0] = jj_gen;
        node = TokenText();
      }
                        {if (true) return node;}
    } catch (ParseException e) {
                {if (true) return createProblemTopLevelNode(start, e);}
    }
    throw new Error("Missing return statement in function");
  }

  IASTTopLevelNode createProblemTopLevelNode(Token start, ParseException e) throws ParseException {
        IASTTopLevelNode stmt;

        ppRestOfLine(false);
        List<IToken> tokens = new ArrayList<IToken>();
        start = start.next;
        while (true) {
                tokens.add(((ASTToken)start).iToken);
                if (start == token)
                        break;
                start = start.next;
        }
        IASTPreprocessorTokenStream stream = ASTFactory.createPreprocessorTokenStream(tokens);
        ParserUtils.setSourceRangeForTokenStream(stream, stream);
        stmt = ASTFactory.createProblemTopLevelNode(stream, createMessage(start, e));
        ParserUtils.copySourceInfo(stmt, stream);

        hadErrors = true;
        return stmt;
  }

/**
 *	Preprocessor directive
 */
  final public IASTTopLevelNode Directive() throws ParseException {
        Token pound = null;
        Token eol = null;
        IASTTopLevelNode node = null;
    pound = jj_consume_token(POUND);
    switch ((jj_ntk==-1)?jj_ntk():jj_ntk) {
    case IF:
      node = ppIf();
      break;
    case IFDEF:
      node = ppIfdef();
      break;
    case IFNDEF:
      node = ppIfndef();
      break;
    case ELSE:
      node = ppElse();
      break;
    case ELIF:
      node = ppElif();
      break;
    case ENDIF:
      node = ppEndif();
      break;
    case DEFINE:
      node = ppDefine();
      break;
    case UNDEF:
      node = ppUndef();
      break;
    case INCLUDE:
      node = ppInclude();
      break;
    case ERROR:
      node = ppError();
      break;
    case WARNING:
      node = ppWarning();
      break;
    case PRAGMA:
      node = ppPragma();
      break;
    default:
      jj_la1[1] = jj_gen;
      node = ppUnknown();
    }
    eol = jj_consume_token(EOL);
                ParserUtils.setSourceRangeFromTokenSpan(node, pound, eol);
                ParserUtils.expandSourceRangeToLine(node);
                {if (true) return node;}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorIfStatement ppIf() throws ParseException {
        Token start;
        IASTPreprocessorTokenStream expr = null;
          resetDirectiveParsing();
    start = jj_consume_token(IF);
    expr = Tokens(true);
        if (expr == null) {
                expr = ASTFactory.createPreprocessorTokenStream();
                ParserUtils.setSourceRangeFromTokenAfter(expr, start);
        }
        {if (true) return ASTFactory.createPreprocessorIfStatement(expr);}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorElifStatement ppElif() throws ParseException {
        Token start;
        IASTPreprocessorTokenStream expr = null;
          resetDirectiveParsing();
    start = jj_consume_token(ELIF);
    expr = Tokens(true);
        if (expr == null) {
                expr = ASTFactory.createPreprocessorTokenStream();
                ParserUtils.setSourceRangeFromTokenAfter(expr, start);
        }
        {if (true) return ASTFactory.createPreprocessorElifStatement(expr);}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorIfdefStatement ppIfdef() throws ParseException {
        Token name;
    jj_consume_token(IFDEF);
    name = jj_consume_token(IDENTIFIER);
    Tokens(true);
        {if (true) return ASTFactory.createPreprocessorIfdefStatement(
                getLiteralTextNodeSpanning(name, name));}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorIfndefStatement ppIfndef() throws ParseException {
        Token name;
    jj_consume_token(IFNDEF);
    name = jj_consume_token(IDENTIFIER);
    Tokens(true);
        {if (true) return ASTFactory.createPreprocessorIfndefStatement(
                getLiteralTextNodeSpanning(name, name));}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorElseStatement ppElse() throws ParseException {
          resetDirectiveParsing();
    jj_consume_token(ELSE);
    Tokens(true);
        {if (true) return ASTFactory.createPreprocessorElseStatement();}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorEndifStatement ppEndif() throws ParseException {
          resetDirectiveParsing();
    jj_consume_token(ENDIF);
    Tokens(true);
        {if (true) return ASTFactory.createPreprocessorEndifStatement();}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorDefineStatement ppDefine() throws ParseException {
        Token name;
        Token lparen=null, rparen=null;
        IASTListNode<IASTLiteralTextNode> arguments = null;
        IASTPreprocessorTokenStream expansion = null;
    jj_consume_token(DEFINE);
    name = jj_consume_token(IDENTIFIER);
    switch ((jj_ntk==-1)?jj_ntk():jj_ntk) {
    case LPAREN:
      lparen = jj_consume_token(LPAREN);
      arguments = ppMacroArgs();
      rparen = jj_consume_token(RPAREN);
      break;
    default:
      jj_la1[2] = jj_gen;
      ;
    }
    expansion = Tokens(true);
        if (expansion != null && expansion.getTokens().size() == 0)
                expansion = null;
        if (arguments != null)
                ParserUtils.setSourceRangeForListNode(lparen, arguments, rparen);
        {if (true) return ASTFactory.createPreprocessorDefineStatement(
                getLiteralTextNodeSpanning(name, name),
                arguments,
                expansion);}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorUndefStatement ppUndef() throws ParseException {
        Token name;
    jj_consume_token(UNDEF);
    name = jj_consume_token(IDENTIFIER);
    Tokens(true);
        {if (true) return ASTFactory.createPreprocessorUndefStatement(getLiteralTextNodeSpanning(name, name));}
    throw new Error("Missing return statement in function");
  }

  final public IASTListNode<IASTLiteralTextNode> ppMacroArgs() throws ParseException {
        Token name = null;
        IASTListNode<IASTLiteralTextNode> args = null;
    switch ((jj_ntk==-1)?jj_ntk():jj_ntk) {
    case IDENTIFIER:
    case ELLIPSIS:
      switch ((jj_ntk==-1)?jj_ntk():jj_ntk) {
      case IDENTIFIER:
        name = jj_consume_token(IDENTIFIER);
        break;
      case ELLIPSIS:
        name = jj_consume_token(ELLIPSIS);
        break;
      default:
        jj_la1[3] = jj_gen;
        jj_consume_token(-1);
        throw new ParseException();
      }
      switch ((jj_ntk==-1)?jj_ntk():jj_ntk) {
      case COMMA:
        jj_consume_token(COMMA);
        args = ppMacroArgs();
        break;
      default:
        jj_la1[4] = jj_gen;
        ;
      }
      break;
    default:
      jj_la1[5] = jj_gen;
      ;
    }
                if (args == null)
                        args = ASTFactory.createLiteralTextNodeList();
                if (name != null)
                        args.add(0, getLiteralTextNodeSpanning(name, name));
                {if (true) return args;}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorIncludeStatement ppInclude() throws ParseException {
        Token start;
        IASTPreprocessorTokenStream nameTokens = null;
    start = jj_consume_token(INCLUDE);
    nameTokens = Tokens(true);
        if (nameTokens == null) {
                nameTokens = ASTFactory.createPreprocessorTokenStream();
                ParserUtils.setSourceRangeFromTokenAfter(nameTokens, start);
        }
        {if (true) return ASTFactory.createPreprocessorIncludeStatement(nameTokens);}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorErrorStatement ppError() throws ParseException {
        Token start;
        IASTPreprocessorTokenStream expr = null;
    start = jj_consume_token(ERROR);
    expr = Tokens(true);
        if (expr == null) {
                expr = ASTFactory.createPreprocessorTokenStream();
                ParserUtils.setSourceRangeFromTokenAfter(expr, start);
        }
        {if (true) return ASTFactory.createPreprocessorErrorStatement(expr);}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorWarningStatement ppWarning() throws ParseException {
        Token start;
        IASTPreprocessorTokenStream expr = null;
    start = jj_consume_token(WARNING);
    expr = Tokens(true);
        if (expr == null) {
                expr = ASTFactory.createPreprocessorTokenStream();
                ParserUtils.setSourceRangeFromTokenAfter(expr, start);
        }
        {if (true) return ASTFactory.createPreprocessorWarningStatement(expr);}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorPragmaStatement ppPragma() throws ParseException {
        Token start;
        IASTPreprocessorTokenStream expr = null;
    start = jj_consume_token(PRAGMA);
    expr = Tokens(true);
        if (expr == null) {
                expr = ASTFactory.createPreprocessorTokenStream();
                ParserUtils.setSourceRangeFromTokenAfter(expr, start);
        }
        {if (true) return ASTFactory.createPreprocessorPragmaStatement(expr);}
    throw new Error("Missing return statement in function");
  }

  final public IASTPreprocessorUnknownStatement ppUnknown() throws ParseException {
        IASTPreprocessorTokenStream expr = null;
    expr = Tokens(true);
        {if (true) return ASTFactory.createPreprocessorUnknownStatement(expr);}
    throw new Error("Missing return statement in function");
  }

  final public IASTTopLevelNode Empty() throws ParseException {
        Token eol;
    eol = jj_consume_token(EOL);
                IASTPreprocessorTokenStreamStatement stmt = ASTFactory.createPreprocessorTokenStreamStatement(
                        ASTFactory.createTokenList(new IToken[] { ((ASTToken) eol).iToken }));
                ParserUtils.setSourceRangeFromTokenSpan(stmt.getTokenStream(), eol, eol);
                ParserUtils.setSourceRangeFromTokenSpan(stmt, eol, eol);
                ParserUtils.expandSourceRangeToLine(stmt);
                {if (true) return stmt;}
    throw new Error("Missing return statement in function");
  }

/**
 *	Tokenized text
 */
  final public IASTTopLevelNode TokenText() throws ParseException {
        Token eol = null;
        IASTPreprocessorTokenStream tokens = null;
    tokens = Tokens(false);
    eol = jj_consume_token(EOL);
                if (tokens == null) {
                        //return expandToLine(getPreprocessorTextStatementSpanning(eol, eol));
                        tokens = ASTFactory.createPreprocessorTokenStream();
                }
                tokens.getTokens().add(((ASTToken)eol).iToken);
                IASTPreprocessorTokenStreamStatement stmt =
                         ASTFactory.createPreprocessorTokenStreamStatement(tokens);
        ParserUtils.setSourceRangeForTokenStream(tokens, stmt.getTokenStream());
        ParserUtils.setSourceRangeForTokenStream(stmt, stmt.getTokenStream());
                ParserUtils.expandSourceRangeToLine(stmt);

                {if (true) return stmt;}
    throw new Error("Missing return statement in function");
  }

/**
 *	Tokenized text -- anything up to an EOL
 */
  final public IASTPreprocessorTokenStream Tokens(boolean first) throws ParseException {
        List<IToken> tokens = null;
          resetDirectiveParsing();
    tokens = TokenList(first);
                if (tokens != null) {
                        IASTPreprocessorTokenStream stream = ASTFactory.createPreprocessorTokenStream(tokens);
                        ParserUtils.setSourceRangeForTokenStream(stream, stream);
                        {if (true) return stream;}
                } else {
                        {if (true) return null;}
                }
    throw new Error("Missing return statement in function");
  }

  void resetDirectiveParsing() throws ParseException {
        if (token instanceof ASTToken)
                ((PreTokenManager) token_source).resetDirectiveScanningState((ASTToken)token);
  }

  final public IToken Token() throws ParseException {
        Token tok = null;
    switch ((jj_ntk==-1)?jj_ntk():jj_ntk) {
    case PPTOKEN:
      tok = jj_consume_token(PPTOKEN);
      break;
    case IDENTIFIER:
      tok = jj_consume_token(IDENTIFIER);
      break;
    case INTEGER:
      tok = jj_consume_token(INTEGER);
      break;
    case STRING:
      tok = jj_consume_token(STRING);
      break;
    case CHAR:
      tok = jj_consume_token(CHAR);
      break;
    default:
      jj_la1[6] = jj_gen;
      jj_consume_token(-1);
      throw new ParseException();
    }
                {if (true) return ((ASTToken) tok).iToken;}
    throw new Error("Missing return statement in function");
  }

  List<IToken> TokenList(boolean first) throws ParseException {
            switch ((jj_ntk==-1)?jj_ntk():jj_ntk) {
            case IDENTIFIER:
            case PPTOKEN:
            case INTEGER:
            case STRING:
            case CHAR:
              break;
            case EOL:
              //return new ArrayList<IToken>();
              return null;
            default:
              return null;
            }

        IToken token = null;
        boolean finished = false;
        List<IToken> tokens = new ArrayList<IToken>();
        do {
                token = Token();
                if (token != null) {
                        if (first) {
                                token.setFollowsSpace(false);
                                first = false;
                        }
                        tokens.add(token);
                }
            switch ((jj_ntk==-1)?jj_ntk():jj_ntk) {
            case IDENTIFIER:
            case PPTOKEN:
            case INTEGER:
            case STRING:
            case CHAR:
              break;
            default:
              finished = true;
              break;
            }
        } while (!finished);
        return tokens;
  }

  final public IASTLiteralTextNode ppRestOfLine(boolean skip) throws ParseException {
        Token start = token, end = start;
        if (skip)
                start = end = getNextToken();
        while (true) {
                end = getNextToken();
                if (end.kind == EOL || end.kind == EOF)
                        break;
        }
                {if (true) return getLiteralTextNodeSpanningUpTo(start, end);}
    throw new Error("Missing return statement in function");
  }

  final public void UNUSED() throws ParseException {
    jj_consume_token(ERROR);
    skip();
  }

  void skip() throws ParseException {
         getToken(1);
  }

  public TokenManager token_source;
  public Token token, jj_nt;
  private int jj_ntk;
  private int jj_gen;
  final private int[] jj_la1 = new int[7];
  static private int[] jj_la1_0;
  static {
      jj_la1_0();
   }
   private static void jj_la1_0() {
      jj_la1_0 = new int[] {0x2,0xf27b8,0x800,0x4040,0x8000,0x4040,0xf00040,};
   }


  public PreParserCore(TokenManager tm) {
    token_source = tm;
    token = new Token();
    jj_ntk = -1;
    jj_gen = 0;
    for (int i = 0; i < 7; i++) jj_la1[i] = -1;
  }

  public void ReInit(TokenManager tm) {
    token_source = tm;
    token = new Token();
    jj_ntk = -1;
    jj_gen = 0;
    for (int i = 0; i < 7; i++) jj_la1[i] = -1;
  }

  final private Token jj_consume_token(int kind) throws ParseException {
    Token oldToken;
    if ((oldToken = token).next != null) token = token.next;
    else token = token.next = token_source.getNextToken();
    jj_ntk = -1;
    if (token.kind == kind) {
      jj_gen++;
      return token;
    }
    token = oldToken;
    jj_kind = kind;
    throw generateParseException();
  }

  final public Token getNextToken() {
    if (token.next != null) token = token.next;
    else token = token.next = token_source.getNextToken();
    jj_ntk = -1;
    jj_gen++;
    return token;
  }

  final public Token getToken(int index) {
    Token t = token;
    for (int i = 0; i < index; i++) {
      if (t.next != null) t = t.next;
      else t = t.next = token_source.getNextToken();
    }
    return t;
  }

  final private int jj_ntk() {
    if ((jj_nt=token.next) == null)
      return (jj_ntk = (token.next=token_source.getNextToken()).kind);
    else
      return (jj_ntk = jj_nt.kind);
  }

  private java.util.Vector jj_expentries = new java.util.Vector();
  private int[] jj_expentry;
  private int jj_kind = -1;

  public ParseException generateParseException() {
    jj_expentries.removeAllElements();
    boolean[] la1tokens = new boolean[24];
    for (int i = 0; i < 24; i++) {
      la1tokens[i] = false;
    }
    if (jj_kind >= 0) {
      la1tokens[jj_kind] = true;
      jj_kind = -1;
    }
    for (int i = 0; i < 7; i++) {
      if (jj_la1[i] == jj_gen) {
        for (int j = 0; j < 32; j++) {
          if ((jj_la1_0[i] & (1<<j)) != 0) {
            la1tokens[j] = true;
          }
        }
      }
    }
    for (int i = 0; i < 24; i++) {
      if (la1tokens[i]) {
        jj_expentry = new int[1];
        jj_expentry[0] = i;
        jj_expentries.addElement(jj_expentry);
      }
    }
    int[][] exptokseq = new int[jj_expentries.size()][];
    for (int i = 0; i < jj_expentries.size(); i++) {
      exptokseq[i] = (int[])jj_expentries.elementAt(i);
    }
    return new ParseException(token, exptokseq, tokenImage);
  }

  final public void enable_tracing() {
  }

  final public void disable_tracing() {
  }

}
