new, way better build system, tests, and template output
authorAaron Becker <abecker3@illinois.edu>
Tue, 3 Jun 2008 21:19:46 +0000 (21:19 +0000)
committerAaron Becker <abecker3@illinois.edu>
Tue, 3 Jun 2008 21:19:46 +0000 (21:19 +0000)
src/langs/charj/LICENSE [new file with mode: 0644]
src/langs/charj/Makefile [new file with mode: 0644]
src/langs/charj/build.xml [new file with mode: 0644]
src/langs/charj/src/charj/Main.java [new file with mode: 0644]
src/langs/charj/src/charj/translator/Charj.g [new file with mode: 0644]
src/langs/charj/src/charj/translator/Charj.stg [new file with mode: 0644]
src/langs/charj/src/charj/translator/CharjEmitter.g [new file with mode: 0644]
src/langs/charj/src/charj/translator/CharjTreeParser.g [new file with mode: 0644]
src/langs/charj/src/charj/translator/Translator.java [new file with mode: 0644]
src/langs/charj/tests/hello.cj [new file with mode: 0644]

diff --git a/src/langs/charj/LICENSE b/src/langs/charj/LICENSE
new file mode 100644 (file)
index 0000000..4aabbaa
--- /dev/null
@@ -0,0 +1,68 @@
+This software is distributed under the Illinois public license, as described
+in charm/LICENSE. 
+
+Portions of the Charj grammar are based on a Java 1.5 recognizer by Habelitz
+Software Developments. This recognizer is available at
+http://antlr.org/grammar/1207932239307/Java1_5Grammars
+and is governed by the following license:
+
+BSD licence
+Copyright (c) 2007-2008 by HABELITZ Software Developments
+All rights reserved.
+http://www.habelitz.com
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions
+are met:
+
+ 1. Redistributions of source code must retain the above copyright
+    notice, this list of conditions and the following disclaimer.
+ 2. Redistributions in binary form must reproduce the above copyright
+    notice, this list of conditions and the following disclaimer in the
+    documentation and/or other materials provided with the distribution.
+ 3. The name of the author may not be used to endorse or promote products
+    derived from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY HABELITZ SOFTWARE DEVELOPMENTS ('HSD') ``AS IS'' 
+AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 
+IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 
+ARE DISCLAIMED. IN NO EVENT SHALL 'HSD' BE LIABLE FOR ANY DIRECT, INDIRECT, 
+INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 
+LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, 
+OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 
+LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 
+NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, 
+EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+
+Portions of the Charj language are based on the Mantra language by Terence
+Parr. This software is available at http://www.linguamantra.org/ and is
+governed by the following license:
+
+[The "BSD licence"]
+Copyright (c) 2007 Terence Parr
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions
+are met:
+
+ 1. Redistributions of source code must retain the above copyright
+    notice, this list of conditions and the following disclaimer.
+ 2. Redistributions in binary form must reproduce the above copyright
+    notice, this list of conditions and the following disclaimer in the
+    documentation and/or other materials provided with the distribution.
+ 3. The name of the author may not be used to endorse or promote products
+    derived from this software without specific prior written permission.
+
+THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
diff --git a/src/langs/charj/Makefile b/src/langs/charj/Makefile
new file mode 100644 (file)
index 0000000..66842a9
--- /dev/null
@@ -0,0 +1,18 @@
+ANT=ant -lib lib/ant-antlr3.jar
+
+# Ant does the actual building, just invoke it
+.DEFAULT_GOAL:dist
+dist:
+       $(ANT) dist
+compile:
+       $(ANT) compile
+clean:
+       $(ANT) clean
+doc:
+       $(ANT) doc
+all:
+       $(ANT) all
+
+test:
+       ./bin/charjc tests/hello.cj
+
diff --git a/src/langs/charj/build.xml b/src/langs/charj/build.xml
new file mode 100644 (file)
index 0000000..b9f7a35
--- /dev/null
@@ -0,0 +1,131 @@
+<project name="Charj" default="dist" basedir=".">\r
+    <description>\r
+        A translator and standard library for Charj, a language based on the\r
+        Charm++ runtime system.\r
+    </description>\r
+    \r
+    <property name="project.name" value="Charj" />\r
+    \r
+    <!-- set global properties for this build -->\r
+    <property name="build" location="build"/>\r
+    <property name="src" location="src"/>\r
+    <property name="buildsrc" location="${build}/src"/>\r
+    <property name="buildlib" location="${build}/lib" />\r
+    <property name="classes" location="${build}/classes"/>\r
+    <property name="lib" location="lib" />\r
+    <property name="doc" location="docs"/>\r
+\r
+    <property name="package" value="charj"/>\r
+    \r
+    <!-- where to write/find token files -->\r
+    <property name="token.lib" location="${buildsrc}/${package}" />\r
+\r
+    <!-- Define path used for classpath later -->\r
+    <path id="project.class.path">\r
+        <pathelement location="lib/antlr-2.7.7.jar"/>\r
+        <pathelement location="lib/antlr-3.0.1.jar"/>\r
+        <pathelement location="lib/antlr-runtime-3.0.1.jar"/>\r
+        <pathelement location="lib/stringtemplate-3.1b1.jar"/>\r
+    </path>\r
+\r
+    <!-- antlr options -->\r
+    <property name="profile" value="false" />\r
+    <property name="report" value="false" />\r
+    <property name="multithreaded" value="true" />\r
+    <property name="depend" value="true" />\r
+\r
+    <target name="init">\r
+        <tstamp />\r
+        <!-- Create the build directory structure used by compile -->\r
+        <copy todir="${buildsrc}">\r
+            <fileset dir="${src}"/>\r
+        </copy>\r
+        <mkdir dir="${classes}" />\r
+        <mkdir dir="${classes}/META-INF" />\r
+        <mkdir dir="${buildlib}" />\r
+        <mkdir dir="${doc}" />\r
+    </target>\r
+\r
+    <macrodef name="antlr3">\r
+        <attribute name="grammar.name"/>\r
+        <attribute name="grammar.path"/>\r
+        <sequential>\r
+            <echo message="antlr @{grammar.name}" />\r
+            <antlr:antlr3 xmlns:antlr="antlib:org/apache/tools/ant/antlr" \r
+                target="@{grammar.path}/@{grammar.name}" \r
+                outputdirectory="@{grammar.path}"\r
+                libdirectory="@{grammar.path}"\r
+                multithreaded="${multithreaded}"\r
+                report="${report}"\r
+                depend="${depend}"\r
+                profile="${profile}">\r
+                <classpath refid="project.class.path"/>\r
+            </antlr:antlr3>\r
+        </sequential>\r
+    </macrodef>\r
+    \r
+    <target name="Charj" depends="init">\r
+        <antlr3 grammar.name="Charj.g" \r
+            grammar.path="${buildsrc}/charj/translator"/>\r
+    </target>\r
+\r
+    <target name="CharjEmitter" depends="Charj">\r
+        <antlr3 grammar.name="CharjEmitter.g" \r
+            grammar.path="${buildsrc}/charj/translator"/>\r
+    </target>\r
+    \r
+    <target name="compile" depends="Charj, CharjEmitter" description="compile">\r
+        <javac debug="true" srcdir="${buildsrc}" destdir="${classes}"\r
+               target="1.5" listfiles="Yes" deprecation="Yes">\r
+            <classpath refid="project.class.path"/>\r
+        </javac>\r
+    </target>\r
+\r
+    <target name="manifest">\r
+        <manifest file="${classes}/META-INF/MANIFEST.MF">\r
+            <attribute name="Main-Class" value="charj.Main" />\r
+        </manifest>\r
+    </target>\r
+\r
+    <target name="dist" depends="compile, manifest" \r
+       description="create jarfiles">\r
+       <jar jarfile="${buildlib}/charj.jar" basedir="${classes}"\r
+           manifest="${classes}/META-INF/MANIFEST.MF"/>\r
+    </target>\r
+\r
+    <target name="doc" description="generate documentation">\r
+       <javadoc destdir="${doc}"\r
+                author="true"\r
+                version="true"\r
+                use="true"\r
+                windowtitle="${project.name}"\r
+                sourcepath="${src}"\r
+                Protected="All" Private="All"\r
+                Public="All"\r
+                Locale="de"\r
+                linksource="yes"\r
+                breakiterator="Yes">\r
+       </javadoc>\r
+    </target>\r
+\r
+    <target name="clean" description="clean up">\r
+       <delete>\r
+          <fileset dir="${buildsrc}" />\r
+          <fileset dir="${classes}" />\r
+          <fileset dir="${buildlib}" />\r
+          <fileset dir="${doc}" />\r
+       </delete>\r
+    </target>\r
+    \r
+    <target name="redo" depends="init">\r
+        <!--\r
+       <touch>\r
+         <fileset dir="${src}" includes="*.g"/>\r
+       </touch>\r
+       -->\r
+    </target>\r
+    \r
+    <target name="all" depends="clean, redo, dist, doc" \r
+        description="do all"/>\r
+            \r
+</project>\r
diff --git a/src/langs/charj/src/charj/Main.java b/src/langs/charj/src/charj/Main.java
new file mode 100644 (file)
index 0000000..0d9279c
--- /dev/null
@@ -0,0 +1,12 @@
+package charj;
+
+import charj.translator.Translator;
+import java.io.FileInputStream;
+
+public class Main 
+{
+    public static void main(String[] args) throws Exception
+    {
+        System.out.println(Translator.translate(new FileInputStream(args[0])));
+    }
+}
diff --git a/src/langs/charj/src/charj/translator/Charj.g b/src/langs/charj/src/charj/translator/Charj.g
new file mode 100644 (file)
index 0000000..e097fb7
--- /dev/null
@@ -0,0 +1,1064 @@
+/**
+ * ANTLR (v3) grammar for the Charj Language
+ *
+ * The other .g files are tree parsers that can read and modify an AST 
+ * using the output of this grammar.
+ */
+
+
+grammar Charj;
+
+options {
+    backtrack = true; 
+    memoize = true;
+    output = AST;
+    ASTLabelType = CommonTree;
+}
+
+tokens {
+
+    // operators and other special chars
+    
+    AND                     = '&'               ;
+    AND_ASSIGN              = '&='              ;
+    ASSIGN                  = '='               ;
+    AT                      = '@'               ;
+    BIT_SHIFT_RIGHT         = '>>>'             ;
+    BIT_SHIFT_RIGHT_ASSIGN  = '>>>='            ;
+    COLON                   = ':'               ;
+    COMMA                   = ','               ;
+    DEC                     = '--'              ;
+    DIV                     = '/'               ;
+    DIV_ASSIGN              = '/='              ;
+    DOT                     = '.'               ;
+    DOTSTAR                 = '.*'              ;
+    ELLIPSIS                = '...'             ;
+    EQUAL                   = '=='              ;
+    GREATER_OR_EQUAL        = '>='              ;
+    GREATER_THAN            = '>'               ;
+    INC                     = '++'              ;
+    LBRACK                  = '['               ;
+    LCURLY                  = '{'               ;
+    LESS_OR_EQUAL           = '<='              ;
+    LESS_THAN               = '<'               ;
+    LOGICAL_AND             = '&&'              ;
+    LOGICAL_NOT             = '!'               ;
+    LOGICAL_OR              = '||'              ;
+    LPAREN                  = '('               ;
+    MINUS                   = '-'               ;
+    MINUS_ASSIGN            = '-='              ;
+    MOD                     = '%'               ;
+    MOD_ASSIGN              = '%='              ;
+    NOT                     = '~'               ;
+    NOT_EQUAL               = '!='              ;
+    OR                      = '|'               ;
+    OR_ASSIGN               = '|='              ;
+    PLUS                    = '+'               ;
+    PLUS_ASSIGN             = '+='              ;
+    QUESTION                = '?'               ;
+    RBRACK                  = ']'               ;
+    RCURLY                  = '}'               ;
+    RPAREN                  = ')'               ;
+    SEMI                    = ';'               ;
+    SHIFT_LEFT              = '<<'              ;
+    SHIFT_LEFT_ASSIGN       = '<<='             ;
+    SHIFT_RIGHT             = '>>'              ;
+    SHIFT_RIGHT_ASSIGN      = '>>='             ;
+    STAR                    = '*'               ;
+    STAR_ASSIGN             = '*='              ;
+    XOR                     = '^'               ;
+    XOR_ASSIGN              = '^='              ;
+
+    // keywords
+    
+    ABSTRACT                = 'abstract'        ;
+    ASSERT                  = 'assert'          ;
+    BOOLEAN                 = 'boolean'         ;
+    BREAK                   = 'break'           ;
+    BYTE                    = 'byte'            ;
+    CASE                    = 'case'            ;
+    CATCH                   = 'catch'           ;
+    CHAR                    = 'char'            ;
+    CLASS                   = 'class'           ;
+    CONTINUE                = 'continue'        ;
+    DEFAULT                 = 'default'         ;
+    DO                      = 'do'              ;
+    DOUBLE                  = 'double'          ;
+    ELSE                    = 'else'            ;
+    ENUM                    = 'enum'            ;
+    EXTENDS                 = 'extends'         ;
+    FALSE                   = 'false'           ;
+    FINAL                   = 'final'           ;
+    FINALLY                 = 'finally'         ;
+    FLOAT                   = 'float'           ;
+    FOR                     = 'for'             ;
+    IF                      = 'if'              ;
+    IMPLEMENTS              = 'implements'      ;
+    INSTANCEOF              = 'instanceof'      ;
+    INTERFACE               = 'interface'       ;
+    IMPORT                  = 'import'          ;
+    INT                     = 'int'             ;
+    LONG                    = 'long'            ;
+    NATIVE                  = 'native'          ;
+    NEW                     = 'new'             ;
+    NULL                    = 'null'            ;
+    PACKAGE                 = 'package'         ;
+    PRIVATE                 = 'private'         ;
+    PROTECTED               = 'protected'       ;
+    PUBLIC                  = 'public'          ;
+    RETURN                  = 'return'          ;
+    SHORT                   = 'short'           ;
+    STATIC                  = 'static'          ;
+    SUPER                   = 'super'           ;
+    SWITCH                  = 'switch'          ;
+    SYNCHRONIZED            = 'synchronized'    ;
+    THIS                    = 'this'            ;
+    THROW                   = 'throw'           ;
+    THROWS                  = 'throws'          ;
+    TRANSIENT               = 'transient'       ;
+    TRUE                    = 'true'            ;
+    TRY                     = 'try'             ;
+    VOID                    = 'void'            ;
+    VOLATILE                = 'volatile'        ;
+    WHILE                   = 'while'           ;
+    
+    // tokens for imaginary nodes
+    
+    ARGUMENT_LIST;
+    ARRAY_DECLARATOR;
+    ARRAY_DECLARATOR_LIST;
+    ARRAY_ELEMENT_ACCESS;
+    ARRAY_INITIALIZER;
+    BLOCK_SCOPE;
+    CAST_EXPR;
+    CATCH_CLAUSE_LIST;
+    CLASS_CONSTRUCTOR_CALL;
+    CLASS_INSTANCE_INITIALIZER;
+    CLASS_STATIC_INITIALIZER;
+    CLASS_TOP_LEVEL_SCOPE;
+    CONSTRUCTOR_DECL;
+    ENUM_TOP_LEVEL_SCOPE;
+    EXPR;
+    EXTENDS_BOUND_LIST;
+    EXTENDS_CLAUSE;
+    FOR_CONDITION;
+    FOR_EACH;
+    FOR_INIT;
+    FOR_UPDATE;
+    FORMAL_PARAM_LIST;
+    FORMAL_PARAM_STD_DECL;
+    FORMAL_PARAM_VARARG_DECL;
+    FUNCTION_METHOD_DECL;
+    GENERIC_TYPE_ARG_LIST;
+    GENERIC_TYPE_PARAM_LIST;
+    INTERFACE_TOP_LEVEL_SCOPE;
+    IMPLEMENTS_CLAUSE;
+    LABELED_STATEMENT;
+    LOCAL_MODIFIER_LIST;
+    CHARJ_SOURCE;
+    METHOD_CALL;
+    MODIFIER_LIST;
+    PARENTESIZED_EXPR;
+    POST_DEC;
+    POST_INC;
+    PRE_DEC;
+    PRE_INC;
+    QUALIFIED_TYPE_IDENT;
+    STATIC_ARRAY_CREATOR;
+    SUPER_CONSTRUCTOR_CALL;
+    SWITCH_BLOCK_LABEL_LIST;
+    THIS_CONSTRUCTOR_CALL;
+    THROWS_CLAUSE;
+    TYPE;
+    UNARY_MINUS;
+    UNARY_PLUS;
+    VAR_DECLARATION;
+    VAR_DECLARATOR;
+    VAR_DECLARATOR_LIST;
+    VOID_METHOD_DECL;
+}
+
+@header {
+package charj.translator;
+}
+
+@members {
+    
+    private boolean mMessageCollectionEnabled = false;
+    private boolean mHasErrors = false;
+    private List<String> mMessages;
+
+    /**
+     *  Switches error message collection on or of.
+     *
+     *  The standard destination for parser error messages is <code>System.err</code>.
+     *  However, if <code>true</code> gets passed to this method this default
+     *  behaviour will be switched off and all error messages will be collected
+     *  instead of written to anywhere.
+     *
+     *  The default value is <code>false</code>.
+     *
+     *  @param pNewState  <code>true</code> if error messages should be collected.
+     */
+    public void enableErrorMessageCollection(boolean pNewState) {
+        mMessageCollectionEnabled = pNewState;
+        if (mMessages == null && mMessageCollectionEnabled) {
+            mMessages = new ArrayList<String>();
+        }
+    }
+    
+    /**
+     *  Collects an error message or passes the error message to <code>
+     *  super.emitErrorMessage(...)</code>.
+     *
+     *  The actual behaviour depends on whether collecting error messages
+     *  has been enabled or not.
+     *
+     *  @param pMessage  The error message.
+     */
+     @Override
+    public void emitErrorMessage(String pMessage) {
+        if (mMessageCollectionEnabled) {
+            mMessages.add(pMessage);
+        } else {
+            super.emitErrorMessage(pMessage);
+        }
+    }
+    
+    /**
+     *  Returns collected error messages.
+     *
+     *  @return  A list holding collected error messages or <code>null</code> if
+     *           collecting error messages hasn't been enabled. Of course, this
+     *           list may be empty if no error message has been emited.
+     */
+    public List<String> getMessages() {
+        return mMessages;
+    }
+    
+    /**
+     *  Tells if parsing a Charj source has caused any error messages.
+     *
+     *  @return  <code>true</code> if parsing a Charj source has caused at least
+     *           one error message.
+     */
+    public boolean hasErrors() {
+        return mHasErrors;
+    }
+}
+
+@lexer::header {
+package charj.translator; 
+}
+
+@lexer::members {
+/** 
+ *  Determines if whitespaces and comments should be preserved or thrown away.
+ *
+ *  If <code>true</code> whitespaces and comments will be preserved within the
+ *  hidden channel, otherwise the appropriate tokens will be skiped. This is
+ *  a 'little bit' expensive.
+ */
+public boolean preserveWhitespacesAndComments = true;
+}
+
+// Starting point for parsing a Charj file.
+charjSource
+    :   compilationUnit
+        ->  ^(CHARJ_SOURCE compilationUnit)
+    ;
+
+compilationUnit
+    :   packageDeclaration? 
+        importDeclaration* 
+        typeDecls*
+    ;
+
+typeDecls
+    :   typeDeclaration
+    |   SEMI!
+    ;
+
+packageDeclaration
+    :   PACKAGE^ qualifiedIdentifier SEMI!  
+    ;
+    
+importDeclaration
+    :   IMPORT^ STATIC? qualifiedIdentifier DOTSTAR? SEMI!
+    ;
+    
+typeDeclaration
+    :   modifierList!
+        (   classTypeDeclaration[$modifierList.tree]
+        |   interfaceTypeDeclaration[$modifierList.tree]
+        |   enumTypeDeclaration[$modifierList.tree]
+        )
+    ;
+    
+classTypeDeclaration[CommonTree modifiers]
+    :   CLASS IDENT genericTypeParameterList? classExtendsClause? implementsClause? classBody
+        ->  ^(CLASS {$modifiers} IDENT genericTypeParameterList? classExtendsClause? implementsClause? classBody)
+    ;
+    
+classExtendsClause
+    :   EXTENDS type
+        ->  ^(EXTENDS_CLAUSE[$EXTENDS, "EXTENDS_CLAUSE"] type)
+    ;   
+    
+interfaceExtendsClause
+    :   EXTENDS typeList
+        ->  ^(EXTENDS_CLAUSE[$EXTENDS, "EXTENDS_CLAUSE"] typeList)
+    ;   
+    
+implementsClause
+    :   IMPLEMENTS typeList
+        ->  ^(IMPLEMENTS_CLAUSE[$IMPLEMENTS, "IMPLEMENTS_CLAUSE"] typeList)
+    ;
+        
+genericTypeParameterList
+    :   LESS_THAN genericTypeParameter (COMMA genericTypeParameter)* genericTypeListClosing
+        ->  ^(GENERIC_TYPE_PARAM_LIST[$LESS_THAN, "GENERIC_TYPE_PARAM_LIST"] genericTypeParameter+)
+    ;
+
+genericTypeListClosing  // This 'trick' is fairly dirty - if there's some time a better solution should 
+                        // be found to resolve the problem with nested generic type parameter lists 
+                        // (i.e. <T1 extends AnyType<T2>> for generic type parameters or <T1<T2>> for 
+                        // generic type arguments etc). 
+    :   GREATER_THAN
+    |   SHIFT_RIGHT
+    |   BIT_SHIFT_RIGHT
+    |   // nothing
+    ;
+
+genericTypeParameter
+    :   IDENT bound?
+        ->  ^(IDENT bound?)
+    ;
+        
+bound
+    :   EXTENDS type (AND type)*
+        ->  ^(EXTENDS_BOUND_LIST[$EXTENDS, "EXTENDS_BOUND_LIST"] type+)
+    ;
+
+enumTypeDeclaration[CommonTree modifiers]
+    :   ENUM IDENT implementsClause? enumBody
+        ->  ^(ENUM {$modifiers} IDENT implementsClause? enumBody)
+    ;
+    
+enumBody
+    :   LCURLY enumScopeDeclarations RCURLY
+        ->  ^(ENUM_TOP_LEVEL_SCOPE[$LCURLY, "ENUM_TOP_LEVEL_SCOPE"] enumScopeDeclarations)
+    ;
+
+enumScopeDeclarations
+    :   enumConstants (COMMA!)? enumClassScopeDeclarations?
+    ;
+
+enumClassScopeDeclarations
+    :   SEMI classScopeDeclarations*
+        ->  ^(CLASS_TOP_LEVEL_SCOPE[$SEMI, "CLASS_TOP_LEVEL_SCOPE"] classScopeDeclarations*)
+    ;
+
+enumConstants
+    :   enumConstant (COMMA! enumConstant)*
+    ;
+    
+enumConstant
+    :   IDENT^ arguments? classBody?
+    ;
+    
+interfaceTypeDeclaration[CommonTree modifiers]
+    :   INTERFACE IDENT genericTypeParameterList? interfaceExtendsClause? interfaceBody
+        ->  ^(INTERFACE {$modifiers} IDENT genericTypeParameterList? interfaceExtendsClause? interfaceBody)
+    ;
+    
+typeList
+    :   type (COMMA! type)*
+    ;
+    
+classBody
+    :   LCURLY classScopeDeclarations* RCURLY
+        ->  ^(CLASS_TOP_LEVEL_SCOPE[$LCURLY, "CLASS_TOP_LEVEL_SCOPE"] classScopeDeclarations*)
+    ;
+    
+interfaceBody
+    :   LCURLY interfaceScopeDeclarations* RCURLY
+        ->  ^(INTERFACE_TOP_LEVEL_SCOPE[$LCURLY, "CLASS_TOP_LEVEL_SCOPE"] interfaceScopeDeclarations*)
+    ;
+
+classScopeDeclarations
+    :   block           ->  ^(CLASS_INSTANCE_INITIALIZER block)
+    |   STATIC block    ->  ^(CLASS_STATIC_INITIALIZER[$STATIC, "CLASS_STATIC_INITIALIZER"] block)
+    |   modifierList
+        (   genericTypeParameterList?
+            (   type IDENT formalParameterList arrayDeclaratorList? throwsClause? (block | SEMI)
+                ->  ^(FUNCTION_METHOD_DECL modifierList genericTypeParameterList? type IDENT formalParameterList arrayDeclaratorList? throwsClause? block?)
+            |   VOID IDENT formalParameterList throwsClause? (block | SEMI)
+                ->  ^(VOID_METHOD_DECL modifierList genericTypeParameterList? IDENT formalParameterList throwsClause? block?)
+            |   ident=IDENT formalParameterList throwsClause? block
+                ->  ^(CONSTRUCTOR_DECL[$ident, "CONSTRUCTOR_DECL"] modifierList genericTypeParameterList? formalParameterList throwsClause? block)
+            )
+        |   type classFieldDeclaratorList SEMI
+            ->  ^(VAR_DECLARATION modifierList type classFieldDeclaratorList)
+        )
+    |   typeDeclaration
+    |   SEMI!
+    ;
+            
+interfaceScopeDeclarations
+    :   modifierList
+        (   genericTypeParameterList?
+            (   type IDENT formalParameterList arrayDeclaratorList? throwsClause? SEMI
+                ->  ^(FUNCTION_METHOD_DECL modifierList genericTypeParameterList? type IDENT formalParameterList arrayDeclaratorList? throwsClause?)
+            |   VOID IDENT formalParameterList throwsClause? SEMI
+                ->  ^(VOID_METHOD_DECL modifierList genericTypeParameterList? IDENT formalParameterList throwsClause?)
+            )
+        |   type interfaceFieldDeclaratorList SEMI
+            ->  ^(VAR_DECLARATION modifierList type interfaceFieldDeclaratorList)
+        )
+    |   typeDeclaration
+    |   SEMI!
+    ;
+
+classFieldDeclaratorList
+    :   classFieldDeclarator (COMMA classFieldDeclarator)*
+        ->  ^(VAR_DECLARATOR_LIST classFieldDeclarator+)
+    ;
+
+classFieldDeclarator
+    :   variableDeclaratorId (ASSIGN variableInitializer)?
+        ->  ^(VAR_DECLARATOR variableDeclaratorId variableInitializer?)
+    ;
+    
+interfaceFieldDeclaratorList
+    :   interfaceFieldDeclarator (COMMA interfaceFieldDeclarator)*
+        ->  ^(VAR_DECLARATOR_LIST interfaceFieldDeclarator+)
+    ;
+
+interfaceFieldDeclarator
+    :   variableDeclaratorId ASSIGN variableInitializer
+        ->  ^(VAR_DECLARATOR variableDeclaratorId variableInitializer)
+    ;
+    
+variableDeclaratorId
+    :   IDENT^ arrayDeclaratorList?
+    ;
+
+variableInitializer
+    :   arrayInitializer
+    |   expression
+    ;
+
+arrayDeclarator
+    :   LBRACK RBRACK
+        ->  ^(ARRAY_DECLARATOR)
+    ;
+
+arrayDeclaratorList
+    :   arrayDeclarator+
+        ->  ^(ARRAY_DECLARATOR_LIST arrayDeclarator+)   
+    ;
+    
+arrayInitializer
+    :   LCURLY (variableInitializer (COMMA variableInitializer)* COMMA?)? RCURLY
+        ->  ^(ARRAY_INITIALIZER[$LCURLY, "ARRAY_INITIALIZER"] variableInitializer*)
+    ;
+
+throwsClause
+    :   THROWS qualifiedIdentList
+        ->  ^(THROWS_CLAUSE[$THROWS, "THROWS_CLAUSE"] qualifiedIdentList)
+    ;
+
+modifierList
+    :   modifier*   
+        ->  ^(MODIFIER_LIST modifier*)
+    ;
+
+modifier
+    :   PUBLIC
+    |   PROTECTED
+    |   PRIVATE
+    |   STATIC
+    |   ABSTRACT
+    |   NATIVE
+    |   SYNCHRONIZED
+    |   TRANSIENT
+    |   VOLATILE
+    |   localModifier
+    ;
+
+localModifierList
+    :   localModifier*
+        -> ^(LOCAL_MODIFIER_LIST localModifier*)
+    ;
+    
+localModifier
+    :   FINAL
+    ;
+
+type
+    :   simpleType
+    |   objectType
+    ;
+
+simpleType // including static arrays of simple type elements
+    :   primitiveType arrayDeclaratorList?
+        ->  ^(TYPE primitiveType arrayDeclaratorList?)  
+    ;
+    
+objectType // including static arrays of object type reference elements
+    :   qualifiedTypeIdent arrayDeclaratorList?
+        ->  ^(TYPE qualifiedTypeIdent arrayDeclaratorList?)
+    ;
+
+objectTypeSimplified
+    :   qualifiedTypeIdentSimplified arrayDeclaratorList?
+        ->  ^(TYPE qualifiedTypeIdentSimplified arrayDeclaratorList?)
+    ;
+
+qualifiedTypeIdent
+    :   typeIdent (DOT typeIdent)*
+        ->  ^(QUALIFIED_TYPE_IDENT typeIdent+) 
+    ;
+
+qualifiedTypeIdentSimplified
+    :   typeIdentSimplified (DOT typeIdentSimplified)*
+        ->  ^(QUALIFIED_TYPE_IDENT typeIdentSimplified+) 
+    ;
+
+typeIdent
+    :   IDENT^ genericTypeArgumentList?
+    ;
+
+typeIdentSimplified
+    :   IDENT^ genericTypeArgumentListSimplified?
+    ;
+
+primitiveType
+    :   BOOLEAN
+    |   CHAR
+    |   BYTE
+    |   SHORT
+    |   INT
+    |   LONG
+    |   FLOAT
+    |   DOUBLE
+    ;
+
+genericTypeArgumentList
+    :   LESS_THAN genericTypeArgument (COMMA genericTypeArgument)* genericTypeListClosing
+        ->  ^(GENERIC_TYPE_ARG_LIST[$LESS_THAN, "GENERIC_TYPE_ARG_LIST"] genericTypeArgument+)
+    ;
+
+genericTypeArgument
+    :   type
+    |   QUESTION genericWildcardBoundType?
+        ->  ^(QUESTION genericWildcardBoundType?)
+    ;
+    
+genericWildcardBoundType
+    :   (EXTENDS | SUPER)^ type
+    ;
+
+genericTypeArgumentListSimplified
+    :   LESS_THAN genericTypeArgumentSimplified (COMMA genericTypeArgumentSimplified)* genericTypeListClosing
+        ->  ^(GENERIC_TYPE_ARG_LIST[$LESS_THAN, "GENERIC_TYPE_ARG_LIST"] genericTypeArgumentSimplified+)
+    ;
+    
+genericTypeArgumentSimplified
+    :   type
+    |   QUESTION
+    ;
+    
+qualifiedIdentList
+    :   qualifiedIdentifier (COMMA! qualifiedIdentifier)*
+    ;
+    
+formalParameterList
+    :   LPAREN 
+        (   // Contains at least one standard argument declaration and optionally a variable argument declaration.
+            formalParameterStandardDecl (COMMA formalParameterStandardDecl)* (COMMA formalParameterVarArgDecl)? 
+            ->  ^(FORMAL_PARAM_LIST[$LPAREN, "FORMAL_PARAM_LIST"] formalParameterStandardDecl+ formalParameterVarArgDecl?) 
+            // Contains a variable argument declaration only.
+        |   formalParameterVarArgDecl
+            ->  ^(FORMAL_PARAM_LIST[$LPAREN, "FORMAL_PARAM_LIST"] formalParameterVarArgDecl) 
+            // Contains nothing.
+        |   ->  ^(FORMAL_PARAM_LIST[$LPAREN, "FORMAL_PARAM_LIST"]) 
+        )
+        RPAREN
+    ;
+    
+formalParameterStandardDecl
+    :   localModifierList type variableDeclaratorId
+        ->  ^(FORMAL_PARAM_STD_DECL localModifierList type variableDeclaratorId)
+    ;
+    
+formalParameterVarArgDecl
+    :   localModifierList type ELLIPSIS variableDeclaratorId
+        ->  ^(FORMAL_PARAM_VARARG_DECL localModifierList type variableDeclaratorId)
+    ;
+    
+qualifiedIdentifier
+    :   (   IDENT               ->  IDENT
+        )
+        (   DOT ident=IDENT     ->  ^(DOT $qualifiedIdentifier $ident)
+        )*
+    ;
+    
+block
+    :   LCURLY blockStatement* RCURLY
+        ->  ^(BLOCK_SCOPE[$LCURLY, "BLOCK_SCOPE"] blockStatement*)
+    ;
+
+blockStatement
+    :   localVariableDeclaration SEMI!
+    |   typeDeclaration
+    |   statement
+    ;
+    
+localVariableDeclaration
+    :   localModifierList type classFieldDeclaratorList
+        ->  ^(VAR_DECLARATION localModifierList type classFieldDeclaratorList)
+    ;
+    
+        
+statement
+    :   block
+    |   ASSERT expr1=expression 
+        (   COLON expr2=expression SEMI                                     ->  ^(ASSERT $expr1 $expr2)
+        |   SEMI                                                            ->  ^(ASSERT $expr1)
+        )
+    |   IF parenthesizedExpression ifStat=statement 
+        (   ELSE elseStat=statement                                         ->  ^(IF parenthesizedExpression $ifStat $elseStat)
+        |                                                                   ->  ^(IF parenthesizedExpression $ifStat)
+        )   
+    |   FOR LPAREN 
+        (   forInit SEMI forCondition SEMI forUpdater RPAREN statement      ->  ^(FOR forInit forCondition forUpdater statement) 
+        |   localModifierList type IDENT COLON expression RPAREN statement
+                                                                            ->  ^(FOR_EACH[$FOR, "FOR_EACH"] localModifierList type IDENT expression statement)
+        ) 
+    |   WHILE parenthesizedExpression statement                             ->  ^(WHILE parenthesizedExpression statement)
+    |   DO statement WHILE parenthesizedExpression SEMI                     ->  ^(DO statement parenthesizedExpression)
+    |   TRY block (catches finallyClause? | finallyClause)                  ->  ^(TRY block catches? finallyClause?)
+    |   SWITCH parenthesizedExpression LCURLY switchBlockLabels RCURLY      ->  ^(SWITCH parenthesizedExpression switchBlockLabels)
+    |   SYNCHRONIZED parenthesizedExpression block                          ->  ^(SYNCHRONIZED parenthesizedExpression block)
+    |   RETURN expression? SEMI                                             ->  ^(RETURN expression?)
+    |   THROW expression SEMI                                               ->  ^(THROW expression)
+    |   BREAK IDENT? SEMI                                                   ->  ^(BREAK IDENT?)
+    |   CONTINUE IDENT? SEMI                                                ->  ^(CONTINUE IDENT?)
+    |   IDENT COLON statement                                               ->  ^(LABELED_STATEMENT IDENT statement)
+    |   expression SEMI!
+    |   SEMI // Preserve empty statements.
+    ;           
+        
+catches
+    :   catchClause+
+        ->  ^(CATCH_CLAUSE_LIST catchClause+)
+    ;
+    
+catchClause
+    :   CATCH^ LPAREN! formalParameterStandardDecl RPAREN! block
+    ;
+
+finallyClause
+    :   FINALLY block
+        ->  block
+    ;
+
+switchBlockLabels
+    :   switchCaseLabels switchDefaultLabel? switchCaseLabels
+        ->  ^(SWITCH_BLOCK_LABEL_LIST switchCaseLabels switchDefaultLabel? switchCaseLabels)
+    ;
+    
+switchCaseLabels
+    :   switchCaseLabel*
+    ;
+        
+switchCaseLabel
+    :   CASE^ expression COLON! blockStatement*
+    ;
+    
+switchDefaultLabel
+    :   DEFAULT^ COLON! blockStatement*
+    ;
+    
+forInit
+    :   localVariableDeclaration    ->  ^(FOR_INIT localVariableDeclaration)
+    |   expressionList              ->  ^(FOR_INIT expressionList)
+    |                               ->  ^(FOR_INIT)
+    ;
+    
+forCondition
+    :   expression?
+        ->  ^(FOR_CONDITION expression?)
+    ;
+    
+forUpdater
+    :   expressionList?
+        ->  ^(FOR_UPDATE expressionList?)
+    ;
+
+// EXPRESSIONS
+
+parenthesizedExpression
+    :   LPAREN expression RPAREN
+        ->  ^(PARENTESIZED_EXPR[$LPAREN, "PARENTESIZED_EXPR"] expression)
+    ;
+    
+expressionList
+    :   expression (COMMA! expression)*
+    ;
+
+expression
+    :   assignmentExpression
+        ->  ^(EXPR assignmentExpression)
+    ;
+
+assignmentExpression
+    :   conditionalExpression 
+        (   (   ASSIGN^
+            |   PLUS_ASSIGN^
+            |   MINUS_ASSIGN^
+            |   STAR_ASSIGN^
+            |   DIV_ASSIGN^
+            |   AND_ASSIGN^
+            |   OR_ASSIGN^
+            |   XOR_ASSIGN^
+            |   MOD_ASSIGN^
+            |   SHIFT_LEFT_ASSIGN^
+            |   SHIFT_RIGHT_ASSIGN^
+            |   BIT_SHIFT_RIGHT_ASSIGN^
+        ) 
+        assignmentExpression)?
+    ;
+    
+conditionalExpression
+    :   logicalOrExpression (QUESTION^ assignmentExpression COLON! conditionalExpression)?
+    ;
+
+logicalOrExpression
+    :   logicalAndExpression (LOGICAL_OR^ logicalAndExpression)*
+    ;
+
+logicalAndExpression
+    :   inclusiveOrExpression (LOGICAL_AND^ inclusiveOrExpression)*
+    ;
+
+inclusiveOrExpression
+    :   exclusiveOrExpression (OR^ exclusiveOrExpression)*
+    ;
+
+exclusiveOrExpression
+    :   andExpression (XOR^ andExpression)*
+    ;
+
+andExpression
+    :   equalityExpression (AND^ equalityExpression)*
+    ;
+
+equalityExpression
+    :   instanceOfExpression 
+        (   (   EQUAL^
+            |   NOT_EQUAL^
+            ) 
+            instanceOfExpression
+        )*
+    ;
+
+instanceOfExpression
+    :   relationalExpression (INSTANCEOF^ type)?
+    ;
+
+relationalExpression
+    :   shiftExpression 
+        (   (   LESS_OR_EQUAL^
+            |   GREATER_OR_EQUAL^
+            |   LESS_THAN^
+            |   GREATER_THAN^
+            )
+            shiftExpression
+        )*
+    ;
+    
+shiftExpression
+    :   additiveExpression
+        (   (   BIT_SHIFT_RIGHT^
+            |   SHIFT_RIGHT^
+            |   SHIFT_LEFT^
+            )
+            additiveExpression
+        )*
+    ;
+
+additiveExpression
+    :   multiplicativeExpression
+        (   (   PLUS^
+            |   MINUS^
+            )
+            multiplicativeExpression
+        )*
+    ;
+
+multiplicativeExpression
+    :   unaryExpression 
+        (   (   STAR^
+            |   DIV^
+            |   MOD^
+            )
+            unaryExpression
+        )*
+    ;
+    
+unaryExpression
+    :   PLUS unaryExpression        ->  ^(UNARY_PLUS[$PLUS, "UNARY_PLUS"] unaryExpression)
+    |   MINUS unaryExpression       ->  ^(UNARY_MINUS[$MINUS, "UNARY_MINUS"] unaryExpression)
+    |   INC postfixedExpression     ->  ^(PRE_INC[$INC, "PRE_INC"] postfixedExpression)
+    |   DEC postfixedExpression     ->  ^(PRE_DEC[$DEC, "PRE_DEC"] postfixedExpression)
+    |   unaryExpressionNotPlusMinus
+    ;
+
+unaryExpressionNotPlusMinus
+    :   NOT unaryExpression                             ->  ^(NOT unaryExpression)
+    |   LOGICAL_NOT unaryExpression                     ->  ^(LOGICAL_NOT unaryExpression)
+    |   LPAREN type RPAREN unaryExpression              ->  ^(CAST_EXPR[$LPAREN, "CAST_EXPR"] type unaryExpression)
+    |   postfixedExpression
+    ;
+    
+postfixedExpression
+        // At first resolve the primary expression ...
+    :   (   primaryExpression                       ->  primaryExpression
+        )
+        // ... and than the optional things that may follow a primary expression 0 or more times.
+        (   outerDot=DOT                            
+            (   (   genericTypeArgumentListSimplified?  // Note: generic type arguments are only valid for method calls, i.e. if there
+                                                        //       is an argument list.
+                    IDENT                           ->  ^(DOT $postfixedExpression IDENT)
+                ) 
+                (   arguments                       ->  ^(METHOD_CALL $postfixedExpression genericTypeArgumentListSimplified? arguments)
+                )?
+            |   THIS                                ->  ^(DOT $postfixedExpression THIS)
+            |   Super=SUPER arguments                   ->  ^(SUPER_CONSTRUCTOR_CALL[$Super, "SUPER_CONSTRUCTOR_CALL"] $postfixedExpression arguments)
+            |   (   SUPER innerDot=DOT IDENT        ->  ^($innerDot ^($outerDot $postfixedExpression SUPER) IDENT)
+                )
+                (   arguments                       ->  ^(METHOD_CALL $postfixedExpression arguments)
+                )?
+            |   innerNewExpression                  ->  ^(DOT $postfixedExpression innerNewExpression)
+            )
+        |   LBRACK expression RBRACK                ->  ^(ARRAY_ELEMENT_ACCESS $postfixedExpression expression)
+        )*
+        // At the end there may follow a post increment/decrement.
+        (   INC -> ^(POST_INC[$INC, "POST_INC"] $postfixedExpression)
+        |   DEC -> ^(POST_DEC[$DEC, "POST_DEC"] $postfixedExpression)
+        )?
+    ;    
+    
+primaryExpression
+    :   parenthesizedExpression
+    |   literal
+    |   newExpression
+    |   qualifiedIdentExpression
+    |   genericTypeArgumentListSimplified 
+        (   SUPER
+            (   arguments                               ->  ^(SUPER_CONSTRUCTOR_CALL[$SUPER, "SUPER_CONSTRUCTOR_CALL"] genericTypeArgumentListSimplified arguments)
+            |   DOT IDENT arguments                     ->  ^(METHOD_CALL ^(DOT SUPER IDENT) genericTypeArgumentListSimplified arguments)
+            )
+        |   IDENT arguments                             ->  ^(METHOD_CALL IDENT genericTypeArgumentListSimplified arguments)
+        |   THIS arguments                              ->  ^(THIS_CONSTRUCTOR_CALL[$THIS, "THIS_CONSTRUCTOR_CALL"] genericTypeArgumentListSimplified arguments)
+        )
+    |   (   THIS                                        ->  THIS
+        )
+        (   arguments                                   ->  ^(THIS_CONSTRUCTOR_CALL[$THIS, "THIS_CONSTRUCTOR_CALL"] arguments)
+        )?
+    |   SUPER arguments                                 ->  ^(SUPER_CONSTRUCTOR_CALL[$SUPER, "SUPER_CONSTRUCTOR_CALL"] arguments)
+    |   (   SUPER DOT IDENT
+        )
+        (   arguments                                   ->  ^(METHOD_CALL ^(DOT SUPER IDENT) arguments)
+        |                                               ->  ^(DOT SUPER IDENT)
+        )
+    |   (   primitiveType                               ->  primitiveType
+        )
+        (   arrayDeclarator                             ->  ^(arrayDeclarator $primaryExpression)   
+        )* 
+        DOT CLASS                                       ->  ^(DOT $primaryExpression CLASS)
+    |   VOID DOT CLASS                                  ->  ^(DOT VOID CLASS)
+    ;
+    
+qualifiedIdentExpression
+        // The qualified identifier itself is the starting point for this rule.
+    :   (   qualifiedIdentifier                             ->  qualifiedIdentifier
+        )
+        // And now comes the stuff that may follow the qualified identifier.
+        (   (   arrayDeclarator                         ->  ^(arrayDeclarator $qualifiedIdentExpression)
+            )+ 
+            (   DOT CLASS                               ->  ^(DOT $qualifiedIdentExpression CLASS)
+            )
+        |   arguments                                   ->  ^(METHOD_CALL qualifiedIdentifier arguments)
+        |   outerDot=DOT
+            (   CLASS                                   ->  ^(DOT qualifiedIdentifier CLASS)
+            |   genericTypeArgumentListSimplified 
+                (   Super=SUPER arguments               ->  ^(SUPER_CONSTRUCTOR_CALL[$Super, "SUPER_CONSTRUCTOR_CALL"] qualifiedIdentifier genericTypeArgumentListSimplified arguments)
+                |   SUPER innerDot=DOT IDENT arguments  ->  ^(METHOD_CALL ^($innerDot ^($outerDot qualifiedIdentifier SUPER) IDENT) genericTypeArgumentListSimplified arguments)
+                |   IDENT arguments                     ->  ^(METHOD_CALL ^(DOT qualifiedIdentifier IDENT) genericTypeArgumentListSimplified arguments)
+                )
+            |   THIS                                    ->  ^(DOT qualifiedIdentifier THIS)
+            |   Super=SUPER arguments                   ->  ^(SUPER_CONSTRUCTOR_CALL[$Super, "SUPER_CONSTRUCTOR_CALL"] qualifiedIdentifier arguments)
+            |   innerNewExpression                      ->  ^(DOT qualifiedIdentifier innerNewExpression)
+            )
+        )?
+    ;
+
+newExpression
+    :   NEW  
+        (   primitiveType newArrayConstruction      // new static array of primitive type elements
+            ->  ^(STATIC_ARRAY_CREATOR[$NEW, "STATIC_ARRAY_CREATOR"] primitiveType newArrayConstruction)
+        |   genericTypeArgumentListSimplified? qualifiedTypeIdentSimplified
+            (   newArrayConstruction                // new static array of object type reference elements
+                ->  ^(STATIC_ARRAY_CREATOR[$NEW, "STATIC_ARRAY_CREATOR"] genericTypeArgumentListSimplified? qualifiedTypeIdentSimplified newArrayConstruction)
+            |   arguments classBody?                // new object type via constructor invocation
+                ->  ^(CLASS_CONSTRUCTOR_CALL[$NEW, "STATIC_ARRAY_CREATOR"] genericTypeArgumentListSimplified? qualifiedTypeIdentSimplified arguments classBody?)
+            )
+        )
+    ;
+    
+innerNewExpression // something like 'InnerType innerType = outer.new InnerType();'
+    :   NEW genericTypeArgumentListSimplified? IDENT arguments classBody?
+        ->  ^(CLASS_CONSTRUCTOR_CALL[$NEW, "STATIC_ARRAY_CREATOR"] genericTypeArgumentListSimplified? IDENT arguments classBody?)
+    ;
+
+newArrayConstruction
+    :   arrayDeclaratorList arrayInitializer
+    |   LBRACK! expression RBRACK! (LBRACK! expression RBRACK!)* arrayDeclaratorList?
+    ;
+
+arguments
+    :   LPAREN expressionList? RPAREN
+        ->  ^(ARGUMENT_LIST[$LPAREN, "ARGUMENT_LIST"] expressionList?)
+    ;
+
+literal 
+    :   HEX_LITERAL
+    |   OCTAL_LITERAL
+    |   DECIMAL_LITERAL
+    |   FLOATING_POINT_LITERAL
+    |   CHARACTER_LITERAL
+    |   STRING_LITERAL
+    |   TRUE
+    |   FALSE
+    |   NULL
+    ;
+
+// LEXER
+
+HEX_LITERAL : '0' ('x'|'X') HEX_DIGIT+ INTEGER_TYPE_SUFFIX? ;
+
+DECIMAL_LITERAL : ('0' | '1'..'9' '0'..'9'*) INTEGER_TYPE_SUFFIX? ;
+
+OCTAL_LITERAL : '0' ('0'..'7')+ INTEGER_TYPE_SUFFIX? ;
+
+fragment
+HEX_DIGIT : ('0'..'9'|'a'..'f'|'A'..'F') ;
+
+fragment
+INTEGER_TYPE_SUFFIX : ('l'|'L') ;
+
+FLOATING_POINT_LITERAL
+    :   ('0'..'9')+ 
+        (
+            DOT ('0'..'9')* EXPONENT? FLOAT_TYPE_SUFFIX?
+        |   EXPONENT FLOAT_TYPE_SUFFIX?
+        |   FLOAT_TYPE_SUFFIX
+        )
+    |   DOT ('0'..'9')+ EXPONENT? FLOAT_TYPE_SUFFIX?
+    ;
+
+fragment
+EXPONENT : ('e'|'E') ('+'|'-')? ('0'..'9')+ ;
+
+fragment
+FLOAT_TYPE_SUFFIX : ('f'|'F'|'d'|'D') ;
+
+CHARACTER_LITERAL
+    :   '\'' ( ESCAPE_SEQUENCE | ~('\''|'\\') ) '\''
+    ;
+
+STRING_LITERAL
+    :  '"' ( ESCAPE_SEQUENCE | ~('\\'|'"') )* '"'
+    ;
+
+fragment
+ESCAPE_SEQUENCE
+    :   '\\' ('b'|'t'|'n'|'f'|'r'|'\"'|'\''|'\\')
+    |   UNICODE_ESCAPE
+    |   OCTAL_ESCAPE
+    ;
+
+fragment
+OCTAL_ESCAPE
+    :   '\\' ('0'..'3') ('0'..'7') ('0'..'7')
+    |   '\\' ('0'..'7') ('0'..'7')
+    |   '\\' ('0'..'7')
+    ;
+
+fragment
+UNICODE_ESCAPE
+    :   '\\' 'u' HEX_DIGIT HEX_DIGIT HEX_DIGIT HEX_DIGIT
+    ;
+
+IDENT
+    :   CHARJ_ID_START (CHARJ_ID_PART)*
+    ;
+
+fragment
+CHARJ_ID_START
+    :  '\u0024'
+    |  '\u0041'..'\u005a'
+    |  '\u005f'
+    |  '\u0061'..'\u007a'
+    |  '\u00c0'..'\u00d6'
+    |  '\u00d8'..'\u00f6'
+    |  '\u00f8'..'\u00ff'
+    |  '\u0100'..'\u1fff'
+    |  '\u3040'..'\u318f'
+    |  '\u3300'..'\u337f'
+    |  '\u3400'..'\u3d2d'
+    |  '\u4e00'..'\u9fff'
+    |  '\uf900'..'\ufaff'
+    ;
+
+fragment
+CHARJ_ID_PART
+    :  CHARJ_ID_START
+    |  '\u0030'..'\u0039'
+    ;
+
+WS  :  (' '|'\r'|'\t'|'\u000C'|'\n') 
+    {   
+        if (!preserveWhitespacesAndComments) {
+            skip();
+        } else {
+            $channel = HIDDEN;
+        }
+    }
+    ;
+
+COMMENT
+    :   '/*' ( options {greedy=false;} : . )* '*/'
+    {   
+        if (!preserveWhitespacesAndComments) {
+            skip();
+        } else {
+            $channel = HIDDEN;
+        }
+    }
+    ;
+
+LINE_COMMENT
+    : '//' ~('\n'|'\r')* '\r'? '\n'
+    {   
+        if (!preserveWhitespacesAndComments) {
+            skip();
+        } else {
+            $channel = HIDDEN;
+        }
+    }
+    ;
diff --git a/src/langs/charj/src/charj/translator/Charj.stg b/src/langs/charj/src/charj/translator/Charj.stg
new file mode 100644 (file)
index 0000000..9a420f5
--- /dev/null
@@ -0,0 +1,10 @@
+group Charj;
+
+classExtends(type) ::= ": public CBase_<type>"
+
+
+interfaceExtends(ts) ::=
+<<
+: public CBase_<ts; separator=", public CBase_">
+>>
+
diff --git a/src/langs/charj/src/charj/translator/CharjEmitter.g b/src/langs/charj/src/charj/translator/CharjEmitter.g
new file mode 100644 (file)
index 0000000..6f2d70b
--- /dev/null
@@ -0,0 +1,471 @@
+/**
+ * ANTLR (v3) Tree Parser for the Charj Language
+ */
+
+tree grammar CharjEmitter;
+
+options {
+    backtrack = true; 
+    memoize = true;
+    tokenVocab = Charj;
+    ASTLabelType = CommonTree;
+    output = template;
+    rewrite = true;
+}
+
+
+@treeparser::header {
+package charj.translator;
+}
+
+@treeparser::members {
+    
+    boolean mMessageCollectionEnabled = false;
+    private boolean mHasErrors = false;
+    List<String> mMessages;
+
+    /**
+     *  Switches error message collection on or off.
+     *
+     *  The standard destination for parser error messages is <code>System.err</code>.
+     *  However, if <code>true</code> gets passed to this method this default
+     *  behaviour will be switched off and all error messages will be collected
+     *  instead of written to anywhere.
+     *
+     *  The default value is <code>false</code>.
+     *
+     *  @param pNewState  <code>true</code> if error messages should be collected.
+     */
+    public void enableErrorMessageCollection(boolean pNewState) {
+        mMessageCollectionEnabled = pNewState;
+        if (mMessages == null && mMessageCollectionEnabled) {
+            mMessages = new ArrayList<String>();
+        }
+    }
+    
+    /**
+     *  Collects an error message or passes the error message to <code>
+     *  super.emitErrorMessage(...)</code>.
+     *
+     *  The actual behaviour depends on whether collecting error messages
+     *  has been enabled or not.
+     *
+     *  @param pMessage  The error message.
+     */
+     @Override
+    public void emitErrorMessage(String pMessage) {
+        if (mMessageCollectionEnabled) {
+            mMessages.add(pMessage);
+        } else {
+            super.emitErrorMessage(pMessage);
+        }
+    }
+    
+    /**
+     *  Returns collected error messages.
+     *
+     *  @return  A list holding collected error messages or <code>null</code> if
+     *           collecting error messages hasn't been enabled. Of course, this
+     *           list may be empty if no error message has been emited.
+     */
+    public List<String> getMessages() {
+        return mMessages;
+    }
+    
+    /**
+     *  Tells if parsing a Charj source has caused any error messages.
+     *
+     *  @return  <code>true</code> if parsing a Charj source has caused at 
+     *           least one error message.
+     */
+    public boolean hasErrors() {
+        return mHasErrors;
+    }
+}
+
+// Starting point for parsing a Charj file.
+charjSource
+    :   ^(CHARJ_SOURCE packageDeclaration? importDeclaration* (ts+=typeDeclaration)*)
+        -> template(allText={$text}, types={$ts}) <<
+        ::: <allText> ::: <types> :::
+        >>
+    ;
+
+packageDeclaration
+    :   ^(PACKAGE qualifiedIdentifier)  
+    ;
+    
+importDeclaration
+    :   ^(IMPORT STATIC? qualifiedIdentifier DOTSTAR?)
+    ;
+    
+typeDeclaration
+    :   ^(CLASS modifierList IDENT genericTypeParameterList? classExtendsClause? implementsClause? classTopLevelScope) -> template(t={$text}) "<t>"
+    |   ^(INTERFACE modifierList IDENT genericTypeParameterList? interfaceExtendsClause? interfaceTopLevelScope)
+    |   ^(ENUM modifierList IDENT implementsClause? enumTopLevelScope)
+    ;
+
+
+classExtendsClause
+    :   ^(EXTENDS_CLAUSE t=type) -> classExtends(type={$t.st})
+    ;   
+
+interfaceExtendsClause 
+    :   ^(EXTENDS_CLAUSE (typeList+=type)+) -> interfaceExtends(ts={$typeList})
+    ;   
+    
+implementsClause
+    :   ^(IMPLEMENTS_CLAUSE type+)
+    ;
+        
+genericTypeParameterList
+    :   ^(GENERIC_TYPE_PARAM_LIST genericTypeParameter+)
+    ;
+
+genericTypeParameter
+    :   ^(IDENT bound?)
+    ;
+        
+bound
+    :   ^(EXTENDS_BOUND_LIST type+)
+    ;
+
+enumTopLevelScope
+    :   ^(ENUM_TOP_LEVEL_SCOPE enumConstant+ classTopLevelScope?)
+    ;
+    
+enumConstant
+    :   ^(IDENT arguments? classTopLevelScope?)
+    ;
+    
+    
+classTopLevelScope
+    :   ^(CLASS_TOP_LEVEL_SCOPE classScopeDeclarations*)
+    ;
+    
+classScopeDeclarations
+    :   ^(CLASS_INSTANCE_INITIALIZER block)
+    |   ^(CLASS_STATIC_INITIALIZER block)
+    |   ^(FUNCTION_METHOD_DECL modifierList genericTypeParameterList? type IDENT formalParameterList arrayDeclaratorList? throwsClause? block?)
+    |   ^(VOID_METHOD_DECL modifierList genericTypeParameterList? IDENT formalParameterList throwsClause? block?)
+    |   ^(VAR_DECLARATION modifierList type variableDeclaratorList)
+    |   ^(CONSTRUCTOR_DECL modifierList genericTypeParameterList? formalParameterList throwsClause? block)
+    |   typeDeclaration
+    ;
+    
+interfaceTopLevelScope
+    :   ^(INTERFACE_TOP_LEVEL_SCOPE interfaceScopeDeclarations*)
+    ;
+    
+interfaceScopeDeclarations
+    :   ^(FUNCTION_METHOD_DECL modifierList genericTypeParameterList? type IDENT formalParameterList arrayDeclaratorList? throwsClause?)
+    |   ^(VOID_METHOD_DECL modifierList genericTypeParameterList? IDENT formalParameterList throwsClause?)
+        // Interface constant declarations have been switched to variable
+        // declarations by Charj.g; the parser has already checked that
+        // there's an obligatory initializer.
+    |   ^(VAR_DECLARATION modifierList type variableDeclaratorList)
+    |   typeDeclaration
+    ;
+
+variableDeclaratorList
+    :   ^(VAR_DECLARATOR_LIST variableDeclarator+)
+    ;
+
+variableDeclarator
+    :   ^(VAR_DECLARATOR variableDeclaratorId variableInitializer?)
+    ;
+    
+variableDeclaratorId
+    :   ^(IDENT arrayDeclaratorList?)
+    ;
+
+variableInitializer
+    :   arrayInitializer
+    |   expression
+    ;
+
+arrayDeclarator
+    :   LBRACK RBRACK
+    ;
+
+arrayDeclaratorList
+    :   ^(ARRAY_DECLARATOR_LIST ARRAY_DECLARATOR*)  
+    ;
+    
+arrayInitializer
+    :   ^(ARRAY_INITIALIZER variableInitializer*)
+    ;
+
+throwsClause
+    :   ^(THROWS_CLAUSE qualifiedIdentifier+)
+    ;
+
+modifierList
+    :   ^(MODIFIER_LIST modifier*)
+    ;
+
+modifier
+    :   PUBLIC
+    |   PROTECTED
+    |   PRIVATE
+    |   STATIC
+    |   ABSTRACT
+    |   NATIVE
+    |   SYNCHRONIZED
+    |   TRANSIENT
+    |   VOLATILE
+    |   localModifier
+    ;
+
+localModifierList
+    :   ^(LOCAL_MODIFIER_LIST localModifier*)
+    ;
+
+localModifier
+    :   FINAL
+    ;
+
+type
+    :   ^(TYPE (primitiveType | qualifiedTypeIdent) arrayDeclaratorList?) -> template(t={$text}) "<t>"
+    ;
+
+qualifiedTypeIdent
+    :   ^(QUALIFIED_TYPE_IDENT typeIdent+) 
+    ;
+
+typeIdent
+    :   ^(IDENT genericTypeArgumentList?)
+    ;
+
+primitiveType
+    :   BOOLEAN
+    |   CHAR
+    |   BYTE
+    |   SHORT
+    |   INT
+    |   LONG
+    |   FLOAT
+    |   DOUBLE
+    ;
+
+genericTypeArgumentList
+    :   ^(GENERIC_TYPE_ARG_LIST genericTypeArgument+)
+    ;
+    
+genericTypeArgument
+    :   type
+    |   ^(QUESTION genericWildcardBoundType?)
+    ;
+
+genericWildcardBoundType                                                                                                                      
+    :   ^(EXTENDS type)
+    |   ^(SUPER type)
+    ;
+
+formalParameterList
+    :   ^(FORMAL_PARAM_LIST formalParameterStandardDecl* formalParameterVarargDecl?) 
+    ;
+    
+formalParameterStandardDecl
+    :   ^(FORMAL_PARAM_STD_DECL localModifierList type variableDeclaratorId)
+    ;
+    
+formalParameterVarargDecl
+    :   ^(FORMAL_PARAM_VARARG_DECL localModifierList type variableDeclaratorId)
+    ;
+    
+qualifiedIdentifier
+    :   IDENT
+    |   ^(DOT qualifiedIdentifier IDENT)
+    ;
+    
+block
+    :   ^(BLOCK_SCOPE blockStatement*)
+    ;
+    
+blockStatement
+    :   localVariableDeclaration
+    |   typeDeclaration
+    |   statement
+    ;
+    
+localVariableDeclaration
+    :   ^(VAR_DECLARATION localModifierList type variableDeclaratorList)
+    ;
+    
+        
+statement
+    :   block
+    |   ^(ASSERT expression expression?)
+    |   ^(IF parenthesizedExpression statement statement?)
+    |   ^(FOR forInit forCondition forUpdater statement)
+    |   ^(FOR_EACH localModifierList type IDENT expression statement) 
+    |   ^(WHILE parenthesizedExpression statement)
+    |   ^(DO statement parenthesizedExpression)
+    |   ^(TRY block catches? block?)  // The second optional block is the optional finally block.
+    |   ^(SWITCH parenthesizedExpression switchBlockLabels)
+    |   ^(SYNCHRONIZED parenthesizedExpression block)
+    |   ^(RETURN expression?)
+    |   ^(THROW expression)
+    |   ^(BREAK IDENT?)
+    |   ^(CONTINUE IDENT?)
+    |   ^(LABELED_STATEMENT IDENT statement)
+    |   expression
+    |   SEMI // Empty statement.
+    ;
+        
+catches
+    :   ^(CATCH_CLAUSE_LIST catchClause+)
+    ;
+    
+catchClause
+    :   ^(CATCH formalParameterStandardDecl block)
+    ;
+
+switchBlockLabels
+    :   ^(SWITCH_BLOCK_LABEL_LIST switchCaseLabel* switchDefaultLabel? switchCaseLabel*)
+    ;
+        
+switchCaseLabel
+    :   ^(CASE expression blockStatement*)
+    ;
+    
+switchDefaultLabel
+    :   ^(DEFAULT blockStatement*)
+    ;
+    
+forInit
+    :   ^(FOR_INIT (localVariableDeclaration | expression*)?)
+    ;
+    
+forCondition
+    :   ^(FOR_CONDITION expression?)
+    ;
+    
+forUpdater
+    :   ^(FOR_UPDATE expression*)
+    ;
+    
+// EXPRESSIONS
+
+parenthesizedExpression
+    :   ^(PARENTESIZED_EXPR expression)
+    ;
+    
+expression
+    :   ^(EXPR expr)
+    ;
+
+expr
+    :   ^(ASSIGN expr expr)
+    |   ^(PLUS_ASSIGN expr expr)
+    |   ^(MINUS_ASSIGN expr expr)
+    |   ^(STAR_ASSIGN expr expr)
+    |   ^(DIV_ASSIGN expr expr)
+    |   ^(AND_ASSIGN expr expr)
+    |   ^(OR_ASSIGN expr expr)
+    |   ^(XOR_ASSIGN expr expr)
+    |   ^(MOD_ASSIGN expr expr)
+    |   ^(BIT_SHIFT_RIGHT_ASSIGN expr expr)
+    |   ^(SHIFT_RIGHT_ASSIGN expr expr)
+    |   ^(SHIFT_LEFT_ASSIGN expr expr)
+    |   ^(QUESTION expr expr expr)
+    |   ^(LOGICAL_OR expr expr)
+    |   ^(LOGICAL_AND expr expr)
+    |   ^(OR expr expr)
+    |   ^(XOR expr expr)
+    |   ^(AND expr expr)
+    |   ^(EQUAL expr expr)
+    |   ^(NOT_EQUAL expr expr)
+    |   ^(INSTANCEOF expr type)
+    |   ^(LESS_OR_EQUAL expr expr)
+    |   ^(GREATER_OR_EQUAL expr expr)
+    |   ^(BIT_SHIFT_RIGHT expr expr)
+    |   ^(SHIFT_RIGHT expr expr)
+    |   ^(GREATER_THAN expr expr)
+    |   ^(SHIFT_LEFT expr expr)
+    |   ^(LESS_THAN expr expr)
+    |   ^(PLUS expr expr)
+    |   ^(MINUS expr expr)
+    |   ^(STAR expr expr)
+    |   ^(DIV expr expr)
+    |   ^(MOD expr expr)
+    |   ^(UNARY_PLUS expr)
+    |   ^(UNARY_MINUS expr)
+    |   ^(PRE_INC expr)
+    |   ^(PRE_DEC expr)
+    |   ^(POST_INC expr)
+    |   ^(POST_DEC expr)
+    |   ^(NOT expr)
+    |   ^(LOGICAL_NOT expr)
+    |   ^(CAST_EXPR type expr)
+    |   primaryExpression
+    ;
+    
+primaryExpression
+    :   ^(  DOT
+            (   primaryExpression
+                (   IDENT
+                |   THIS
+                |   SUPER
+                |   innerNewExpression
+                |   CLASS
+                )
+            |   primitiveType CLASS
+            |   VOID CLASS
+            )
+        )
+    |   parenthesizedExpression
+    |   IDENT
+    |   ^(METHOD_CALL primaryExpression genericTypeArgumentList? arguments)
+    |   explicitConstructorCall
+    |   ^(ARRAY_ELEMENT_ACCESS primaryExpression expression)
+    |   literal
+    |   newExpression
+    |   THIS
+    |   arrayTypeDeclarator
+    |   SUPER
+    ;
+    
+explicitConstructorCall
+    :   ^(THIS_CONSTRUCTOR_CALL genericTypeArgumentList? arguments)
+    |   ^(SUPER_CONSTRUCTOR_CALL primaryExpression? genericTypeArgumentList? arguments)
+    ;
+
+arrayTypeDeclarator
+    :   ^(ARRAY_DECLARATOR (arrayTypeDeclarator | qualifiedIdentifier | primitiveType))
+    ;
+
+newExpression
+    :   ^(  STATIC_ARRAY_CREATOR
+            (   primitiveType newArrayConstruction
+            |   genericTypeArgumentList? qualifiedTypeIdent newArrayConstruction
+            )
+        )
+    |   ^(CLASS_CONSTRUCTOR_CALL genericTypeArgumentList? qualifiedTypeIdent arguments classTopLevelScope?)
+    ;
+
+innerNewExpression // something like 'InnerType innerType = outer.new InnerType();'
+    :   ^(CLASS_CONSTRUCTOR_CALL genericTypeArgumentList? IDENT arguments classTopLevelScope?)
+    ;
+    
+newArrayConstruction
+    :   arrayDeclaratorList arrayInitializer
+    |   expression+ arrayDeclaratorList?
+    ;
+
+arguments
+    :   ^(ARGUMENT_LIST expression*)
+    ;
+
+literal 
+    :   HEX_LITERAL
+    |   OCTAL_LITERAL
+    |   DECIMAL_LITERAL
+    |   FLOATING_POINT_LITERAL
+    |   CHARACTER_LITERAL
+    |   STRING_LITERAL
+    |   TRUE
+    |   FALSE
+    |   NULL
+    ;
diff --git a/src/langs/charj/src/charj/translator/CharjTreeParser.g b/src/langs/charj/src/charj/translator/CharjTreeParser.g
new file mode 100644 (file)
index 0000000..fec8f47
--- /dev/null
@@ -0,0 +1,464 @@
+/**
+ * ANTLR (v3) Tree Parser for the Charj Language
+ */
+
+tree grammar CharjTreeParser;
+
+options {
+    backtrack = true; 
+    memoize = true;
+    tokenVocab = Charj;
+    ASTLabelType = CommonTree;
+}
+
+
+@treeparser::header {
+package charj.translator;
+}
+
+@treeparser::members {
+    
+    boolean mMessageCollectionEnabled = false;
+    private boolean mHasErrors = false;
+    List<String> mMessages;
+
+    /**
+     *  Switches error message collection on or off.
+     *
+     *  The standard destination for parser error messages is <code>System.err</code>.
+     *  However, if <code>true</code> gets passed to this method this default
+     *  behaviour will be switched off and all error messages will be collected
+     *  instead of written to anywhere.
+     *
+     *  The default value is <code>false</code>.
+     *
+     *  @param pNewState  <code>true</code> if error messages should be collected.
+     */
+    public void enableErrorMessageCollection(boolean pNewState) {
+        mMessageCollectionEnabled = pNewState;
+        if (mMessages == null && mMessageCollectionEnabled) {
+            mMessages = new ArrayList<String>();
+        }
+    }
+    
+    /**
+     *  Collects an error message or passes the error message to <code>
+     *  super.emitErrorMessage(...)</code>.
+     *
+     *  The actual behaviour depends on whether collecting error messages
+     *  has been enabled or not.
+     *
+     *  @param pMessage  The error message.
+     */
+     @Override
+    public void emitErrorMessage(String pMessage) {
+        if (mMessageCollectionEnabled) {
+            mMessages.add(pMessage);
+        } else {
+            super.emitErrorMessage(pMessage);
+        }
+    }
+    
+    /**
+     *  Returns collected error messages.
+     *
+     *  @return  A list holding collected error messages or <code>null</code> if
+     *           collecting error messages hasn't been enabled. Of course, this
+     *           list may be empty if no error message has been emited.
+     */
+    public List<String> getMessages() {
+        return mMessages;
+    }
+    
+    /**
+     *  Tells if parsing a Charj source has caused any error messages.
+     *
+     *  @return  <code>true</code> if parsing a Charj source has caused at 
+                 least one error message.
+     */
+    public boolean hasErrors() {
+        return mHasErrors;
+    }
+}
+
+// Starting point for parsing a Charj file.
+charjSource
+    :   ^(CHARJ_SOURCE packageDeclaration? importDeclaration* typeDeclaration*)
+    ;
+
+packageDeclaration
+    :   ^(PACKAGE qualifiedIdentifier)  
+    ;
+    
+importDeclaration
+    :   ^(IMPORT STATIC? qualifiedIdentifier DOTSTAR?)
+    ;
+    
+typeDeclaration
+    :   ^(CLASS modifierList IDENT genericTypeParameterList? extendsClause? implementsClause? classTopLevelScope)
+    |   ^(INTERFACE modifierList IDENT genericTypeParameterList? extendsClause? interfaceTopLevelScope)
+    |   ^(ENUM modifierList IDENT implementsClause? enumTopLevelScope)
+    ;
+
+extendsClause // actually 'type' for classes and 'type+' for interfaces, but this has 
+              // been resolved by the parser grammar.
+    :   ^(EXTENDS_CLAUSE type+)
+    ;   
+    
+implementsClause
+    :   ^(IMPLEMENTS_CLAUSE type+)
+    ;
+        
+genericTypeParameterList
+    :   ^(GENERIC_TYPE_PARAM_LIST genericTypeParameter+)
+    ;
+
+genericTypeParameter
+    :   ^(IDENT bound?)
+    ;
+        
+bound
+    :   ^(EXTENDS_BOUND_LIST type+)
+    ;
+
+enumTopLevelScope
+    :   ^(ENUM_TOP_LEVEL_SCOPE enumConstant+ classTopLevelScope?)
+    ;
+    
+enumConstant
+    :   ^(IDENT arguments? classTopLevelScope?)
+    ;
+    
+    
+classTopLevelScope
+    :   ^(CLASS_TOP_LEVEL_SCOPE classScopeDeclarations*)
+    ;
+    
+classScopeDeclarations
+    :   ^(CLASS_INSTANCE_INITIALIZER block)
+    |   ^(CLASS_STATIC_INITIALIZER block)
+    |   ^(FUNCTION_METHOD_DECL modifierList genericTypeParameterList? type IDENT formalParameterList arrayDeclaratorList? throwsClause? block?)
+    |   ^(VOID_METHOD_DECL modifierList genericTypeParameterList? IDENT formalParameterList throwsClause? block?)
+    |   ^(VAR_DECLARATION modifierList type variableDeclaratorList)
+    |   ^(CONSTRUCTOR_DECL modifierList genericTypeParameterList? formalParameterList throwsClause? block)
+    |   typeDeclaration
+    ;
+    
+interfaceTopLevelScope
+    :   ^(INTERFACE_TOP_LEVEL_SCOPE interfaceScopeDeclarations*)
+    ;
+    
+interfaceScopeDeclarations
+    :   ^(FUNCTION_METHOD_DECL modifierList genericTypeParameterList? type IDENT formalParameterList arrayDeclaratorList? throwsClause?)
+    |   ^(VOID_METHOD_DECL modifierList genericTypeParameterList? IDENT formalParameterList throwsClause?)
+
+
+// Interface constant declarations have been switched to variable
+// declarations by Charj.g; the parser has already checked that
+// there's an obligatory initializer.
+    |   ^(VAR_DECLARATION modifierList type variableDeclaratorList)
+    |   typeDeclaration
+    ;
+
+variableDeclaratorList
+    :   ^(VAR_DECLARATOR_LIST variableDeclarator+)
+    ;
+
+variableDeclarator
+    :   ^(VAR_DECLARATOR variableDeclaratorId variableInitializer?)
+    ;
+    
+variableDeclaratorId
+    :   ^(IDENT arrayDeclaratorList?)
+    ;
+
+variableInitializer
+    :   arrayInitializer
+    |   expression
+    ;
+
+arrayDeclarator
+    :   LBRACK RBRACK
+    ;
+
+arrayDeclaratorList
+    :   ^(ARRAY_DECLARATOR_LIST ARRAY_DECLARATOR*)  
+    ;
+    
+arrayInitializer
+    :   ^(ARRAY_INITIALIZER variableInitializer*)
+    ;
+
+throwsClause
+    :   ^(THROWS_CLAUSE qualifiedIdentifier+)
+    ;
+
+modifierList
+    :   ^(MODIFIER_LIST modifier*)
+    ;
+
+modifier
+    :   PUBLIC
+    |   PROTECTED
+    |   PRIVATE
+    |   STATIC
+    |   ABSTRACT
+    |   NATIVE
+    |   SYNCHRONIZED
+    |   TRANSIENT
+    |   VOLATILE
+    |   localModifier
+    ;
+
+localModifierList
+    :   ^(LOCAL_MODIFIER_LIST localModifier*)
+    ;
+
+localModifier
+    :   FINAL
+    ;
+
+type
+    :   ^(TYPE (primitiveType | qualifiedTypeIdent) arrayDeclaratorList?)
+    ;
+
+qualifiedTypeIdent
+    :   ^(QUALIFIED_TYPE_IDENT typeIdent+) 
+    ;
+
+typeIdent
+    :   ^(IDENT genericTypeArgumentList?)
+    ;
+
+primitiveType
+    :   BOOLEAN
+    |   CHAR
+    |   BYTE
+    |   SHORT
+    |   INT
+    |   LONG
+    |   FLOAT
+    |   DOUBLE
+    ;
+
+genericTypeArgumentList
+    :   ^(GENERIC_TYPE_ARG_LIST genericTypeArgument+)
+    ;
+    
+genericTypeArgument
+    :   type
+    |   ^(QUESTION genericWildcardBoundType?)
+    ;
+
+genericWildcardBoundType                                                                                                                      
+    :   ^(EXTENDS type)
+    |   ^(SUPER type)
+    ;
+
+formalParameterList
+    :   ^(FORMAL_PARAM_LIST formalParameterStandardDecl* formalParameterVarargDecl?) 
+    ;
+    
+formalParameterStandardDecl
+    :   ^(FORMAL_PARAM_STD_DECL localModifierList type variableDeclaratorId)
+    ;
+    
+formalParameterVarargDecl
+    :   ^(FORMAL_PARAM_VARARG_DECL localModifierList type variableDeclaratorId)
+    ;
+    
+qualifiedIdentifier
+    :   IDENT
+    |   ^(DOT qualifiedIdentifier IDENT)
+    ;
+    
+block
+    :   ^(BLOCK_SCOPE blockStatement*)
+    ;
+    
+blockStatement
+    :   localVariableDeclaration
+    |   typeDeclaration
+    |   statement
+    ;
+    
+localVariableDeclaration
+    :   ^(VAR_DECLARATION localModifierList type variableDeclaratorList)
+    ;
+    
+        
+statement
+    :   block
+    |   ^(ASSERT expression expression?)
+    |   ^(IF parenthesizedExpression statement statement?)
+    |   ^(FOR forInit forCondition forUpdater statement)
+    |   ^(FOR_EACH localModifierList type IDENT expression statement) 
+    |   ^(WHILE parenthesizedExpression statement)
+    |   ^(DO statement parenthesizedExpression)
+    |   ^(TRY block catches? block?)  // The second optional block is the optional finally block.
+    |   ^(SWITCH parenthesizedExpression switchBlockLabels)
+    |   ^(SYNCHRONIZED parenthesizedExpression block)
+    |   ^(RETURN expression?)
+    |   ^(THROW expression)
+    |   ^(BREAK IDENT?)
+    |   ^(CONTINUE IDENT?)
+    |   ^(LABELED_STATEMENT IDENT statement)
+    |   expression
+    |   SEMI // Empty statement.
+    ;
+        
+catches
+    :   ^(CATCH_CLAUSE_LIST catchClause+)
+    ;
+    
+catchClause
+    :   ^(CATCH formalParameterStandardDecl block)
+    ;
+
+switchBlockLabels
+    :   ^(SWITCH_BLOCK_LABEL_LIST switchCaseLabel* switchDefaultLabel? switchCaseLabel*)
+    ;
+        
+switchCaseLabel
+    :   ^(CASE expression blockStatement*)
+    ;
+    
+switchDefaultLabel
+    :   ^(DEFAULT blockStatement*)
+    ;
+    
+forInit
+    :   ^(FOR_INIT (localVariableDeclaration | expression*)?)
+    ;
+    
+forCondition
+    :   ^(FOR_CONDITION expression?)
+    ;
+    
+forUpdater
+    :   ^(FOR_UPDATE expression*)
+    ;
+    
+// EXPRESSIONS
+
+parenthesizedExpression
+    :   ^(PARENTESIZED_EXPR expression)
+    ;
+    
+expression
+    :   ^(EXPR expr)
+    ;
+
+expr
+    :   ^(ASSIGN expr expr)
+    |   ^(PLUS_ASSIGN expr expr)
+    |   ^(MINUS_ASSIGN expr expr)
+    |   ^(STAR_ASSIGN expr expr)
+    |   ^(DIV_ASSIGN expr expr)
+    |   ^(AND_ASSIGN expr expr)
+    |   ^(OR_ASSIGN expr expr)
+    |   ^(XOR_ASSIGN expr expr)
+    |   ^(MOD_ASSIGN expr expr)
+    |   ^(BIT_SHIFT_RIGHT_ASSIGN expr expr)
+    |   ^(SHIFT_RIGHT_ASSIGN expr expr)
+    |   ^(SHIFT_LEFT_ASSIGN expr expr)
+    |   ^(QUESTION expr expr expr)
+    |   ^(LOGICAL_OR expr expr)
+    |   ^(LOGICAL_AND expr expr)
+    |   ^(OR expr expr)
+    |   ^(XOR expr expr)
+    |   ^(AND expr expr)
+    |   ^(EQUAL expr expr)
+    |   ^(NOT_EQUAL expr expr)
+    |   ^(INSTANCEOF expr type)
+    |   ^(LESS_OR_EQUAL expr expr)
+    |   ^(GREATER_OR_EQUAL expr expr)
+    |   ^(BIT_SHIFT_RIGHT expr expr)
+    |   ^(SHIFT_RIGHT expr expr)
+    |   ^(GREATER_THAN expr expr)
+    |   ^(SHIFT_LEFT expr expr)
+    |   ^(LESS_THAN expr expr)
+    |   ^(PLUS expr expr)
+    |   ^(MINUS expr expr)
+    |   ^(STAR expr expr)
+    |   ^(DIV expr expr)
+    |   ^(MOD expr expr)
+    |   ^(UNARY_PLUS expr)
+    |   ^(UNARY_MINUS expr)
+    |   ^(PRE_INC expr)
+    |   ^(PRE_DEC expr)
+    |   ^(POST_INC expr)
+    |   ^(POST_DEC expr)
+    |   ^(NOT expr)
+    |   ^(LOGICAL_NOT expr)
+    |   ^(CAST_EXPR type expr)
+    |   primaryExpression
+    ;
+    
+primaryExpression
+    :   ^(  DOT
+            (   primaryExpression
+                (   IDENT
+                |   THIS
+                |   SUPER
+                |   innerNewExpression
+                |   CLASS
+                )
+            |   primitiveType CLASS
+            |   VOID CLASS
+            )
+        )
+    |   parenthesizedExpression
+    |   IDENT
+    |   ^(METHOD_CALL primaryExpression genericTypeArgumentList? arguments)
+    |   explicitConstructorCall
+    |   ^(ARRAY_ELEMENT_ACCESS primaryExpression expression)
+    |   literal
+    |   newExpression
+    |   THIS
+    |   arrayTypeDeclarator
+    |   SUPER
+    ;
+    
+explicitConstructorCall
+    :   ^(THIS_CONSTRUCTOR_CALL genericTypeArgumentList? arguments)
+    |   ^(SUPER_CONSTRUCTOR_CALL primaryExpression? genericTypeArgumentList? arguments)
+    ;
+
+arrayTypeDeclarator
+    :   ^(ARRAY_DECLARATOR (arrayTypeDeclarator | qualifiedIdentifier | primitiveType))
+    ;
+
+newExpression
+    :   ^(  STATIC_ARRAY_CREATOR
+            (   primitiveType newArrayConstruction
+            |   genericTypeArgumentList? qualifiedTypeIdent newArrayConstruction
+            )
+        )
+    |   ^(CLASS_CONSTRUCTOR_CALL genericTypeArgumentList? qualifiedTypeIdent arguments classTopLevelScope?)
+    ;
+
+innerNewExpression // something like 'InnerType innerType = outer.new InnerType();'
+    :   ^(CLASS_CONSTRUCTOR_CALL genericTypeArgumentList? IDENT arguments classTopLevelScope?)
+    ;
+    
+newArrayConstruction
+    :   arrayDeclaratorList arrayInitializer
+    |   expression+ arrayDeclaratorList?
+    ;
+
+arguments
+    :   ^(ARGUMENT_LIST expression*)
+    ;
+
+literal 
+    :   HEX_LITERAL
+    |   OCTAL_LITERAL
+    |   DECIMAL_LITERAL
+    |   FLOATING_POINT_LITERAL
+    |   CHARACTER_LITERAL
+    |   STRING_LITERAL
+    |   TRUE
+    |   FALSE
+    |   NULL
+    ;
diff --git a/src/langs/charj/src/charj/translator/Translator.java b/src/langs/charj/src/charj/translator/Translator.java
new file mode 100644 (file)
index 0000000..bea22bf
--- /dev/null
@@ -0,0 +1,78 @@
+/***
+***/
+
+package charj.translator;
+
+import org.antlr.runtime.*;
+import org.antlr.runtime.tree.*;
+import org.antlr.stringtemplate.*;
+import java.io.*;
+
+public class Translator {
+
+    public static final String templateFile = "src/charj/translator/Charj.stg";
+    public static boolean debug = true;
+    public static boolean errorCondition = false;
+
+    public static String translate(InputStream io) throws Exception {
+        StringTemplateGroup templates = null;
+        try {
+            ClassLoader loader = Thread.currentThread().getContextClassLoader();
+            InputStream istream = loader.getResourceAsStream(templateFile);
+            BufferedReader reader = new BufferedReader(new InputStreamReader(istream));
+            templates = new StringTemplateGroup(reader);
+            reader.close();
+        } catch(IOException ex) {
+            error("Failed to load template file", ex); 
+        }
+
+        // Parse input, creating an AST
+        ANTLRInputStream input = new ANTLRInputStream(io);
+        CharjLexer lexer = new CharjLexer(input);
+        
+        // Use lexer tokens to feed tree parser. Note that the parser is a
+        // rewriter, so a TokenRewriteStream is needed
+        TokenRewriteStream tokens = new TokenRewriteStream(lexer);
+        CharjParser parser = new CharjParser(tokens);
+        CharjParser.charjSource_return r = parser.charjSource();
+
+        // Walk tree, modifying input buffer
+        CommonTree t = (CommonTree)r.getTree();
+        CommonTreeNodeStream nodes = new CommonTreeNodeStream(t);
+        nodes.setTokenStream(tokens);
+        CharjEmitter emitter = new CharjEmitter(nodes);
+        emitter.setTemplateLib(templates);
+        emitter.charjSource();
+
+        return tokens.toString();
+    }
+
+    
+    public static void error(String sourceName, String msg, CommonTree node) 
+    {
+        errorCondition = true;
+        String linecol = ":";
+        if ( node!=null ) {
+            CommonToken t = (CommonToken)node.getToken();
+            linecol = "line " + t.getLine() + ":" + t.getCharPositionInLine();
+        }
+        System.err.println(sourceName + ": " + linecol + " " + msg);
+        System.err.flush();
+    }
+
+
+    public static void error(String sourceName, String msg) {
+        error(sourceName, msg, (CommonTree)null);
+    }
+
+
+    public static void error(String msg) {
+        error("charj", msg, (CommonTree)null);
+    }
+
+
+    public static void error(String msg, Exception e) {
+        error(msg);
+        e.printStackTrace(System.err);
+    }
+}
diff --git a/src/langs/charj/tests/hello.cj b/src/langs/charj/tests/hello.cj
new file mode 100644 (file)
index 0000000..c51cb29
--- /dev/null
@@ -0,0 +1,14 @@
+public class Hello extends Chare {
+    public Hello() {}
+    public void sayHello(int payload) {
+        int[] myArray = new int[25];
+        Array<int> myGenericArray = new Array<int>(25);
+        for (int i=0; i<25; ++i) {
+            myArray[i] = payload + i;
+            myGenericArray[i] = payload * i;
+        }
+    }
+}
+
+public interface INT extends I1, I2 {
+}