📄 java.g
字号:
options { language="Cpp";}/** Java 1.1 Recognizer Grammar * * Run 'java JavaRecognizer <directory full of java files>' * * Authors: * John Mitchell johnm@non.net * Terence Parr parrt@magelang.com * John Lilley jlilley@empathy.com * Scott Stanchfield thetick@magelang.com * * Version 1.00 December 9, 1997 -- initial release * Version 1.01 December 10, 1997 * fixed bug in octal def (0..7 not 0..8) * Version 1.10 August 1998 (parrt) * added tree construction * fixed definition of WS_,comments for mac,pc,unix newlines * added unary plus * Version 1.11 (Nov 20, 1998) * Added "shutup" option to turn off last ambig warning. * Fixed inner class def to allow named class defs as statements * synchronized requires compound not simple statement * add [] after builtInType DOT class in primaryExpression * "const" is reserved but not valid..removed from modifiers * * This grammar is in the PUBLIC DOMAIN * * BUGS * (expression) + "string" is parsed incorrectly (+ as unary plus). * */class JavaRecognizer extends Parser;options { k = 2; // two token lookahead exportVocab=Java; // Call its vocabulary "Java" codeGenMakeSwitchThreshold = 2; // Some optimizations codeGenBitsetTestThreshold = 3; defaultErrorHandler = false; // Don't generate parser error handlers buildAST = true;}imaginaryTokenDefinitions : BLOCK MODIFIERS OBJBLOCK SLIST CTOR_DEF METHOD_DEF VARIABLE_DEF INSTANCE_INIT STATIC_INIT TYPE CLASS_DEF INTERFACE_DEF PACKAGE_DEF ARRAY_DECLARATOR EXTENDS_CLAUSE IMPLEMENTS_CLAUSE PARAMETERS PARAMETER_DEF LABELED_STAT TYPECAST INDEX_OP POST_INC POST_DEC METHOD_CALL EXPR ARRAY_INIT IMPORT UNARY_MINUS UNARY_PLUS CASE_GROUP ELIST FOR_INIT FOR_CONDITION FOR_ITERATOR EMPTY_STAT ; // Compilation Unit: In Java, this is a single file. This is the start// rule for this parsercompilationUnit : // A compilation unit starts with an optional package definition ( packageDefinition | /* nothing */ ) // Next we have a series of zero or more import statements ( importDefinition )* // Wrapping things up with any number of class or interface // definitions ( typeDefinition )* EOF! ;// Package statement: "package" followed by an identifier.packageDefinition options {defaultErrorHandler = true;} // let ANTLR handle errors : p:"package"^ {#p->setType(PACKAGE_DEF);} identifier SEMI! ;// Import statement: import followed by a package or class nameimportDefinition options {defaultErrorHandler = true;} : i:"import"^ {#i->setType(IMPORT);} identifierStar SEMI! ;// A type definition in a file is either a class or interface definition.typeDefinition options {defaultErrorHandler = true;} : m:modifiers! ( classDefinition[#m] | interfaceDefinition[#m] ) | SEMI! ;/** A declaration is the creation of a reference or primitive-type variable * Create a separate Type/Var tree for each var in the var list. */declaration! : m:modifiers t:typeSpec[false] v:variableDefinitions[#m,#t] {#declaration = #v;} ;/* A declaration with no modifierslocalVariableDeclaration : t:typeSpec[false] v:variableDefinitions[#[MODIFIERS, "MODIFIERS"],#t] {#localVariableDeclaration = #v;} ; */// A list of zero or more modifiers. We could have used (modifier)* in// place of a call to modifiers, but I thought it was a good idea to keep// this rule separate so they can easily be collected in a Vector if// someone so desiresmodifiers : ( modifier )* {#modifiers = #([MODIFIERS, "MODIFIERS"], #modifiers);} ;// A type specification is a type name with possible brackets afterwards// (which would make it an array type).typeSpec[bool addImagNode] : type (lb:LBRACK^ {#lb->setType(ARRAY_DECLARATOR);} RBRACK!)* { if ( addImagNode ) { #typeSpec = #(#[TYPE,"TYPE"], #typeSpec); } } ;// A type name. which is either a (possibly qualified) class name or// a primitive (builtin) typetype : identifier | builtInType ;// The primitive types.builtInType : "void" | "boolean" | "byte" | "char" | "short" | "int" | "float" | "long" | "double" ;// A (possibly-qualified) java identifier. We start with the first IDENT// and expand its name by adding dots and following IDENTSidentifier : IDENT ( DOT^ IDENT )* ;identifierStar : IDENT ( DOT^ IDENT )* ( DOT^ STAR )? ;// modifiers for Java classes, interfaces, class/instance vars and methodsmodifier : "private" | "public" | "protected" | "static" | "transient" | "final" | "abstract" | "native" | "threadsafe" | "synchronized"// | "const" // reserved word; leave out | "volatile" ;// Definition of a Java classclassDefinition![ANTLR_USE_NAMESPACE(antlr)RefAST modifiers] : "class" IDENT // it _might_ have a superclass... sc:superClassClause // it might implement some interfaces... ic:implementsClause // now parse the body of the class cb:classBlock {#classDefinition = #(#[CLASS_DEF,"CLASS_DEF"], modifiers,IDENT,sc,ic,cb);} ;superClassClause! : ( "extends" id:identifier )? {#superClassClause = #(#[EXTENDS_CLAUSE,"EXTENDS_CLAUSE"],id);} ;// Definition of a Java InterfaceinterfaceDefinition![ANTLR_USE_NAMESPACE(antlr)RefAST modifiers] : "interface" IDENT // it might extend some other interfaces (ie:interfaceExtends)? // now parse the body of the interface (looks like a class...) cb:classBlock {#interfaceDefinition = #(#[INTERFACE_DEF,"INTERFACE_DEF"], modifiers,IDENT,ie,cb);} ;// This is the body of a class. You can have fields and extra semicolons,// That's about it (until you see what a field is...)classBlock : LCURLY! ( field | SEMI )* RCURLY! {#classBlock = #([OBJBLOCK, "OBJBLOCK"], #classBlock);} ;// An interface can extend several other interfaces...interfaceExtends : e:"extends" {#e->setType(EXTENDS_CLAUSE);} identifier ( COMMA! identifier )* ;// A class can implement several interfaces...implementsClause : ( i:"implements"! identifier ( COMMA! identifier )* )? {#implementsClause = #(#[IMPLEMENTS_CLAUSE,"IMPLEMENTS_CLAUSE"], #implementsClause);} ;// Now the various things that can be defined inside a class or interface...// Note that not all of these are really valid in an interface (constructors,// for example), and if this grammar were used for a compiler there would// need to be some semantic checks to make sure we're doing the right thing...field! : // method, constructor, or variable declaration mods:modifiers ( h:ctorHead s:compoundStatement // constructor {#field = #(#[CTOR_DEF,"CTOR_DEF"], mods, h, s);} | cd:classDefinition[#mods] // inner class {#field = #cd;} | id:interfaceDefinition[#mods] // inner interface {#field = #id;} | t:typeSpec[false] // method or variable declaration(s) ( IDENT // the name of the method // parse the formal parameter declarations. LPAREN! param:parameterDeclarationList RPAREN! rt:returnTypeBrackersOnEndOfMethodHead[#t] // get the list of exceptions that this method is declared to throw (tc:throwsClause)? ( s2:compoundStatement | SEMI ) {#field = #(#[METHOD_DEF,"METHOD_DEF"], mods, #(#[TYPE,"TYPE"],rt), IDENT, param, tc, s2);} | v:variableDefinitions[#mods,#t] SEMI// {#field = #(#[VARIABLE_DEF,"VARIABLE_DEF"], v);} {#field = #v;} ) ) // "static { ... }" class initializer | "static" s3:compoundStatement {#field = #(#[STATIC_INIT,"STATIC_INIT"], s3);} // "{ ... }" instance initializer | compoundStatement {#field = #(#[INSTANCE_INIT,"INSTANCE_INIT"], s3);} ;variableDefinitions[ANTLR_USE_NAMESPACE(antlr)RefAST mods, ANTLR_USE_NAMESPACE(antlr)RefAST t] : variableDeclarator[getASTFactory().dupTree(mods), getASTFactory().dupTree(t)] ( COMMA! variableDeclarator[getASTFactory().dupTree(mods), getASTFactory().dupTree(t)] )* ;/** Declaration of a variable. This can be a class/instance variable, * or a local variable in a method * It can also include possible initialization. */variableDeclarator![ANTLR_USE_NAMESPACE(antlr)RefAST mods, ANTLR_USE_NAMESPACE(antlr)RefAST t] : id:IDENT d:declaratorBrackets[t] v:varInitializer {#variableDeclarator = #(#[VARIABLE_DEF,"VARIABLE_DEF"], mods, #(#[TYPE,"TYPE"],d), id, v);} ;declaratorBrackets[ANTLR_USE_NAMESPACE(antlr)RefAST typ] : {#declaratorBrackets=typ;} (lb:LBRACK^ {#lb->setType(ARRAY_DECLARATOR);} RBRACK!)* ;varInitializer : ( ASSIGN^ initializer )? ;// This is an initializer used to set up an array.arrayInitializer : lc:LCURLY^ {#lc->setType(ARRAY_INIT);} ( initializer ( // CONFLICT: does a COMMA after an initializer start a new // initializer or start the option ',' at end? // ANTLR generates proper code by matching // the comma as soon as possible. options { warnWhenFollowAmbig = false; } : COMMA! initializer )* (COMMA!)? )? RCURLY! ;// The two "things" that can initialize an array element are an expression// and another (nested) array initializer.initializer : expression | arrayInitializer ;// This is the header of a method. It includes the name and parameters// for the method.// This also watches for a list of exception classes in a "throws" clause.ctorHead : IDENT // the name of the method // parse the formal parameter declarations. LPAREN! parameterDeclarationList RPAREN! // get the list of exceptions that this method is declared to throw (throwsClause)? ;// This is a list of exception classes that the method is declared to throwthrowsClause : "throws"^ identifier ( COMMA! identifier )* ;returnTypeBrackersOnEndOfMethodHead[ANTLR_USE_NAMESPACE(antlr)RefAST typ] : {#returnTypeBrackersOnEndOfMethodHead = typ;} (lb:LBRACK^ {#lb->setType(ARRAY_DECLARATOR);} RBRACK!)* ;// A list of formal parametersparameterDeclarationList : ( parameterDeclaration ( COMMA! parameterDeclaration )* )? {#parameterDeclarationList = #(#[PARAMETERS,"PARAMETERS"], #parameterDeclarationList);} ;// A formal parameter.parameterDeclaration! : pm:parameterModifier t:typeSpec[false] id:IDENT pd:parameterDeclaratorBrackets[#t] {#parameterDeclaration = #(#[PARAMETER_DEF,"PARAMETER_DEF"], pm, #([TYPE,"TYPE"],pd), id);} ;parameterDeclaratorBrackets[ANTLR_USE_NAMESPACE(antlr)RefAST t] : {#parameterDeclaratorBrackets = t;} (lb:LBRACK^ {#lb->setType(ARRAY_DECLARATOR);} RBRACK!)* ;parameterModifier : (f:"final")? {#parameterModifier = #(#[MODIFIERS,"MODIFIERS"], f);} ;// Compound statement. This is used in many contexts:// Inside a class definition prefixed with "static":// it is a class initializer// Inside a class definition without "static":// it is an instance initializer// As the body of a method// As a completely indepdent braced block of code inside a method// it starts a new scope for variable definitionscompoundStatement : lc:LCURLY^ {#lc->setType(SLIST);} // include the (possibly-empty) list of statements (statement)* RCURLY! ;statement // A list of statements in curly braces -- start a new scope! : compoundStatement // class definition (no modifiers allowed; pass empty list) | classDefinition[#[MODIFIERS, "MODIFIERS"]] // interface definition (no modifiers allowed; pass empty list) | interfaceDefinition[#[MODIFIERS, "MODIFIERS"]] // declarations are ambiguous with "ID DOT" relative to expression // statements. Must backtrack to be sure. Could use a semantic // predicate to test symbol table to see what the type was coming // up, but that's pretty hard without a symbol table ;)// | (localVariableDeclaration)=> localVariableDeclaration SEMI! | (declaration)=> declaration SEMI! // An expression statement. This could be a method call, // assignment statement, or any other expression evaluated for // side-effects. | expression SEMI!
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -