summaryrefslogtreecommitdiff
path: root/boil/BoilVisitor.java
diff options
context:
space:
mode:
Diffstat (limited to 'boil/BoilVisitor.java')
-rw-r--r--boil/BoilVisitor.java1294
1 files changed, 1294 insertions, 0 deletions
diff --git a/boil/BoilVisitor.java b/boil/BoilVisitor.java
new file mode 100644
index 0000000..e8bafe3
--- /dev/null
+++ b/boil/BoilVisitor.java
@@ -0,0 +1,1294 @@
+package boil;
+
+import syntaxtree.*;
+import visitor.*;
+import st.*;
+import misc.*;
+import java.util.*;
+
+public class BoilVisitor extends GJDepthFirst<String,String> {
+
+ private String vapor;
+ private TypeFactory tf; // the shared type generator
+ private int id;
+ private SymbolTable symt;
+
+ private MethodInstance recentMethod = null; // the most recent method called
+ private ClassInstance recentClass = null;
+
+ public BoilVisitor(SymbolTable symt) {
+ this.symt = symt;
+ this.vapor = "";
+ this.tf = new TypeFactory();
+ this.id = 0;
+ }
+
+ public String getVapor() {
+ return this.vapor;
+ }
+
+ public int getVarIndex(ClassInstance cls, TypeInstance type) {
+ /**
+ * Returns the index of the attribute in the class, or a negative number
+ * if it is not included.
+ */
+ int attr_index = -1;
+ if (cls != null &&
+ ((attr_index = cls.getLocals().indexOf(type)*4) >= 0)) {
+ attr_index += cls.getMethods().size() * 4;
+ }
+ return attr_index;
+ }
+
+ public String memoryRead(String rhs) {
+ String lhs = this.tf.alias(this.getUniqueID());
+ this.addVapor(String.format(" %s = %s\n",
+ lhs,
+ rhs));
+
+ return lhs;
+ }
+
+ private void addVapor(String str) {
+ MinimalLogger.info(String.format("Adding \"%s\"",
+ str));
+ this.vapor += str;
+ }
+
+ private String getUniqueID() {
+ return Integer.toString(this.id++);
+ }
+
+ private void resetIDs() {
+ MinimalLogger.info(String.format("Clearing tf for new function..."));
+ this.tf.reset();
+ this.id = 0;
+ }
+
+ //
+ // Auto class visitors--probably don't need to be overridden.
+ //
+ public String visit(NodeList n, String argu) {
+ String _ret="";
+ int _count=0;
+ for ( Enumeration<Node> e = n.elements(); e.hasMoreElements(); ) {
+ _ret += e.nextElement().accept(this,argu);
+ _count++;
+ }
+ return _ret;
+ }
+
+ public String visit(NodeListOptional n, String argu) {
+ if ( n.present() ) {
+ String _ret="";
+ int _count=0;
+ for ( Enumeration<Node> e = n.elements(); e.hasMoreElements(); ) {
+ _ret += e.nextElement().accept(this,argu);
+ _count++;
+ }
+ return _ret;
+ }
+ else
+ return "";
+ }
+
+ public String visit(NodeOptional n, String argu) {
+ if ( n.present() )
+ return n.node.accept(this,argu);
+ else
+ return "";
+ }
+
+ public String visit(NodeSequence n, String argu) {
+ String _ret=null;
+ int _count=0;
+ for ( Enumeration<Node> e = n.elements(); e.hasMoreElements(); ) {
+ e.nextElement().accept(this,argu);
+ _count++;
+ }
+ return _ret;
+ }
+
+ public String visit(NodeToken n, String argu) {
+ return null;
+ }
+
+ //
+ // User-generated visitor methods below
+ //
+
+ /**
+ * f0 -> MainClass()
+ * f1 -> ( TypeDeclaration() )*
+ * f2 -> <EOF>
+ */
+ public String visit(Goal n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ n.f0.accept(this, argu);
+ n.f1.accept(this, argu);
+ n.f2.accept(this, argu);
+
+ this.addVapor(String.format("func AllocArray(size)\n bytes = MulS(size 4)\n bytes = Add(bytes 4)\n v = HeapAllocZ(bytes)\n [v] = size\n ret v\n"));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "class"
+ * f1 -> Identifier()
+ * f2 -> "{"
+ * f3 -> "public"
+ * f4 -> "static"
+ * f5 -> "void"
+ * f6 -> "main"
+ * f7 -> "("
+ * f8 -> "String"
+ * f9 -> "["
+ * f10 -> "]"
+ * f11 -> Identifier()
+ * f12 -> ")"
+ * f13 -> "{"
+ * f14 -> ( VarDeclaration() )*
+ * f15 -> ( Statement() )*
+ * f16 -> "}"
+ * f17 -> "}"
+ */
+ public String visit(MainClass n, String argu) {
+ String _ret=null;
+ this.tf.reset();
+ String id = n.f1.f0.tokenImage;
+ MinimalLogger.info(String.format("-> %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ this.symt.setActive(TypeEnum.classname, symt.getClass(id));
+ this.symt.setActive(TypeEnum.method, symt.getMethod(n.f6.tokenImage));
+ ///////////////////////////////////////////////////////////////
+ this.addVapor("func Main()\n");
+ n.f1.accept(this, argu);
+ n.f11.accept(this, argu);
+ n.f14.accept(this, argu);
+ n.f15.accept(this, argu);
+ this.addVapor(" ret\n\n");
+ ///////////////////////////////////////////////////////////////
+ this.symt.removeActive(TypeEnum.method);
+ symt.removeActive(TypeEnum.classname);
+ MinimalLogger.info(String.format("<- %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ return _ret;
+ }
+
+ /**
+ * f0 -> ClassDeclaration()
+ * | ClassExtendsDeclaration()
+ */
+ public String visit(TypeDeclaration n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ n.f0.accept(this, argu);
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ ///////////////////////////////////////////////////////////////
+ return _ret;
+ }
+
+ /**
+ * f0 -> "class"
+ * f1 -> Identifier()
+ * f2 -> "{"
+ * f3 -> ( VarDeclaration() )*
+ * f4 -> ( MethodDeclaration() )*
+ * f5 -> "}"
+ */
+ public String visit(ClassDeclaration n, String argu) {
+ String _ret=null;
+ String id = n.f1.f0.tokenImage;
+ MinimalLogger.info(String.format("-> %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ this.symt.setActive(TypeEnum.classname, symt.getClass(id));
+ ///////////////////////////////////////////////////////////////
+ this.addVapor(String.format("const functable_%s\n", id));
+ for (MethodInstance mtd : this.symt.getClass(id).getMethods()) {
+ this.addVapor(String.format(" :%s_%s\n", mtd.getParentClass().getName(), mtd));
+ }
+ this.addVapor("\n");
+ // n.f3.accept(this, argu);
+ n.f4.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ this.symt.removeActive(TypeEnum.classname);
+ MinimalLogger.info(String.format("<- %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "class"
+ * f1 -> Identifier()
+ * f2 -> "extends"
+ * f3 -> Identifier()
+ * f4 -> "{"
+ * f5 -> ( VarDeclaration() )*
+ * f6 -> ( MethodDeclaration() )*
+ * f7 -> "}"
+ */
+ public String visit(ClassExtendsDeclaration n, String argu) {
+ String _ret=null;
+ String id = n.f1.f0.tokenImage;
+ MinimalLogger.info(String.format("-> %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ this.symt.setActive(TypeEnum.classname, symt.getClass(id));
+ ///////////////////////////////////////////////////////////////
+ this.addVapor(String.format("const functable_%s\n", id));
+ for (MethodInstance mtd : this.symt.getClass(id).getMethods()) {
+ this.addVapor(String.format(" :%s_%s\n", mtd.getParentClass().getName(), mtd));
+ }
+ this.addVapor("\n");
+ // n.f3.accept(this, argu);
+ // n.f5.accept(this, argu);
+ n.f6.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ this.symt.removeActive(TypeEnum.classname);
+ MinimalLogger.info(String.format("<- %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ return _ret;
+ }
+
+ /**
+ * f0 -> Type()
+ * f1 -> Identifier()
+ * f2 -> ";"
+ */
+ public String visit(VarDeclaration n, String argu) {
+ String _ret=null;
+ String id = n.f1.f0.tokenImage;
+ MinimalLogger.info(String.format("-> %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ ///////////////////////////////////////////////////////////////
+ // if (t.getClassInstance() != null)
+ // this.addVapor(String.format(" %s = HeapAllocZ(%d)\n",
+ // this.tf.alias(t.getName()),
+ // t.getSize()));
+ n.f0.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "public"
+ * f1 -> Type()
+ * f2 -> Identifier()
+ * f3 -> "("
+ * f4 -> ( FormalParameterList() )?
+ * f5 -> ")"
+ * f6 -> "{"
+ * f7 -> ( VarDeclaration() )*
+ * f8 -> ( Statement() )*
+ * f9 -> "return"
+ * f10 -> Expression()
+ * f11 -> ";"
+ * f12 -> "}"
+ */
+ public String visit(MethodDeclaration n, String argu) {
+ String _ret=null;
+ this.tf.reset();
+ String id = n.f2.f0.tokenImage;
+ MinimalLogger.info(String.format("-> %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ this.symt.setActive(TypeEnum.method, symt.getMethod(id));
+ ///////////////////////////////////////////////////////////////
+ // n.f1.accept(this, argu);
+ this.addVapor(String.format("func %s_%s(this ",
+ this.symt.getActive(TypeEnum.classname),
+ id));
+ String para = n.f4.accept(this, argu);
+ this.addVapor(String.format("%s)\n", para));
+
+ n.f7.accept(this, argu);
+ n.f8.accept(this, argu);
+ String ret = n.f10.accept(this, argu);
+ String retID = this.getUniqueID();
+ this.addVapor(String.format(" %s = %s\n ret %s\n\n",
+ this.tf.alias(retID),
+ ret,
+ this.tf.alias(retID)));
+ ///////////////////////////////////////////////////////////////
+ this.symt.removeActive(TypeEnum.method);
+ MinimalLogger.info(String.format("<- %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ return _ret;
+ }
+
+ /**
+ * f0 -> FormalParameter()
+ * f1 -> ( FormalParameterRest() )*
+ */
+ public String visit(FormalParameterList n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += n.f0.accept(this, argu);
+ _ret += n.f1.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> Type()
+ * f1 -> Identifier()
+ */
+ public String visit(FormalParameter n, String argu) {
+ String _ret="";
+ String id = n.f1.f0.tokenImage;
+ MinimalLogger.info(String.format("-> %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ ///////////////////////////////////////////////////////////////
+ // n.f0.accept(this, argu);
+ _ret += n.f1.accept(this,argu) + " ";
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ return _ret;
+ }
+
+ /**
+ * f0 -> ","
+ * f1 -> FormalParameter()
+ */
+ public String visit(FormalParameterRest n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += n.f1.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> ArrayType()
+ * | BooleanType()
+ * | IntegerType()
+ * | Identifier()
+ */
+ public String visit(Type n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ n.f0.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "int"
+ * f1 -> "["
+ * f2 -> "]"
+ */
+ public String visit(ArrayType n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "boolean"
+ */
+ public String visit(BooleanType n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "int"
+ */
+ public String visit(IntegerType n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> Block()
+ * | AssignmentStatement()
+ * | ArrayAssignmentStatement()
+ * | IfStatement()
+ * | WhileStatement()
+ * | PrintStatement()
+ */
+ public String visit(Statement n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += n.f0.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "{"
+ * f1 -> ( Statement() )*
+ * f2 -> "}"
+ */
+ public String visit(Block n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ n.f1.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> Identifier()
+ * f1 -> "="
+ * f2 -> Expression()
+ * f3 -> ";"
+ */
+ public String visit(AssignmentStatement n, String argu) {
+ String _ret=null;
+ String id = n.f0.f0.tokenImage;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ String lhs = n.f0.accept(this, argu);
+ String expr = n.f2.accept(this, argu);
+
+ int attr_index = 0;
+ TypeInstance t;
+ if ((t = this.symt.getType(lhs)) != null) {
+ // memory store
+ ClassInstance cur = (ClassInstance) this.symt.getActive(TypeEnum.classname);
+ attr_index = getVarIndex(cur, t);
+ lhs = String.format("[this+%d]", attr_index);
+ }
+
+
+ this.addVapor(String.format(" %s = %s\n",
+ lhs,
+ expr));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s",
+ n.getClass().getSimpleName()));
+ return _ret;
+ }
+
+ /**
+ * f0 -> Identifier()
+ * f1 -> "["
+ * f2 -> Expression()
+ * f3 -> "]"
+ * f4 -> "="
+ * f5 -> Expression()
+ * f6 -> ";"
+ */
+ public String visit(ArrayAssignmentStatement n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ String arrID = this.tf.alias(this.getUniqueID());
+ String arr = n.f0.accept(this, argu);
+ this.addVapor(String.format(" %s = %s\n",
+ arrID,
+ arr));
+
+ String indexID = this.tf.alias(this.getUniqueID());
+ this.addVapor(String.format(" %s = MulS(%s %s)\n",
+ indexID,
+ n.f2.accept(this, argu),
+ 4));
+ this.addVapor(String.format(" %s = Add(%s %s)\n",
+ indexID,
+ indexID,
+ 4));
+ this.addVapor(String.format(" %s = Add(%s %s)\n",
+ indexID,
+ arrID,
+ indexID));
+
+ String expr = n.f5.accept(this, argu);
+
+ this.addVapor(String.format(" [%s] = %s\n",
+ indexID,
+ expr));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "if"
+ * f1 -> "("
+ * f2 -> Expression()
+ * f3 -> ")"
+ * f4 -> Statement()
+ * f5 -> "else"
+ * f6 -> Statement()
+ */
+ public String visit(IfStatement n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ String ifID = this.getUniqueID();
+ String cond = n.f2.accept(this, argu);
+
+ this.addVapor(String.format(" %s = %s\n",
+ this.tf.alias(ifID),
+ cond));
+ this.addVapor(String.format(" if0 %s goto :if%s_else\nif%s_body:\n",
+ this.tf.alias(ifID),
+ ifID,
+ ifID));
+
+ n.f4.accept(this, argu);
+
+ this.addVapor(String.format(" goto :if%s_end\nif%s_else:\n",
+ ifID,
+ ifID));
+
+ n.f6.accept(this, argu);
+
+ this.addVapor(String.format("if%s_end:\n",
+ ifID));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "while"
+ * f1 -> "("
+ * f2 -> Expression()
+ * f3 -> ")"
+ * f4 -> Statement()
+ */
+ public String visit(WhileStatement n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ String whileID = this.getUniqueID();
+
+ this.addVapor(String.format("while%s_test:\n",
+ whileID));
+ String cond = n.f2.accept(this, argu);
+
+ String condID = this.getUniqueID();
+ this.addVapor(String.format(" %s = %s\n",
+ this.tf.alias(condID),
+ cond));
+ this.addVapor(String.format(" if0 %s goto :while%s_end\nwhile%s_body:\n",
+ this.tf.alias(condID),
+ whileID,
+ whileID));
+
+ n.f4.accept(this, argu);
+
+ this.addVapor(String.format(" goto :while%s_test\nwhile%s_end:\n",
+ whileID,
+ whileID));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "System.out.println"
+ * f1 -> "("
+ * f2 -> Expression()
+ * f3 -> ")"
+ * f4 -> ";"
+ */
+ public String visit(PrintStatement n, String argu) {
+ String _ret=null;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ String printTemp = this.getUniqueID();
+ String expr = n.f2.accept(this, argu);
+
+ this.addVapor(String.format(" %s = %s\n",
+ this.tf.alias(printTemp),
+ expr));
+
+ this.addVapor(String.format(" PrintIntS(%s)\n",
+ this.tf.alias(printTemp)));
+
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> AndExpression()
+ * | CompareExpression()
+ * | PlusExpression()
+ * | MinusExpression()
+ * | TimesExpression()
+ * | ArrayLookup()
+ * | ArrayLength()
+ * | MessageSend()
+ * | PrimaryExpression()
+ */
+ // Expressions return a TYPE alias which is equal to the expression!
+ public String visit(Expression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += n.f0.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> PrimaryExpression()
+ * f1 -> "&&"
+ * f2 -> PrimaryExpression()
+ */
+ // Expressions return a TYPE alias which is equal to the expression!
+ public String visit(AndExpression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ _ret += this.tf.alias(this.getUniqueID());
+ ///////////////////////////////////////////////////////////////
+ String oper1 = this.memoryRead(n.f0.accept(this, argu));
+ String oper2 = this.memoryRead(n.f2.accept(this, argu));
+ String one = this.tf.alias(this.getUniqueID());
+ this.addVapor(String.format(" %s = Eq(1 %s)\n",
+ one,
+ oper1));
+ String two = this.tf.alias(this.getUniqueID());
+ this.addVapor(String.format(" %s = Eq(1 %s)\n",
+ two,
+ oper2));
+ this.addVapor(String.format(" %s = Eq(%s %s)\n",
+ _ret,
+ one,
+ two));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> PrimaryExpression()
+ * f1 -> "<"
+ * f2 -> PrimaryExpression()
+ */
+ // Expressions return a TYPE alias which is equal to the expression!
+ public String visit(CompareExpression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ _ret += this.tf.alias(this.getUniqueID());
+ ///////////////////////////////////////////////////////////////
+ String oper1 = this.memoryRead(n.f0.accept(this, argu));
+ String oper2 = this.memoryRead(n.f2.accept(this, argu));
+ this.addVapor(String.format(" %s = LtS(%s %s)\n",
+ _ret,
+ oper1,
+ oper2));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> PrimaryExpression()
+ * f1 -> "+"
+ * f2 -> PrimaryExpression()
+ */
+ // Expressions return a TYPE alias which is equal to the expression!
+ public String visit(PlusExpression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ _ret += this.tf.alias(this.getUniqueID());
+ ///////////////////////////////////////////////////////////////
+ String oper1 = this.memoryRead(n.f0.accept(this, argu));
+ String oper2 = this.memoryRead(n.f2.accept(this, argu));
+ this.addVapor(String.format(" %s = Add(%s %s)\n",
+ _ret,
+ oper1,
+ oper2));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> PrimaryExpression()
+ * f1 -> "-"
+ * f2 -> PrimaryExpression()
+ */
+ // Expressions return a TYPE alias which is equal to the expression!
+ public String visit(MinusExpression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ _ret += this.tf.alias(this.getUniqueID());
+ ///////////////////////////////////////////////////////////////
+ String oper1 = this.memoryRead(n.f0.accept(this, argu));
+ String oper2 = this.memoryRead(n.f2.accept(this, argu));
+ this.addVapor(String.format(" %s = Sub(%s %s)\n",
+ _ret,
+ oper1,
+ oper2));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> PrimaryExpression()
+ * f1 -> "*"
+ * f2 -> PrimaryExpression()
+ */
+ // Expressions return a TYPE alias which is equal to the expression!
+ public String visit(TimesExpression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ _ret += this.tf.alias(this.getUniqueID());
+ ///////////////////////////////////////////////////////////////
+ String oper1 = this.memoryRead(n.f0.accept(this, argu));
+ String oper2 = this.memoryRead(n.f2.accept(this, argu));
+ this.addVapor(String.format(" %s = MulS(%s %s)\n",
+ _ret,
+ oper1,
+ oper2));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> PrimaryExpression()
+ * f1 -> "["
+ * f2 -> PrimaryExpression()
+ * f3 -> "]"
+ */
+ // Expressions return a TYPE alias which is equal to the expression!
+ public String visit(ArrayLookup n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ _ret += this.tf.alias(this.getUniqueID());
+ ///////////////////////////////////////////////////////////////
+ String arrID = this.tf.alias(this.getUniqueID());
+ String arr = n.f0.accept(this, argu);
+ String indexID = this.tf.alias(this.getUniqueID());
+ this.addVapor(String.format(" %s = %s\n",
+ arrID,
+ arr));
+ this.addVapor(String.format(" %s = MulS(%s %s)\n",
+ indexID,
+ n.f2.accept(this, argu),
+ 4));
+ this.addVapor(String.format(" %s = Add(%s %s)\n",
+ indexID,
+ indexID,
+ 4));
+ this.addVapor(String.format(" %s = Add(%s %s)\n",
+ indexID,
+ arrID,
+ indexID));
+ this.addVapor(String.format(" %s = [%s]\n",
+ _ret,
+ indexID));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> PrimaryExpression()
+ * f1 -> "."
+ * f2 -> "length"
+ */
+ // Expressions return a TYPE alias which is equal to the expression!
+ public String visit(ArrayLength n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ _ret += this.tf.alias(this.getUniqueID());
+ ///////////////////////////////////////////////////////////////
+ String arrID = this.tf.alias(this.getUniqueID());
+ String arr = n.f0.accept(this, argu);
+ this.addVapor(String.format(" %s = %s\n",
+ arrID,
+ arr));
+ this.addVapor(String.format(" %s = [%s+0]\n",
+ _ret,
+ arrID));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> PrimaryExpression()
+ * f1 -> "."
+ * f2 -> Identifier()
+ * f3 -> "("
+ * f4 -> ( ExpressionList() )?
+ * f5 -> ")"
+ */
+ // Expressions return a TYPE alias which is equal to the expression!
+ public String visit(MessageSend n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += this.tf.alias(this.getUniqueID());
+ String mtd = n.f2.f0.tokenImage;
+ String rhs;
+ TypeInstance t;
+ switch (n.f0.f0.which) {
+ case 3:
+ MinimalLogger.info("Message send found an IDENTIFIER");
+ rhs = ((Identifier) n.f0.f0.choice).f0.tokenImage;
+ t = this.symt.getType(rhs);
+ if (t == null)
+ t = this.symt.getTypeAttr(rhs);
+ rhs = n.f0.accept(this, argu);
+ this.addVapor(String.format(" %s = %s\n",
+ this.tf.alias(t.getName()),
+ rhs));
+ break;
+ case 4:
+ // we'll do everything here and exit the function
+ MinimalLogger.info("Message send found THIS");
+ rhs = n.f0.accept(this, argu);
+ rhs = this.tf.alias(this.getUniqueID());
+ this.addVapor(String.format(" %s = [this]\n",
+ rhs));
+ ClassInstance cur = (ClassInstance) this.symt.getActive(TypeEnum.classname);
+ MinimalLogger.info("Calculating method index to call...");
+ int mtdIndex = cur.getMethods()
+ .indexOf(this.symt.getMethod(mtd, cur)) * 4;
+
+ this.addVapor(n.f4.accept(this, argu));
+ this.addVapor(String.format(" %s = [%s+%d]\n",
+ rhs,
+ rhs,
+ mtdIndex));
+ this.addVapor(String.format(" %s = call %s(this",
+ _ret,
+ rhs));
+ this.addVapor(String.format(" %s)\n",
+ this.tf.retrieveRecentList(this.symt.getMethod(mtd, cur)
+ .getArguments()
+ .size())));
+ this.recentMethod = this.symt.getMethod(mtd, cur);
+ return _ret;
+ case 6:
+ MinimalLogger.info("Message send found ANONYMOUS");
+ // expand the entire object out!
+ rhs = n.f0.accept(this, argu);
+ t = new TypeInstance(rhs, TypeEnum.ERROR,
+ (MethodInstance) this.symt.getActive(TypeEnum.method),
+ (ClassInstance) this.symt.getActive(TypeEnum.classname));
+ t.addClassInstance(this.recentClass);
+ this.addVapor(String.format(" %s = %s\n",
+ this.tf.alias(t.getName()),
+ rhs));
+ break;
+ case 8:
+ MinimalLogger.info("Message send found BRACKET");
+ rhs = n.f0.accept(this, argu);
+ ClassInstance cls = this.recentMethod.getReturn();
+ t = new TypeInstance(this.getUniqueID(), TypeEnum.ERROR,
+ (MethodInstance) this.symt.getActive(TypeEnum.method),
+ (ClassInstance) this.symt.getActive(TypeEnum.classname));
+ this.addVapor(String.format(" %s = %s\n",
+ this.tf.alias(t.getName()),
+ rhs));
+ t.addClassInstance(cls);
+ break;
+ default:
+ MinimalLogger.severe(String.format("Message send found UNKNOWN %s",
+ n.f0.f0.choice.toString()));
+ rhs = null;
+ t = null;
+ }
+
+ String tp1 = this.tf.alias(this.getUniqueID());
+ String tp2 = this.tf.alias(this.getUniqueID());
+
+ this.addVapor(String.format(" %s = [%s+%d]\n",
+ tp1,
+ this.tf.alias(t.getName()),
+ 0));
+
+ MinimalLogger.info("Calculating method index to call...");
+ MinimalLogger.severe("t: " + t);
+ MinimalLogger.severe("mtd: " + mtd);
+ MinimalLogger.severe("t.getClassInstance() " + t.getClassInstance());
+ MinimalLogger.severe("t.getClassInstance().getMethods() " + t.getClassInstance().getMethods().toString());
+ this.recentMethod = this.symt.getMethod(mtd, t.getClassInstance());
+ int mtdIndex = t.getClassInstance().getMethods()
+ .indexOf(this.symt.getMethod(mtd, t.getClassInstance())) * 4;
+
+ this.addVapor(String.format(" %s = [%s+%d]\n",
+ tp2,
+ tp1,
+ mtdIndex));
+
+ this.addVapor(n.f4.accept(this, argu));
+
+ this.addVapor(String.format(" %s = call %s(%s",
+ _ret,
+ tp2,
+ this.tf.alias(t.getName())));
+
+ this.addVapor(String.format(" %s)\n",
+ this.tf.retrieveRecentList(this.symt.getMethod(mtd, t.getClassInstance())
+ .getArguments()
+ .size())));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> Expression()
+ * f1 -> ( ExpressionRest() )*
+ */
+ public String visit(ExpressionList n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ String rhs = n.f0.accept(this, argu);
+ _ret += String.format(" %s = %s\n",
+ this.tf.alias(this.getUniqueID()),
+ rhs);
+ _ret += n.f1.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> ","
+ * f1 -> Expression()
+ */
+ public String visit(ExpressionRest n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ String rhs = n.f1.accept(this, argu);
+ _ret += String.format(" %s = %s\n",
+ this.tf.alias(this.getUniqueID()),
+ rhs);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> IntegerLiteral()
+ * | TrueLiteral()
+ * | FalseLiteral()
+ * | Identifier()
+ * | ThisExpression()
+ * | ArrayAllocationExpression()
+ * | AllocationExpression()
+ * | NotExpression()
+ * | BracketExpression()
+ */
+ public String visit(PrimaryExpression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += n.f0.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> <INTEGER_LITERAL>
+ */
+ public String visit(IntegerLiteral n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += n.f0.tokenImage;
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "true"
+ */
+ public String visit(TrueLiteral n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += "1";
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "false"
+ */
+ public String visit(FalseLiteral n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += "0";
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> <IDENTIFIER>
+ */
+ public String visit(Identifier n, String argu) {
+ String _ret="";
+ String id = n.f0.tokenImage;
+ MinimalLogger.info(String.format("-> %s (%s)",
+ n.getClass().getSimpleName(),
+ id));
+ ///////////////////////////////////////////////////////////////
+ ClassInstance cur = (ClassInstance) this.symt.getActive(TypeEnum.classname);
+ // TypeInstance localt = this.symt.getType(id);
+ TypeInstance t = this.symt.getTypeAttr(id);
+ if (cur.getLocals().contains(t)) {
+ MinimalLogger.info(String.format("Identifier found a class variable %s",
+ id));
+ int attr_index = getVarIndex(cur, t);
+ _ret += String.format("[this+%d]", attr_index);
+ } else {
+ _ret += this.tf.alias(id);
+ }
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s (%s) with %s",
+ n.getClass().getSimpleName(),
+ id,
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "this"
+ */
+ public String visit(ThisExpression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += "this";
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "new"
+ * f1 -> "int"
+ * f2 -> "["
+ * f3 -> Expression()
+ * f4 -> "]"
+ */
+ public String visit(ArrayAllocationExpression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ String len = n.f3.accept(this, argu);
+ String aAllocID = this.tf.alias(this.getUniqueID());
+ this.addVapor(String.format(" %s = call :AllocArray(%s)\n",
+ aAllocID,
+ len));
+
+ _ret += aAllocID;
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "new"
+ * f1 -> Identifier()
+ * f2 -> "("
+ * f3 -> ")"
+ */
+ public String visit(AllocationExpression n, String argu) {
+ String _ret="";
+ String id = n.f1.f0.tokenImage;
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ _ret += this.tf.alias(this.getUniqueID());
+ ///////////////////////////////////////////////////////////////
+ ClassInstance cls = this.symt.getClass(id);
+ this.recentClass = cls;
+ this.addVapor(String.format(" %s = HeapAllocZ(%d)\n",
+ _ret,
+ cls.getSize()));
+
+ this.addVapor(String.format(" [%s+0] = :functable_%s\n",
+ _ret,
+ id));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "!"
+ * f1 -> Expression()
+ */
+ public String visit(NotExpression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ _ret += this.tf.alias(this.getUniqueID());
+ ///////////////////////////////////////////////////////////////
+ this.addVapor(String.format(" %s = Eq(%s 0)\n",
+ _ret,
+ n.f1.accept(this, argu)));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+ /**
+ * f0 -> "("
+ * f1 -> Expression()
+ * f2 -> ")"
+ */
+ public String visit(BracketExpression n, String argu) {
+ String _ret="";
+ MinimalLogger.info(String.format("-> %s",
+ n.getClass().getSimpleName()));
+ ///////////////////////////////////////////////////////////////
+ _ret += n.f1.accept(this, argu);
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<- %s with %s",
+ n.getClass().getSimpleName(),
+ _ret));
+ return _ret;
+ }
+
+}