/** * * Copyright (C) 1996, 1997 Sun Microsystems Inc. * * Use of this file and the system it is part of is constrained by the * file COPYRIGHT in the root directory of this system. You may, however, * make any modifications you wish to this file. * * Author: Sreenivasa Viswanadha * Date: 3/20/97 * * This file contains a Java grammar and actions that implement a front-end. * * * Derived in part from the following work: * * PUBLIC DOMAIN PCCTS-BASED C++ GRAMMAR (cplusplus.g, stat.g, expr.g) * * Authors: Sumana Srinivasan, NeXT Inc.; sumana_srinivasan@next.com * Terence Parr, Parr Research Corporation; parrt@parr-research.com * Russell Quong, Purdue University; quong@ecn.purdue.edu * * VERSION 1.1 * */ PARSER_BEGIN(CPPParser) public final class CPPParser { private static String vers = "0.1"; private static String id = "C++ Parser"; private static void msg(String s) { System.out.println(id + " Version " + vers +": " + s); } public static CPPProgram parse(java.io.InputStream in) throws ParseException { CPPParser parser; CPPProgram prog = null; try { parser = new CPPParser(in); prog = new CPPProgram(parser.translation_unit()); msg("Program parsed successfully."); } catch (ParseException e) { prog = null; msg(e.getMessage()); } return prog; } public static void main(String args[]) { CPPParser parser; java.io.InputStream input; int ai = 0; if (ai == (args.length-1)) { msg("Reading from file " + args[ai] + " . . ."); try { input = new java.io.FileInputStream(args[ai]); } catch (java.io.FileNotFoundException e) { msg("File " + args[0] + " not found."); return; } } else if (ai >= args.length) { msg("Reading from standard input . . ."); input = System.in; } else { msg("Usage: java " + id + " [-d] [inputfile]"); return; } try { parser = new CPPParser(input); parser.translation_unit(); msg("Program parsed successfully."); } catch (ParseException e) { msg(e.getMessage()); } } /** * A symbol table manager object. Currently only types are recorded for * doing semantic predicates for parsing. */ static SymtabManager sym; /* * Methods used in semantics predicates. */ /** * Reads a fully qualified name (since it is used during lookahead, we * cannot use token. We have to explicitly use getToken). */ static String GetFullyScopedName() { Token t = getToken(1); if (t.kind != ID && t.kind != SCOPE) return null; StringBuffer s = new StringBuffer(); int i; if (t.kind != SCOPE) { s.append(t.image); t = getToken(2); i = 3; } else i = 2; while (t.kind == SCOPE) { s.append(t.image); s.append((t = getToken(i++)).image); t = getToken(i++); } return s.toString(); } /** * This method first tries to read a sequence of tokens of the form * ("::")? ("::" )* * and if it succeeds then asks the symbol table manager if this is * the name of a constructor. */ static boolean IsCtor() { return sym.IsCtor(GetFullyScopedName()); } } PARSER_END(CPPParser) TOKEN_MGR_DECLS : { static int beginLine; static int beginCol; static boolean lineDirective = false; static void resetBeginLineCol() { } } SKIP : { " " | "\t" | "\n" | "\r" | "//" : IN_LINE_COMMENT | "/*" : IN_COMMENT | < "#" ([" ", "\t"])* "line" > : LINE_NUMBER | < "#" ([" ", "\t"])* ["0"-"9"] > { input_stream.backup(1); } : LINE_NUMBER | "#" : PREPROCESSOR_OUTPUT } SKIP: { < (["0"-"9"])+ > { try { beginLine = Integer.parseInt(image.toString()); } catch(NumberFormatException e) { } // Will never come here. } : LINE_DIRECTIVE } SKIP: { "\n" : AFTER_LINE_DIRECTIVE | <~[]> } SKIP: { <~[]> { input_stream.adjustBeginLineColumn(beginLine, 1); input_stream.backup(1); } : DEFAULT } SKIP: { "\n" : DEFAULT } MORE: { < ~[] > } SKIP: { "*/" : DEFAULT } MORE: { < ~[] > } SKIP: { "\n" : DEFAULT } MORE: { < ~[] > } TOKEN : { < LCURLYBRACE: "{" > | < RCURLYBRACE: "}" > | < LSQUAREBRACKET: "[" > | < RSQUAREBRACKET: "]" > | < LPARENTHESIS: "(" > | < RPARENTHESIS: ")" > | < SCOPE: "::" > | < COLON: ":" > | < SEMICOLON: ";" > | < COMMA: "," > | < QUESTIONMARK: "?" > | < ELLIPSIS: "..." > | < ASSIGNEQUAL: "=" > | < TIMESEQUAL: "*=" > | < DIVIDEEQUAL: "/=" > | < MODEQUAL: "%=" > | < PLUSEQUAL: "+=" > | < MINUSEQUAL: "-=" > | < SHIFTLEFTEQUAL: "<<=" > | < SHIFTRIGHTEQUAL: ">>=" > | < BITWISEANDEQUAL: "&=" > | < BITWISEXOREQUAL: "^=" > | < BITWISEOREQUAL: "|=" > | < OR: "||" > | < AND: "&&" > | < BITWISEOR: "|" > | < BITWISEXOR: "^" > | < AMPERSAND: "&" > | < EQUAL: "==" > | < NOTEQUAL: "!=" > | < LESSTHAN: "<" > | < GREATERTHAN: ">" > | < LESSTHANOREQUALTO: "<=" > | < GREATERTHANOREQUALTO: ">=" > | < SHIFTLEFT: "<<" > | < SHIFTRIGHT: ">>" > | < PLUS: "+" > | < MINUS: "-" > | < STAR: "*" > | < DIVIDE: "/" > | < MOD: "%" > | < PLUSPLUS: "++" > | < MINUSMINUS: "--" > | < TILDE: "~" > | < NOT: "!" > | < DOT: "." > | < POINTERTO: "->" > | < DOTSTAR: ".*" > | < ARROWSTAR: "->*" > | < AUTO: "auto" > | < BREAK: "break" > | < CASE: "case" > | < CATCH: "catch" > | < CHAR: "char" > | < CONST: "const" > | < CONTINUE: "continue" > | < _DEFAULT: "default" > | < DELETE: "delete" > | < DO: "do" > | < DOUBLE: "double" > | < ELSE: "else" > | < ENUM: "enum" > | < EXTERN: "extern" > | < FLOAT: "float" > | < FOR: "for" > | < FRIEND: "friend" > | < GOTO: "goto" > | < IF: "if" > | < INLINE: "inline" > | < INT: "int" > | < LONG: "long" > | < NEW: "new" > | < PRIVATE: "private" > | < PROTECTED: "protected" > | < PUBLIC: "public" > | < REDECLARED: "redeclared" > | < REGISTER: "register" > | < RETURN: "return" > | < SHORT: "short" > | < SIGNED: "signed" > | < SIZEOF: "sizeof" > | < STATIC: "static" > | < STRUCT: "struct" > | < CLASS : "class" > | < SWITCH: "switch" > | < TEMPLATE: "template" > | < THIS: "this" > | < TRY: "try" > | < TYPEDEF: "typedef" > | < UNION: "union" > | < UNSIGNED: "unsigned" > | < VIRTUAL: "virtual" > | < VOID: "void" > | < VOLATILE: "volatile" > | < WHILE: "while" > | < OPERATOR: "operator" > | < TRUETOK: "true" > | < FALSETOK: "false" > | < THROW: "throw" > } TOKEN [IGNORE_CASE] : { < OCTALINT : "0" (["0"-"7"])* > | < OCTALLONG : "l" > | < UNSIGNED_OCTALINT : "u" > | < UNSIGNED_OCTALLONG : ("ul" | "lu") > | < DECIMALINT : ["1"-"9"] (["0"-"9"])* > | < DECIMALLONG : ["u","l"] > | < UNSIGNED_DECIMALINT : "u" > | < UNSIGNED_DECIMALLONG : ("ul" | "lu") > | < HEXADECIMALINT : "0x" (["0"-"9","a"-"f"])+ > | < HEXADECIMALLONG : (["u","l"])? > | < UNSIGNED_HEXADECIMALINT : "u" > | < UNSIGNED_HEXADECIMALLONG : ("ul" | "lu") > | < FLOATONE : ((["0"-"9"])+ "." (["0"-"9"])* | (["0"-"9"])* "." (["0"-"9"])+) ("e" (["-","+"])? (["0"-"9"])+)? (["f","l"])? > | < FLOATTWO : (["0"-"9"])+ "e" (["-","+"])? (["0"-"9"])+ (["f","l"])? > } TOKEN : { < CHARACTER : ("L")? "'" ( (~["'","\\","\n","\r"]) | ("\\" ( ["n","t","v","b","r","f","a","\\","?","'","\""] | "0" (["0"-"7"])* | ["1"-"9"] (["0"-"9"])* | ("0x" | "0X") (["0"-"9","a"-"f","A"-"F"])+ ) ) ) "'" > | < STRING : ("L")? "\"" ( ( ~["\"","\\","\n","\r"]) | ("\\" ( ["n","t","v","b","r","f","a","\\","?","'","\""] | "0" (["0"-"7"])* | ["1"-"9"] (["0"-"9"])* | ("0x" | "0X") (["0"-"9","a"-"f","A"-"F"])+ ) ) )* "\"" > } TranslationUnit translation_unit() : { TranslationUnit trans = new TranslationUnit(); ExternalDeclaration_NPList list = new ExternalDeclaration_NPList(); ExternalDeclaration ed = null; } { { sym.OpenScope(null, false); } ( LOOKAHEAD(2) ed=external_declaration() { if(ed != null) { list.addElement(ed); } } )* { sym.CloseScope(); trans.set_externaldeclaration_nplist(list); return trans; } } ExternalDeclaration external_declaration() : { ExternalDeclaration ed = null; Declaration decl = null; DeclarationSpecifiers declspec = null; } { ( LOOKAHEAD(("typedef" | template_head())? class_head() "{") ( template_head() )? decl = declaration() | LOOKAHEAD("enum" ()? "{") enum_specifier() (init_declarator_list(false))? ";" | LOOKAHEAD ((template_head())? dtor_ctor_decl_spec() dtor_declarator() "{") dtor_definition() | LOOKAHEAD(dtor_ctor_decl_spec() ctor_declarator_lookahead()) ctor_definition() | LOOKAHEAD((declaration_specifiers())? function_declarator_lookahead()) function_definition() | LOOKAHEAD((scope_override())? "operator") conversion_function_decl_or_def() | template_head() ( LOOKAHEAD(dtor_ctor_decl_spec() ctor_declarator_lookahead()) ctor_definition() | LOOKAHEAD((declaration_specifiers())? function_declarator_lookahead()) function_definition() | declspec = declaration_specifiers() (init_declarator_list(declspec.get_isTypeDef()))? ";" ) | decl = declaration() | ";" ) { if(decl != null) { ed = new ExternalDeclaration(decl); } return ed; } } FunctionDefinition function_definition() : { // Scope sc = null; DeclarationSpecifiers declspec = null; FunctionDefinition funcdef = new FunctionDefinition(); } { ( LOOKAHEAD(3) declspec = declaration_specifiers() funcdef = function_declarator(declspec.get_isTypeDef()) func_decl_def(funcdef.get_scope()) { try { funcdef.set_returntype(new ReturnType((BuiltInTypeSpecifier)declspec)); } catch(ClassCastException e) { // if there was no type specified, default is integer funcdef.set_returntype(new ReturnType(new BuiltInTypeSpecifier(false, "int"))); } } | funcdef = function_declarator(false) func_decl_def(funcdef.get_scope()) ) { return funcdef; } } void func_decl_def(Scope sc) : { boolean closeReqd = false; } { { if (closeReqd = (sc != null && sc != sym.GetCurScope())) sym.OpenScope(sc); } ( ";" | compound_statement() ) { if (closeReqd) sym.CloseScope(); } } void linkage_specification() : {} { "extern" ( "{" ( external_declaration() )* "}" ( LOOKAHEAD(";") ";")? | declaration() ) } Declaration declaration() : { Declaration decl = null; DeclarationSpecifiers declspec = null; boolean isTypedef = false; } { ( LOOKAHEAD(2) declspec = declaration_specifiers() (init_declarator_list(declspec.get_isTypeDef()))? ";" | linkage_specification() ) { if(declspec != null) { decl = new Declaration(declspec); } return decl; } } /** * Very temporary. Just returns true if it sees a typedef. Finally, we will * need a structure that stores all the attributes. */ boolean type_modifiers() : { boolean isTypedef = false; } { ( isTypedef = storage_class_specifier() | type_qualifier() | "inline" | "virtual" | "friend" ) { return isTypedef; } } /** * Very temporary. Just returns true if it sees a typedef. Finally, we will * need a structure that stores all the attributes. */ DeclarationSpecifiers declaration_specifiers() : { Token t; DeclarationSpecifiers declspec = null; boolean isTypeDef = false, tmp; } { ( ( LOOKAHEAD(type_modifiers()) tmp = type_modifiers() { isTypeDef |= tmp; } )+ // AM - only supporting 1 built-in-type specifier, which is used for // function args [ LOOKAHEAD(2) ( LOOKAHEAD(builtin_type_specifier()) declspec = builtin_type_specifier() ( LOOKAHEAD(2) ( LOOKAHEAD(builtin_type_specifier()) builtin_type_specifier() | LOOKAHEAD(type_modifiers()) tmp = type_modifiers() ) { isTypeDef |= tmp; } )* | ( declspec = class_specifier() | enum_specifier() | qualified_type() ) (LOOKAHEAD(2) tmp = type_modifiers() { isTypeDef |= tmp;} )* ) ] | // AM - only supporting 1 built-in-type specifier, which is used for // function args LOOKAHEAD(builtin_type_specifier()) declspec = builtin_type_specifier() ( LOOKAHEAD(2) ( LOOKAHEAD(builtin_type_specifier()) builtin_type_specifier() | tmp = type_modifiers() { isTypeDef |= tmp; } ) )* | ( declspec = class_specifier() | enum_specifier() | qualified_type() ) (LOOKAHEAD(2) tmp = type_modifiers() { isTypeDef |= tmp; } )* ) { if(declspec == null) { declspec = new UnknownTypeSpecifier(); } declspec.set_isTypeDef(isTypeDef); return declspec; } } /* void type_specifier() : {} { simple_type_specifier() | class_specifier() | enum_specifier() } */ void simple_type_specifier() : {} { ( builtin_type_specifier() | qualified_type() ) } void scope_override_lookahead() : {} { "::" | ("<" template_argument_list() ">")? "::" } String scope_override() : { String name = ""; Token t; } { ( ("::") { name += "::"; } ( LOOKAHEAD(2) t = ("<" template_argument_list() ">")? "::" { name += t.image + "::"; } )* | ( LOOKAHEAD(2) t = ("<" template_argument_list() ">")? "::" { name += t.image + "::"; } )+ ) { return name; } } String qualified_id() : { String name = ""; Token t; } { [ LOOKAHEAD(scope_override_lookahead()) name = scope_override() ] ( t = [ "<" template_argument_list() ">" ] { return name + t.image; } | "operator" optor() { return "operator"; } ) } void ptr_to_member() : {} { scope_override() "*" } void qualified_type() : {} { LOOKAHEAD({ sym.IsFullyScopedTypeName(GetFullyScopedName()) } ) qualified_id() } void type_qualifier() : {} { "const" | "volatile" } /** * Very temporary. Just returns true if it sees a typedef. Finally, we will * need a structure that stores all the attributes. */ boolean storage_class_specifier() : {} { ( "auto" | "register" | "static" | "extern" ) { return false; } | "typedef" { return true; } } BuiltInTypeSpecifier builtin_type_specifier() : {} { "void" { return new BuiltInTypeSpecifier(false, "void"); } | "char" { return new BuiltInTypeSpecifier(false, "char"); } | "short" { return new BuiltInTypeSpecifier(false, "short"); } | "int" { return new BuiltInTypeSpecifier(false, "int"); } | "long" { return new BuiltInTypeSpecifier(false, "long"); } | "float" { return new BuiltInTypeSpecifier(false, "float"); } | "double" { return new BuiltInTypeSpecifier(false, "double"); } | "signed" { return new BuiltInTypeSpecifier(false, "signed"); } | "unsigned" { return new BuiltInTypeSpecifier(false, "unsigned"); } } void init_declarator_list(boolean isTypedef) : {} { init_declarator(isTypedef) ("," init_declarator(isTypedef))* } void init_declarator(boolean isTypedef) : { String name; Declarator decl = new Declarator(); } { declarator(decl) { if (isTypedef) sym.PutTypeName(decl.get_name()); } ( "=" initializer() | "(" expression_list() ")" )? } void class_head() : {} { ("struct" | "union" | "class") ( (base_clause(null))?)? } ClassSpecifier class_specifier() : { ClassSpecifier classspec = new ClassSpecifier(); MemberDeclaration_NPList list = new MemberDeclaration_NPList(); MemberDeclaration membdecl = null; ClassScope sc = null; Token t; } { ( ("struct" | "union" | "class" ) ( "{" { sym.OpenScope(null, false); } ( membdecl = member_declaration() { if(membdecl != null) { list.addElement(membdecl); } } )* "}" { sym.CloseScope(); } | LOOKAHEAD(2) t = { sc = (ClassScope)sym.OpenScope(t.image, true); // remember the classname classspec.set_name(new ClassName(t.image)); } (base_clause(sc))? "{" ( membdecl = member_declaration() { if(membdecl != null) { list.addElement(membdecl); } } )* "}" { sym.CloseScope(); } | t= (LOOKAHEAD(2) "<" template_argument_list() ">")? { sym.PutTypeName(t.image); // remember the classname classspec.set_name(new ClassName(t.image)); } ) ) { classspec.set_memberdeclaration_nplist(list); return classspec; } } void base_clause(ClassScope scope) : {} { ":" base_specifier(scope) ( "," base_specifier(scope) )* } void base_specifier(ClassScope scope) : { Token t; } { ("virtual" (access_specifier())? | access_specifier() ("virtual")?)? (LOOKAHEAD(scope_override_lookahead()) scope_override())? t = ("<" template_argument_list() ">")? { scope.AddSuper(sym.GetScope(t.image)); } } void access_specifier() : {} { "public" | "protected" | "private" } MemberDeclaration member_declaration() : { MemberDeclaration membdecl = null; DeclarationSpecifiers declspec = null; } { ( LOOKAHEAD(("typedef")? class_head() "{") declaration() | LOOKAHEAD("enum" ()? "{") enum_specifier() ( member_declarator_list(false) )? ";" | LOOKAHEAD( "operator" ) conversion_function_decl_or_def() | LOOKAHEAD(dtor_ctor_decl_spec() dtor_declarator() "{") dtor_definition() | LOOKAHEAD(("inline"| "virtual")* "~") dtor_ctor_decl_spec() simple_dtor_declarator() ";" | LOOKAHEAD(dtor_ctor_decl_spec() ctor_declarator_lookahead()) ctor_definition() | LOOKAHEAD(dtor_ctor_decl_spec() ctor_declarator_lookahead() ";") (dtor_ctor_decl_spec() ctor_declarator() ";") | LOOKAHEAD((declaration_specifiers())? function_declarator_lookahead()) membdecl = function_definition() | LOOKAHEAD(declaration_specifiers()) declspec = declaration_specifiers() (member_declarator_list(declspec.get_isTypeDef()))? ";" | LOOKAHEAD() function_declarator(false) ";" | LOOKAHEAD(3) qualified_id() ";" | access_specifier() ":" | ";" ) { return membdecl; } } void member_declarator_list(boolean isTypedef) : {} { member_declarator(isTypedef) ("=" )? ("," member_declarator(isTypedef) ("=" )?)* } void member_declarator(boolean isTypedef) : { String name; Declarator decl = new Declarator(); } { declarator(decl) { if (isTypedef) sym.PutTypeName(decl.get_name()); } } void conversion_function_decl_or_def() : { Scope sc = null; String name = null; } { [ LOOKAHEAD(scope_override_lookahead()) name = scope_override() ] "operator" declaration_specifiers() ("*" | "&")? "(" (parameter_list())? ")" (LOOKAHEAD(2) type_qualifier())? (exception_spec())? func_decl_def(null) // Temporary (fix the null) } void enum_specifier() : { Token t; } { "enum" ( "{" enumerator_list() "}" | t= (LOOKAHEAD(2) "{" enumerator_list() "}")? { sym.PutTypeName(t.image); } ) } void enumerator_list() : {} { enumerator() ("," enumerator())* } void enumerator() : {} { ("=" constant_expression())? } String ptr_operator() : { String op = new String(); } { ( "&" cv_qualifier_seq() {op = "&"; } | "*" cv_qualifier_seq() {op = "*"; } | ptr_to_member() cv_qualifier_seq() {msg ("Ignoring ptr_to_member"); } ) { return op; } } void cv_qualifier_seq() : {} { [ LOOKAHEAD(2) ( "const" [ LOOKAHEAD(2) "volatile" ] | "volatile" [ LOOKAHEAD(2) "const" ] ) ] } void declarator(Declarator decl) : { String name; String ptrop; } { ( LOOKAHEAD(ptr_operator()) ptrop = ptr_operator() declarator(decl) { if(decl.get_anypointeroperator_nplist() == null) { decl.set_anypointeroperator_nplist(new AnyPointerOperator_NPList()); } decl.get_anypointeroperator_nplist().addElement(new PointerOperator(ptrop)); } | name = direct_declarator() { decl.set_name(name); if(decl.get_anypointeroperator_nplist() == null) { decl.set_anypointeroperator_nplist(new AnyPointerOperator_NPList()); } decl.get_anypointeroperator_nplist().addElement(new EPointerOperator()); } ) } String direct_declarator() : { String name; Token t; Declarator decl = new Declarator(); } { LOOKAHEAD(2) "~" t = (LOOKAHEAD(2) declarator_suffixes())? { return ("~" + t.image); } | "(" declarator(decl) ")" (LOOKAHEAD(2) declarator_suffixes())? { return (decl.get_name()); } | name = qualified_id() (LOOKAHEAD(2) declarator_suffixes())? { return (name); } } void declarator_suffixes() : {} { ("[" (constant_expression())? "]" )+ | "(" (parameter_list())? ")" (LOOKAHEAD(2) type_qualifier())? (exception_spec())? } /** * Used only for lookahead. */ void function_declarator_lookahead() : {} { (LOOKAHEAD(2) ptr_operator() )* qualified_id() "(" } FunctionDefinition function_declarator(boolean isTypedef) : { FunctionDefinition funcdef = null; } { ( LOOKAHEAD(ptr_operator()) ptr_operator() funcdef = function_declarator(isTypedef) | funcdef = function_direct_declarator(isTypedef) ) { return funcdef; } } FunctionDefinition function_direct_declarator(boolean isTypedef) : { String name; Scope sc = null; boolean closeReqd = false; FunctionDefinition funcdef = new FunctionDefinition(); ParameterDeclaration_NPList paramlist = null; } { name = qualified_id() { sc = sym.GetScopeOfFullyScopedName(name); if (closeReqd = (sc != null && sc != sym.GetCurScope())) sym.OpenScope(sc); // store the name funcdef.set_name(new FunctionName(name)); } "(" (paramlist = parameter_list())? ")" (LOOKAHEAD(2) type_qualifier())? (exception_spec())? (LOOKAHEAD("=") "=" )? { if (closeReqd) sym.CloseScope(); if (isTypedef) sym.PutTypeName(name); // remember parameters funcdef.set_parameterdeclaration_nplist(paramlist); return funcdef; } } void dtor_ctor_decl_spec() : {} { [ "virtual" [ "inline"] | "inline" [ "virtual"] ] } void dtor_definition() : {} { (template_head())? dtor_ctor_decl_spec() dtor_declarator() compound_statement() } void ctor_definition() : { Scope sc = null; boolean closeReqd = false; } { dtor_ctor_decl_spec() sc = ctor_declarator() { if (closeReqd = (sc != null && sc != sym.GetCurScope())) sym.OpenScope(sc); } (exception_spec())? ( ";" | [ ctor_initializer() ] compound_statement() ) { if (closeReqd) sym.CloseScope(); } } void ctor_declarator_lookahead() : {} { LOOKAHEAD( { IsCtor() } ) qualified_id() "(" } Scope ctor_declarator() : { String name; Scope sc = null; boolean closeReqd = false; } { LOOKAHEAD( { IsCtor() } ) name = qualified_id() { sc = sym.GetScopeOfFullyScopedName(name); if (closeReqd = (sc != null && sc != sym.GetCurScope())) sym.OpenScope(sc); } "(" [ LOOKAHEAD(2) parameter_list() ] ")" [ LOOKAHEAD(2) exception_spec() ] { if (closeReqd) sym.CloseScope(); return sc; } } void ctor_initializer() : {} { ":" superclass_init() ("," superclass_init())* } void superclass_init() : {} { qualified_id() "(" (expression_list())? ")" } void dtor_declarator() : {} { (LOOKAHEAD(scope_override_lookahead()) scope_override())? simple_dtor_declarator() } void simple_dtor_declarator() : {} { "~" LOOKAHEAD( { IsCtor() } ) "(" (parameter_list())? ")" } ParameterDeclaration_NPList parameter_list() : { ParameterDeclaration_NPList paramlist = null; } { ( paramlist = parameter_declaration_list() [ LOOKAHEAD(2) [ "," ] "..." ] | "..." ) { return paramlist; } } ParameterDeclaration_NPList parameter_declaration_list() : { ParameterDeclaration_NPList paramlist = new ParameterDeclaration_NPList(); ParameterDeclaration paramdecl = null; } { (paramdecl = parameter_declaration()) { paramlist.addElement(paramdecl); } (LOOKAHEAD(2) "," (paramdecl = parameter_declaration()) { paramlist.addElement(paramdecl); } )* { return paramlist; } } ParameterDeclaration parameter_declaration() : { ParameterDeclaration paramdecl = new ParameterDeclaration(); DeclarationSpecifiers typedeclspec = null; Declarator decl = new Declarator(); } { typedeclspec = declaration_specifiers() { // verify the declspec if a built in type specifier, // throws an exception otherwise paramdecl.set_builtintypespecifier((BuiltInTypeSpecifier)typedeclspec); } ( LOOKAHEAD(declarator(new Declarator())) declarator(decl) | abstract_declarator() ) ("=" assignment_expression())? { paramdecl.set_declarator(decl); return paramdecl; } } void initializer() : {} { LOOKAHEAD(3) "{" initializer() ("," initializer())* "}" | assignment_expression() } void type_name() : {} { declaration_specifiers() abstract_declarator() } void abstract_declarator() : {} { [ LOOKAHEAD(2) ( "(" abstract_declarator() ")" (abstract_declarator_suffix())+ | ("[" (constant_expression())? "]")+ | ptr_operator() abstract_declarator() ) ] } void abstract_declarator_suffix() : {} { "[" ( constant_expression() )? "]" | "(" (parameter_list())? ")" } void template_head() : {} { "template" "<" template_parameter_list() ">" } void template_parameter_list() : {} { template_parameter() ("," template_parameter())* } void template_parameter() : { Token t; } { LOOKAHEAD(3) "class" t= { sym.PutTypeName(t.image); } | parameter_declaration() } void template_id() : {} { "<" template_argument_list() ">" } void template_argument_list() : {} { template_argument() ("," template_argument())* } void template_argument() : {} { LOOKAHEAD(3) type_name() | shift_expression() } void statement_list() : {} { (LOOKAHEAD(statement()) statement())+ } void statement() : {} { LOOKAHEAD( declaration() ) declaration() | LOOKAHEAD( expression() ";" ) expression() ";" | compound_statement() | selection_statement() | jump_statement() | ";" | try_block() | throw_statement() | LOOKAHEAD(2) labeled_statement() | iteration_statement() } void labeled_statement() : {} { ":" statement() | "case" constant_expression() ":" statement() | "default" ":" statement() } void compound_statement() : {} { "{" { sym.OpenScope(null, false); } (statement_list())? { sym.CloseScope(); } "}" } void selection_statement() : {} { "if" "(" expression() ")" statement() (LOOKAHEAD(2) "else" statement())? | "switch" "(" expression() ")" statement() } void iteration_statement() : {} { "while" "(" expression() ")" statement() | "do" statement() "while" "(" expression() ")" ";" | "for" "(" (LOOKAHEAD(3) declaration() | expression() ";" | ";") (expression())? ";" (expression())? ")" statement() } void jump_statement() : {} { "goto" ";" | "continue" ";" | "break" ";" | "return" (expression())? ";" } void try_block() : {} { "try" compound_statement() (handler())* } void handler() : {} { "catch" "(" exception_declaration() ")" compound_statement() | "finally" compound_statement() } void exception_declaration() : {} { parameter_declaration_list() | "..." } void throw_statement() : {} { "throw" (assignment_expression())? ";" } void expression() : {} { assignment_expression() ( LOOKAHEAD(2) "," assignment_expression())* } void assignment_expression() : {} { conditional_expression() (("=" | "*=" | "/=" | "%=" | "+=" | "-=" | "<<=" | ">>=" | "&=" | "^=" | "|=" ) assignment_expression() )? } void conditional_expression() : {} { logical_or_expression() ("?" conditional_expression() ":" conditional_expression())? } void constant_expression() : {} { conditional_expression() } void logical_or_expression() : {} { logical_and_expression() ( "||" logical_and_expression())* } void logical_and_expression() : {} { inclusive_or_expression() ( "&&" inclusive_or_expression())* } void inclusive_or_expression() : {} { exclusive_or_expression()( "|" exclusive_or_expression())* } void exclusive_or_expression() : {} { and_expression()( "^" and_expression())* } void and_expression() : {} { equality_expression()( LOOKAHEAD(2) "&" equality_expression())* } void equality_expression() : {} { relational_expression()(( "!=" | "==") relational_expression())* } void relational_expression() : {} { shift_expression() ( LOOKAHEAD(2) ( "<" | ">" | "<=" | ">=" ) shift_expression() )* } void shift_expression() : {} { additive_expression()(( "<<" | ">>") additive_expression())* } void additive_expression() : {} { multiplicative_expression() (LOOKAHEAD(2) ( "+" | "-") multiplicative_expression())* } void multiplicative_expression() : {} { pm_expression() (LOOKAHEAD(2) ( "*" | "/" | "%") pm_expression())* } void pm_expression() : {} { cast_expression() (( ".*" | "->*" ) cast_expression())* } void cast_expression() : {} { LOOKAHEAD( "(" type_name() ")" ) "(" type_name() ")" cast_expression() | unary_expression() } void unary_expression() : {} { "++" unary_expression() | "--" unary_expression() | LOOKAHEAD(3) unary_operator() cast_expression() | "sizeof" ( LOOKAHEAD("(") "(" type_name() ")" | unary_expression() ) | postfix_expression() } void new_expression() : {} { (LOOKAHEAD("::") ("::"))? "new" ( LOOKAHEAD("(" type_name() ")" ) "(" type_name() ")" | (LOOKAHEAD("(" expression_list() ) "(" expression_list() ")")? ( LOOKAHEAD("(" type_name() ")" ) "(" type_name() ")" | LOOKAHEAD(declaration_specifiers()) new_type_id() ) ) (LOOKAHEAD(new_initializer()) new_initializer())? } void new_type_id() : {} { declaration_specifiers() ( LOOKAHEAD(new_declarator()) new_declarator() )? } void new_declarator() : {} { direct_new_declarator() | ptr_operator() cv_qualifier_seq() [ LOOKAHEAD(2) new_declarator() ] } void direct_new_declarator() : {} { (LOOKAHEAD(2) "[" expression() "]" )+ } void new_initializer() : {} { "(" ( expression_list() )? ")" } void delete_expression() : {} { ( "::" )? "delete" ( "[" "]" )? cast_expression() } void unary_operator() : {} { "&" | "*" | "+" | "-" | "~" | "!" } void postfix_expression() : {} { LOOKAHEAD(3) primary_expression() ( LOOKAHEAD(2) ( "[" expression() "]" | "(" ( expression_list() )? ")" | "." id_expression() | "->" id_expression() | "++" | "--" ) )* | simple_type_specifier() "(" ( expression_list() )? ")" } void id_expression() : {} { (LOOKAHEAD(scope_override_lookahead()) scope_override())? ( | "operator" optor() | "~" ) } void primary_expression() : {} { "this" | ( LOOKAHEAD(2) )+ | "(" expression() ")" | LOOKAHEAD( ("::")? "new") new_expression() | LOOKAHEAD( ("::")? "delete") delete_expression() | id_expression() | constant() } void expression_list() : {} { assignment_expression()( "," assignment_expression())* } void constant() : {} { | | | | | | | | | | | | | | | "true" | "false" } void optor() : {} { "new" [ LOOKAHEAD(2) "[" "]" ] | "delete" [ LOOKAHEAD(2) "[" "]" ] | "+" | "-" | "*" | "/" | "%" | "^" | "&" | "|" | "~" | "!" | "=" | "<" | ">" | "+=" | "-=" | "*=" | "/=" | "%=" | "^=" | "&=" | "|=" | "<<" | ">>" | ">>=" | "<<=" | "==" | "!=" | "<=" | ">=" | "&&" | "||" | "++" | "--" | "," | "->*" | "->" | "(" ")" | "[" "]" | declaration_specifiers() (LOOKAHEAD(2) ("*"|"&"))? } void exception_spec() : {} { "throw" "(" exception_list() ")" } void exception_list() : {} { type_name() ( "," type_name())* } TOKEN : { < ID : ["a"-"z","A"-"Z", "_"] (["a"-"z","A"-"Z","0"-"9","_"])* > } /*end*/