-package org.simantics.scl.compiler.internal.codegen.utils;\r
-\r
-import java.util.ArrayDeque;\r
-import java.util.ArrayList;\r
-\r
-import org.simantics.scl.compiler.constants.Constant;\r
-import org.simantics.scl.compiler.internal.codegen.continuations.Cont;\r
-import org.simantics.scl.compiler.internal.codegen.continuations.ContRef;\r
-import org.simantics.scl.compiler.internal.codegen.continuations.ReturnCont;\r
-import org.simantics.scl.compiler.internal.codegen.references.BoundVar;\r
-import org.simantics.scl.compiler.internal.codegen.references.Val;\r
-import org.simantics.scl.compiler.internal.codegen.references.ValRef;\r
-import org.simantics.scl.compiler.internal.codegen.ssa.SSABlock;\r
-import org.simantics.scl.compiler.internal.codegen.ssa.statements.LetApply;\r
-import org.simantics.scl.compiler.types.Type;\r
-import org.simantics.scl.compiler.types.util.TypeUnparsingContext;\r
-\r
-import gnu.trove.map.hash.THashMap;\r
-import gnu.trove.set.hash.THashSet;\r
-\r
-public class PrintingContext {\r
-\r
- THashMap<Object, String> names = new THashMap<Object, String>(); \r
- int nameId = 0;\r
- int indentation = 0;\r
- StringBuilder stringBuilder = new StringBuilder();\r
- TypeUnparsingContext typeUnparsingContext = \r
- new TypeUnparsingContext();\r
- Object errorMarker;\r
- THashMap<BoundVar, LetApply> inlineExpressions = new THashMap<BoundVar, LetApply>(); \r
- \r
- private static class BlockEntry { \r
- ArrayDeque<SSABlock> blockQueue = new ArrayDeque<SSABlock>(); \r
- THashSet<SSABlock> blockSet = new THashSet<SSABlock>();\r
- } \r
- private ArrayList<BlockEntry> blockQueueStack = new ArrayList<BlockEntry>(2); \r
- \r
- public void pushBlockQueue() {\r
- blockQueueStack.add(new BlockEntry());\r
- }\r
- \r
- public void popBlockQueue() {\r
- blockQueueStack.remove(blockQueueStack.size()-1);\r
- }\r
- \r
- public SSABlock pollBlock() {\r
- BlockEntry entry = blockQueueStack.get(blockQueueStack.size()-1);\r
- return entry.blockQueue.poll();\r
- }\r
- \r
- public void addBlock(SSABlock block) {\r
- BlockEntry entry = blockQueueStack.get(blockQueueStack.size()-1);\r
- if(entry.blockSet.add(block))\r
- entry.blockQueue.add(block);\r
- }\r
- \r
- public void append(Constant val) {\r
- append(val.toString());\r
- }\r
- \r
- public void append(ReturnCont val) {\r
- append("return");\r
- }\r
- \r
- public void append(Type type) {\r
- append(type.toString(typeUnparsingContext));\r
- }\r
- \r
- public void append(Type[] types) {\r
- append('[');\r
- boolean first = true;\r
- for(Type type : types) {\r
- if(first)\r
- first = false;\r
- else\r
- append(", ");\r
- append(type);\r
- }\r
- append(']');\r
- }\r
- \r
- public void append(ValRef ref) {\r
- append(ref.getBinding());\r
- if(ref.getTypeParameters().length > 0) {\r
- append("<");\r
- for(int i=0;i<ref.getTypeParameters().length;++i) {\r
- if(i > 0)\r
- append(",");\r
- append(ref.getTypeParameters()[i]);\r
- }\r
- append(">");\r
- }\r
- }\r
- \r
- public void append(Val val) {\r
- if(val instanceof Constant) {\r
- append((Constant)val);\r
- }\r
- else if(val instanceof BoundVar) {\r
- BoundVar var = (BoundVar)val;\r
- \r
- LetApply inlineExpression = inlineExpressions.remove(var);\r
- if(inlineExpression != null) {\r
- append('(');\r
- inlineExpression.bodyToString(this);\r
- append(')');\r
- }\r
- else {\r
- String label = var.getLabel();\r
- if(label == null)\r
- label = getName(val);\r
- append(label);\r
- }\r
- }\r
- else {\r
- append(getName(val));\r
- }\r
- /*append('{');\r
- append(val.getType());\r
- append('}');*/\r
- }\r
-\r
- public void append(ContRef ref) {\r
- append(ref.getBinding());\r
- }\r
- \r
- public void append(Cont cont) {\r
- if(cont instanceof ReturnCont)\r
- append((ReturnCont)cont);\r
- else\r
- append("[" + getName(cont) + "]");\r
- }\r
-\r
- private String getName(Object var) {\r
- if(var == null)\r
- return "NULL";\r
- String name = names.get(var);\r
- if(name == null) {\r
- name = idToName(nameId++);\r
- names.put(var, name);\r
- }\r
- return name;\r
- }\r
-\r
- private static final int alphabetCount = 'z'-'a'+1;\r
- \r
- private static String idToName(int id) {\r
- String name = Character.toString((char)('a' + id % alphabetCount));\r
- id /= alphabetCount;\r
- if(id > 0)\r
- name = idToName(id-1) + name;\r
- return name;\r
- }\r
- \r
- public PrintingContext append(String str) {\r
- stringBuilder.append(str);\r
- return this;\r
- }\r
- \r
- public PrintingContext append(char c) {\r
- stringBuilder.append(c);\r
- return this;\r
- }\r
- \r
- public void indentation() {\r
- for(int i=0;i<indentation;++i)\r
- stringBuilder.append(" ");\r
- }\r
- \r
- @Override\r
- public String toString() {\r
- return stringBuilder.toString();\r
- }\r
-\r
- public void indent() {\r
- ++indentation;\r
- }\r
-\r
- public void dedent() {\r
- --indentation;\r
- }\r
-\r
- public void setErrorMarker(Object errorMarker) {\r
- this.errorMarker = errorMarker; \r
- }\r
- \r
- public Object getErrorMarker() {\r
- return errorMarker;\r
- }\r
-\r
- public void addInlineExpression(BoundVar target, LetApply letApply) {\r
- inlineExpressions.put(target, letApply);\r
- }\r
-\r
-}\r
+package org.simantics.scl.compiler.internal.codegen.utils;
+
+import java.util.ArrayDeque;
+import java.util.ArrayList;
+
+import org.simantics.scl.compiler.constants.Constant;
+import org.simantics.scl.compiler.internal.codegen.continuations.Cont;
+import org.simantics.scl.compiler.internal.codegen.continuations.ContRef;
+import org.simantics.scl.compiler.internal.codegen.continuations.ReturnCont;
+import org.simantics.scl.compiler.internal.codegen.references.BoundVar;
+import org.simantics.scl.compiler.internal.codegen.references.Val;
+import org.simantics.scl.compiler.internal.codegen.references.ValRef;
+import org.simantics.scl.compiler.internal.codegen.ssa.SSABlock;
+import org.simantics.scl.compiler.internal.codegen.ssa.statements.LetApply;
+import org.simantics.scl.compiler.types.Type;
+import org.simantics.scl.compiler.types.util.TypeUnparsingContext;
+
+import gnu.trove.map.hash.THashMap;
+import gnu.trove.set.hash.THashSet;
+
+public class PrintingContext {
+
+ THashMap<Object, String> names = new THashMap<Object, String>();
+ int nameId = 0;
+ int indentation = 0;
+ StringBuilder stringBuilder = new StringBuilder();
+ TypeUnparsingContext typeUnparsingContext =
+ new TypeUnparsingContext();
+ Object errorMarker;
+ THashMap<BoundVar, LetApply> inlineExpressions = new THashMap<BoundVar, LetApply>();
+
+ private static class BlockEntry {
+ ArrayDeque<SSABlock> blockQueue = new ArrayDeque<SSABlock>();
+ THashSet<SSABlock> blockSet = new THashSet<SSABlock>();
+ }
+ private ArrayList<BlockEntry> blockQueueStack = new ArrayList<BlockEntry>(2);
+
+ public void pushBlockQueue() {
+ blockQueueStack.add(new BlockEntry());
+ }
+
+ public void popBlockQueue() {
+ blockQueueStack.remove(blockQueueStack.size()-1);
+ }
+
+ public SSABlock pollBlock() {
+ BlockEntry entry = blockQueueStack.get(blockQueueStack.size()-1);
+ return entry.blockQueue.poll();
+ }
+
+ public void addBlock(SSABlock block) {
+ BlockEntry entry = blockQueueStack.get(blockQueueStack.size()-1);
+ if(entry.blockSet.add(block))
+ entry.blockQueue.add(block);
+ }
+
+ public void append(Constant val) {
+ append(val.toString());
+ }
+
+ public void append(ReturnCont val) {
+ append("return");
+ }
+
+ public void append(Type type) {
+ append(type.toString(typeUnparsingContext));
+ }
+
+ public void append(Type[] types) {
+ append('[');
+ boolean first = true;
+ for(Type type : types) {
+ if(first)
+ first = false;
+ else
+ append(", ");
+ append(type);
+ }
+ append(']');
+ }
+
+ public void append(ValRef ref) {
+ append(ref.getBinding());
+ if(ref.getTypeParameters().length > 0) {
+ append("<");
+ for(int i=0;i<ref.getTypeParameters().length;++i) {
+ if(i > 0)
+ append(",");
+ append(ref.getTypeParameters()[i]);
+ }
+ append(">");
+ }
+ }
+
+ public void append(Val val) {
+ if(val instanceof Constant) {
+ append((Constant)val);
+ }
+ else if(val instanceof BoundVar) {
+ BoundVar var = (BoundVar)val;
+
+ LetApply inlineExpression = inlineExpressions.remove(var);
+ if(inlineExpression != null) {
+ append('(');
+ inlineExpression.bodyToString(this);
+ append(')');
+ }
+ else {
+ String label = var.getLabel();
+ if(label == null)
+ label = getName(val);
+ append(label);
+ }
+ }
+ else {
+ append(getName(val));
+ }
+ /*append('{');
+ append(val.getType());
+ append('}');*/
+ }
+
+ public void append(ContRef ref) {
+ append(ref.getBinding());
+ }
+
+ public void append(Cont cont) {
+ if(cont instanceof ReturnCont)
+ append((ReturnCont)cont);
+ else
+ append("[" + getName(cont) + "]");
+ }
+
+ private String getName(Object var) {
+ if(var == null)
+ return "NULL";
+ String name = names.get(var);
+ if(name == null) {
+ name = idToName(nameId++);
+ names.put(var, name);
+ }
+ return name;
+ }
+
+ private static final int alphabetCount = 'z'-'a'+1;
+
+ private static String idToName(int id) {
+ String name = Character.toString((char)('a' + id % alphabetCount));
+ id /= alphabetCount;
+ if(id > 0)
+ name = idToName(id-1) + name;
+ return name;
+ }
+
+ public PrintingContext append(String str) {
+ stringBuilder.append(str);
+ return this;
+ }
+
+ public PrintingContext append(char c) {
+ stringBuilder.append(c);
+ return this;
+ }
+
+ public void indentation() {
+ for(int i=0;i<indentation;++i)
+ stringBuilder.append(" ");
+ }
+
+ @Override
+ public String toString() {
+ return stringBuilder.toString();
+ }
+
+ public void indent() {
+ ++indentation;
+ }
+
+ public void dedent() {
+ --indentation;
+ }
+
+ public void setErrorMarker(Object errorMarker) {
+ this.errorMarker = errorMarker;
+ }
+
+ public Object getErrorMarker() {
+ return errorMarker;
+ }
+
+ public void addInlineExpression(BoundVar target, LetApply letApply) {
+ inlineExpressions.put(target, letApply);
+ }
+
+}