summaryrefslogtreecommitdiff
path: root/vaporize/VaporizeVisitor.java
diff options
context:
space:
mode:
Diffstat (limited to 'vaporize/VaporizeVisitor.java')
-rw-r--r--vaporize/VaporizeVisitor.java271
1 files changed, 271 insertions, 0 deletions
diff --git a/vaporize/VaporizeVisitor.java b/vaporize/VaporizeVisitor.java
new file mode 100644
index 0000000..3562887
--- /dev/null
+++ b/vaporize/VaporizeVisitor.java
@@ -0,0 +1,271 @@
+package vaporize;
+
+import cs132.vapor.ast.*;
+import misc.*;
+
+import java.util.*;
+
+public class VaporizeVisitor extends VInstr.VisitorP<LIRDict, RuntimeException> {
+
+ private ArrayList<String> vaporm;
+
+ String[] callee_save = new String[] { "$s0", "$s1", "$s2", "$s3", "$s4", "$s5", "$s6", "$s7" };
+ String[] caller_save = new String[] { "$t0", "$t1", "$t2", "$t3", "$t4", "$t5", "$t6", "$t7", "$t8" };
+ String[] arg_pass = new String[] { "$a0", "$a1", "$a2", "$a3" };
+ String[] ret_pass = new String[] { "$v0" };
+
+ public VaporizeVisitor(VaporProgram vp, ArrayList<String> vaporm, ArrayList<LIRDict> interval_list) {
+ this.vaporm = vaporm;
+
+ // is it possible for interval_list and the
+ // function in vp to be out of order?
+ for (int i = 0; i < vp.functions.length; ++i) {
+ this.addVaporm(String.format("func %s [in %d, out %d, local %d]",
+ vp.functions[i].ident, 0, 0, interval_list.get(i).getSpilledNum() + 17));
+ for (int j = 0; j < this.callee_save.length; ++j) {
+ this.addVaporm(String.format(" local[%s] = %s",
+ j,
+ this.callee_save[j]));
+ }
+
+ for (int j = 0; j < vp.functions[i].params.length; ++j)
+ this.addVaporm(String.format(" %s = %s",
+ interval_list.get(i).getInterval(vp.functions[i].params[j].toString())
+ .getAssignedRegister(),
+ arg_pass[j]));
+
+
+ TreeSet<Node> f = this.sortFunction(vp.functions[i]);
+ MinimalLogger.info(String.format("Starting loop with function:\n %s",
+ f.toString()));
+
+ for (Node n : f) {
+ if (n instanceof VInstr)
+ ((VInstr) n).accept(interval_list.get(i), this);
+ else
+ this.addVaporm(((VCodeLabel) n).ident + ":");
+ }
+ }
+ }
+
+ public TreeSet<Node> sortFunction(VFunction f) {
+ TreeSet<Node> sort = new TreeSet<Node>((v1, v2) -> {
+ return Integer.compare(v1.sourcePos.line, v2.sourcePos.line);
+ });
+
+ for (VInstr s : f.body) {
+ sort.add(s);
+ }
+ for (VCodeLabel l : f.labels) {
+ sort.add(l);
+ }
+ return sort;
+ }
+
+ public ArrayList<String> getVaporm() {
+ return this.vaporm;
+ }
+
+ public void addVaporm(String str) {
+ MinimalLogger.info(String.format("Adding string:\n%s",
+ str));
+ this.vaporm.add(str);
+ }
+
+ public void visit(LIRDict d, VAssign n) throws RuntimeException {
+ MinimalLogger.info(String.format("->%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ ///////////////////////////////////////////////////////////////
+ String dest = d.getInterval(((VVarRef.Local) n.dest).ident).getAssignedRegister();
+ String source = (n.source instanceof VVarRef.Local) ?
+ d.getInterval(n.source.toString()).getAssignedRegister()
+ : n.source.toString();
+ this.addVaporm(String.format(" %s = %s",
+ dest, source));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<-%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ }
+
+ public void visit(LIRDict d, VCall n) throws RuntimeException {
+ MinimalLogger.info(String.format("->%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ ///////////////////////////////////////////////////////////////
+
+ for (int i = 0; i < this.caller_save.length; ++i) {
+ this.addVaporm(String.format(" local[%s] = %s",
+ i+8,
+ this.caller_save[i]));
+ }
+
+ // FIXME for arg num > 4!
+ for (int i = 0; i < n.args.length; ++i) {
+ String reg = (n.args[i] instanceof VVarRef.Local) ?
+ d.getInterval(n.args[i].toString()).getAssignedRegister()
+ : n.args[i].toString();
+ MinimalLogger.info(String.format("Adding argument for %s",
+ n.args[i].toString));
+ this.addVaporm(String.format(" %s = %s",
+ this.arg_pass[i],
+ reg));
+ }
+
+ this.addVaporm(String.format(" call %s",
+ d.getInterval(n.addr.toString())
+ .getAssignedRegister()));
+ // get dest
+ if (n.dest != null) {
+ this.addVaporm(String.format(" %s = $v0",
+ d.getInterval(((VVarRef.Local) n.dest).ident)
+ .getAssignedRegister()));
+ }
+
+ for (int i = 0; i < this.caller_save.length; ++i) {
+ this.addVaporm(String.format(" %s = local[%s]",
+ this.caller_save[i],
+ i+8));
+ }
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<-%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ }
+
+ public void visit(LIRDict d, VBuiltIn n) throws RuntimeException {
+ MinimalLogger.info(String.format("->%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ ///////////////////////////////////////////////////////////////
+ String ret = "";
+ if (n.dest != null) {
+ ret += String.format("%s = ",
+ d.getInterval(((VVarRef.Local) n.dest).ident)
+ .getAssignedRegister());
+ }
+ ret += String.format("%s(",
+ ((VBuiltIn.Op) n.op).name);
+
+ String par;
+ for (VOperand a : n.args) {
+ par = (a instanceof VVarRef.Local) ?
+ d.getInterval(a.toString()).getAssignedRegister()
+ : a.toString();
+ ret += String.format("%s ",
+ par);
+ }
+
+ ret += ")";
+
+ this.addVaporm(String.format(" %s",
+ ret));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<-%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ }
+
+ public void visit(LIRDict d, VMemWrite n) throws RuntimeException {
+ MinimalLogger.info(String.format("->%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ ///////////////////////////////////////////////////////////////
+ String dest = d.getInterval(((VMemRef.Global) n.dest).base.toString())
+ .getAssignedRegister();
+ String source = (n.source instanceof VVarRef.Local) ?
+ d.getInterval(n.source.toString()).getAssignedRegister() :
+ n.source.toString();
+ int byteOffset = ((VMemRef.Global) n.dest).byteOffset;
+ this.addVaporm(String.format(" [%s+%d] = %s",
+ dest, byteOffset, source));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<-%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ }
+
+ public void visit(LIRDict d, VMemRead n) throws RuntimeException {
+ MinimalLogger.info(String.format("->%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ ///////////////////////////////////////////////////////////////
+ String dest = (n.dest instanceof VVarRef.Local) ?
+ d.getInterval(n.dest.toString()).getAssignedRegister() :
+ n.dest.toString();
+ String source = d.getInterval(((VMemRef.Global) n.source).base.toString())
+ .getAssignedRegister();
+ int byteOffset = ((VMemRef.Global) n.source).byteOffset;
+ this.addVaporm(String.format(" %s = [%s+%d]",
+ dest, source, byteOffset));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<-%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ }
+
+ public void visit(LIRDict d, VBranch n) throws RuntimeException {
+ MinimalLogger.info(String.format("->%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ ///////////////////////////////////////////////////////////////
+ String ret = " ";
+ if (n.positive)
+ ret += "if ";
+ else
+ ret += "if0 ";
+
+ ret += d.getInterval(n.value.toString())
+ .getAssignedRegister() + " goto :";
+
+ ret += n.target.ident;
+
+ this.addVaporm(String.format("%s",
+ ret));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<-%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ }
+
+ public void visit(LIRDict d, VGoto n) throws RuntimeException {
+ MinimalLogger.info(String.format("->%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ ///////////////////////////////////////////////////////////////
+ this.addVaporm(String.format(" goto :%s",
+ (((VAddr.Label) n.target).label).ident));
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<-%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ }
+
+ public void visit(LIRDict d, VReturn n) throws RuntimeException {
+ MinimalLogger.info(String.format("->%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ ///////////////////////////////////////////////////////////////
+ // get ret
+ if (n.value != null) {
+ String reg = (n.value instanceof VVarRef.Local) ?
+ d.getInterval(n.value.toString()).getAssignedRegister() :
+ n.value.toString();
+ this.addVaporm(String.format(" $v0 = %s",
+ d.getInterval(((VVarRef.Local) n.value).ident)
+ .getAssignedRegister()));
+ }
+ for (int j = 0; j < this.callee_save.length; ++j) {
+ this.addVaporm(String.format(" %s = local[%s]",
+ this.callee_save[j],
+ j));
+ }
+ this.addVaporm(" ret");
+ ///////////////////////////////////////////////////////////////
+ MinimalLogger.info(String.format("<-%s (%s)",
+ n.getClass().getSimpleName(),
+ n.sourcePos.toString()));
+ }
+
+}