-package org.simantics.graph.compiler.internal.translation;\r
-\r
-import java.util.Collection;\r
-\r
-import org.antlr.runtime.tree.Tree;\r
-import org.simantics.databoard.Bindings;\r
-import org.simantics.databoard.binding.ArrayBinding;\r
-import org.simantics.databoard.binding.Binding;\r
-import org.simantics.databoard.binding.BooleanBinding;\r
-import org.simantics.databoard.binding.ByteBinding;\r
-import org.simantics.databoard.binding.DoubleBinding;\r
-import org.simantics.databoard.binding.FloatBinding;\r
-import org.simantics.databoard.binding.IntegerBinding;\r
-import org.simantics.databoard.binding.LongBinding;\r
-import org.simantics.databoard.binding.MapBinding;\r
-import org.simantics.databoard.binding.OptionalBinding;\r
-import org.simantics.databoard.binding.RecordBinding;\r
-import org.simantics.databoard.binding.StringBinding;\r
-import org.simantics.databoard.binding.UnionBinding;\r
-import org.simantics.databoard.binding.VariantBinding;\r
-import org.simantics.databoard.binding.error.BindingException;\r
-import org.simantics.databoard.type.Datatype;\r
-import org.simantics.graph.compiler.internal.parsing.GraphParser;\r
-import org.simantics.ltk.ISource;\r
-import org.simantics.ltk.Problem;\r
-import org.simantics.ltk.antlr.ANTLRUtils;\r
-\r
-public class DataValueTranslator {\r
- \r
- ISource source;\r
- Collection<Problem> problems;\r
- \r
- public DataValueTranslator(ISource source, Collection<Problem> problems) {\r
- this.source = source;\r
- this.problems = problems;\r
- }\r
-\r
- public Object translate(Tree _tree, Binding binding) {\r
- while(_tree.getType() == GraphParser.TUPLE && \r
- _tree.getChildCount()==1)\r
- _tree = _tree.getChild(0);\r
- final Tree tree = _tree;\r
- return binding.accept(new Binding.Visitor<Object>() {\r
-\r
- @Override\r
- public Object visit(ArrayBinding b) {\r
- if(tree.getType() == GraphParser.ARRAY) {\r
- int count = tree.getChildCount();\r
- Object[] components = new Object[count];\r
- Binding componentBinding = b.getComponentBinding();\r
- for(int i=0;i<count;++i)\r
- components[i] = translate(tree.getChild(i),\r
- componentBinding\r
- );\r
- return b.createUnchecked(components);\r
- }\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
-\r
- @Override\r
- public Object visit(BooleanBinding b) {\r
- if(tree.getType() == GraphParser.TRUE)\r
- return b.createUnchecked(true);\r
- else if(tree.getType() == GraphParser.FALSE)\r
- return b.createUnchecked(false);\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
-\r
- @Override\r
- public Object visit(DoubleBinding b) {\r
- if(tree.getType() == GraphParser.INT || tree.getType() == GraphParser.FLOAT)\r
- return b.createUnchecked(tree.getText());\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
-\r
- @Override\r
- public Object visit(FloatBinding b) {\r
- if(tree.getType() == GraphParser.INT || tree.getType() == GraphParser.FLOAT)\r
- return b.createUnchecked(tree.getText());\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
-\r
- @Override\r
- public Object visit(IntegerBinding b) {\r
- if(tree.getType() == GraphParser.INT)\r
- return b.createUnchecked(tree.getText());\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
-\r
- @Override\r
- public Object visit(ByteBinding b) {\r
- if(tree.getType() == GraphParser.INT)\r
- return b.createUnchecked(tree.getText());\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
-\r
- @Override\r
- public Object visit(LongBinding b) {\r
- if(tree.getType() == GraphParser.INT)\r
- return b.createUnchecked(tree.getText());\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
-\r
- @Override\r
- public Object visit(OptionalBinding b) {\r
- if(tree.getType() == GraphParser.NO_VALUE) \r
- return b.createNoValueUnchecked();\r
- else\r
- return b.createValueUnchecked(\r
- translate(tree, b.getComponentBinding())\r
- );\r
- }\r
-\r
- @Override\r
- public Object visit(RecordBinding b) {\r
- boolean hadError = false;\r
- if(tree.getType() == GraphParser.RECORD) {\r
- int count = tree.getChildCount();\r
- Object[] components = new Object[b.componentBindings.length];\r
- boolean[] setValues = new boolean[b.componentBindings.length];\r
- for(int i=0;i<count;++i) {\r
- Tree assignment = tree.getChild(i);\r
- String field = assignment.getChild(0).getText();\r
- Integer comp = \r
- b.type().getComponentIndex(field);\r
- if(comp == null) {\r
- hadError = true;\r
- problems.add(new Problem(\r
- ANTLRUtils.location(source, tree), \r
- "Record type " + b.type() + " does not have a field " + field + "."\r
- ));\r
- }\r
- else { \r
- components[comp] = translate(\r
- assignment.getChild(1),\r
- b.getComponentBinding(comp)\r
- );\r
- setValues[comp] = true;\r
- }\r
- }\r
- try {\r
- for(int i=0;i<b.componentBindings.length;++i) \r
- if(!setValues[i]) {\r
- if(b.componentBindings[i] instanceof OptionalBinding)\r
- components[i] = b.componentBindings[i].createDefault();\r
- else \r
- problems.add(new Problem(\r
- ANTLRUtils.location(source, tree), \r
- "Not all fields of the record are given."\r
- ));\r
- return b.createDefaultUnchecked();\r
- }\r
- return b.create(components);\r
- } catch(BindingException e) { \r
- }\r
- }\r
- if(tree.getType() == GraphParser.TUPLE) {\r
- int count = tree.getChildCount();\r
- if(count == b.getComponentCount()) { \r
- Object[] components = new Object[count];\r
- for(int i=0;i<count;++i)\r
- components[i] = \r
- translate(tree.getChild(i), \r
- b.getComponentBinding(i));\r
- return b.createUnchecked(components);\r
- }\r
- }\r
- if(!hadError)\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
-\r
- @Override\r
- public Object visit(StringBinding b) {\r
- if(tree.getType() == GraphParser.STRING) {\r
- String str = tree.getText();\r
- if(str.charAt(1) == '"' && str.length() >= 6)\r
- return b.createUnchecked(str.substring(3, str.length()-3));\r
- else\r
- return b.createUnchecked(str.substring(1, str.length()-1));\r
- }\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
-\r
- @Override\r
- public Object visit(UnionBinding b) {\r
- if(tree.getType() == GraphParser.TAGGED_VALUE) {\r
- String tag = tree.getChild(0).getText();\r
- Integer comp = b.type().getComponentIndex(tag);\r
- if(comp != null) {\r
- if(tree.getChildCount() == 2)\r
- return b.createUnchecked(comp, \r
- translate(\r
- tree.getChild(1), \r
- b.getComponentBinding(comp)\r
- ));\r
- else {\r
- Binding binding = b.getComponentBinding(comp);\r
- if(binding instanceof RecordBinding &&\r
- ((RecordBinding)binding).getComponentCount() == 0)\r
- return b.createUnchecked(comp, \r
- ((RecordBinding)binding).createUnchecked());\r
- else\r
- typeError(tree, binding);\r
- }\r
- }\r
- }\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked(); \r
- }\r
-\r
- @Override\r
- public Object visit(VariantBinding b) {\r
- if(tree.getType() == GraphParser.VARIANT) {\r
- Datatype type = \r
- new DataTypeTranslator(source, problems).translate(tree.getChild(0));\r
- Binding binding = Bindings.getBinding(type);\r
- \r
- Object value = translate(tree.getChild(1), binding);\r
- return b.createUnchecked(binding, value);\r
- }\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
-\r
- @Override\r
- public Object visit(MapBinding b) {\r
- if(tree.getType() == GraphParser.MAP) {\r
- int count = tree.getChildCount();\r
- Object[] keys = new Object[count];\r
- Object[] values = new Object[count];\r
- Binding keyBinding = b.getKeyBinding();\r
- Binding valueBinding = b.getValueBinding();\r
- for(int i=0;i<count;++i) {\r
- keys[i] = translate(tree.getChild(i).getChild(0), keyBinding);\r
- values[i] = translate(tree.getChild(i).getChild(1), valueBinding);\r
- }\r
- return b.createUnchecked(keys, values);\r
- }\r
- typeError(tree, b);\r
- return b.createDefaultUnchecked();\r
- }\r
- });\r
- }\r
- \r
- private void typeError(Tree tree, Binding binding) { \r
- problems.add(new Problem(\r
- ANTLRUtils.location(source, tree), \r
- "Value does not correspond to the data type " + binding.type() + "."\r
- ));\r
- }\r
- \r
-}\r
+package org.simantics.graph.compiler.internal.translation;
+
+import java.util.Collection;
+
+import org.antlr.runtime.tree.Tree;
+import org.simantics.databoard.Bindings;
+import org.simantics.databoard.binding.ArrayBinding;
+import org.simantics.databoard.binding.Binding;
+import org.simantics.databoard.binding.BooleanBinding;
+import org.simantics.databoard.binding.ByteBinding;
+import org.simantics.databoard.binding.DoubleBinding;
+import org.simantics.databoard.binding.FloatBinding;
+import org.simantics.databoard.binding.IntegerBinding;
+import org.simantics.databoard.binding.LongBinding;
+import org.simantics.databoard.binding.MapBinding;
+import org.simantics.databoard.binding.OptionalBinding;
+import org.simantics.databoard.binding.RecordBinding;
+import org.simantics.databoard.binding.StringBinding;
+import org.simantics.databoard.binding.UnionBinding;
+import org.simantics.databoard.binding.VariantBinding;
+import org.simantics.databoard.binding.error.BindingException;
+import org.simantics.databoard.type.Datatype;
+import org.simantics.graph.compiler.internal.parsing.GraphParser;
+import org.simantics.ltk.ISource;
+import org.simantics.ltk.Problem;
+import org.simantics.ltk.antlr.ANTLRUtils;
+
+public class DataValueTranslator {
+
+ ISource source;
+ Collection<Problem> problems;
+
+ public DataValueTranslator(ISource source, Collection<Problem> problems) {
+ this.source = source;
+ this.problems = problems;
+ }
+
+ public Object translate(Tree _tree, Binding binding) {
+ while(_tree.getType() == GraphParser.TUPLE &&
+ _tree.getChildCount()==1)
+ _tree = _tree.getChild(0);
+ final Tree tree = _tree;
+ return binding.accept(new Binding.Visitor<Object>() {
+
+ @Override
+ public Object visit(ArrayBinding b) {
+ if(tree.getType() == GraphParser.ARRAY) {
+ int count = tree.getChildCount();
+ Object[] components = new Object[count];
+ Binding componentBinding = b.getComponentBinding();
+ for(int i=0;i<count;++i)
+ components[i] = translate(tree.getChild(i),
+ componentBinding
+ );
+ return b.createUnchecked(components);
+ }
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(BooleanBinding b) {
+ if(tree.getType() == GraphParser.TRUE)
+ return b.createUnchecked(true);
+ else if(tree.getType() == GraphParser.FALSE)
+ return b.createUnchecked(false);
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(DoubleBinding b) {
+ if(tree.getType() == GraphParser.INT || tree.getType() == GraphParser.FLOAT)
+ return b.createUnchecked(tree.getText());
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(FloatBinding b) {
+ if(tree.getType() == GraphParser.INT || tree.getType() == GraphParser.FLOAT)
+ return b.createUnchecked(tree.getText());
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(IntegerBinding b) {
+ if(tree.getType() == GraphParser.INT)
+ return b.createUnchecked(tree.getText());
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(ByteBinding b) {
+ if(tree.getType() == GraphParser.INT)
+ return b.createUnchecked(tree.getText());
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(LongBinding b) {
+ if(tree.getType() == GraphParser.INT)
+ return b.createUnchecked(tree.getText());
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(OptionalBinding b) {
+ if(tree.getType() == GraphParser.NO_VALUE)
+ return b.createNoValueUnchecked();
+ else
+ return b.createValueUnchecked(
+ translate(tree, b.getComponentBinding())
+ );
+ }
+
+ @Override
+ public Object visit(RecordBinding b) {
+ boolean hadError = false;
+ if(tree.getType() == GraphParser.RECORD) {
+ int count = tree.getChildCount();
+ Object[] components = new Object[b.componentBindings.length];
+ boolean[] setValues = new boolean[b.componentBindings.length];
+ for(int i=0;i<count;++i) {
+ Tree assignment = tree.getChild(i);
+ String field = assignment.getChild(0).getText();
+ Integer comp =
+ b.type().getComponentIndex(field);
+ if(comp == null) {
+ hadError = true;
+ problems.add(new Problem(
+ ANTLRUtils.location(source, tree),
+ "Record type " + b.type() + " does not have a field " + field + "."
+ ));
+ }
+ else {
+ components[comp] = translate(
+ assignment.getChild(1),
+ b.getComponentBinding(comp)
+ );
+ setValues[comp] = true;
+ }
+ }
+ try {
+ for(int i=0;i<b.componentBindings.length;++i)
+ if(!setValues[i]) {
+ if(b.componentBindings[i] instanceof OptionalBinding)
+ components[i] = b.componentBindings[i].createDefault();
+ else
+ problems.add(new Problem(
+ ANTLRUtils.location(source, tree),
+ "Not all fields of the record are given."
+ ));
+ return b.createDefaultUnchecked();
+ }
+ return b.create(components);
+ } catch(BindingException e) {
+ }
+ }
+ if(tree.getType() == GraphParser.TUPLE) {
+ int count = tree.getChildCount();
+ if(count == b.getComponentCount()) {
+ Object[] components = new Object[count];
+ for(int i=0;i<count;++i)
+ components[i] =
+ translate(tree.getChild(i),
+ b.getComponentBinding(i));
+ return b.createUnchecked(components);
+ }
+ }
+ if(!hadError)
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(StringBinding b) {
+ if(tree.getType() == GraphParser.STRING) {
+ String str = tree.getText();
+ if(str.charAt(1) == '"' && str.length() >= 6)
+ return b.createUnchecked(str.substring(3, str.length()-3));
+ else
+ return b.createUnchecked(str.substring(1, str.length()-1));
+ }
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(UnionBinding b) {
+ if(tree.getType() == GraphParser.TAGGED_VALUE) {
+ String tag = tree.getChild(0).getText();
+ Integer comp = b.type().getComponentIndex(tag);
+ if(comp != null) {
+ if(tree.getChildCount() == 2)
+ return b.createUnchecked(comp,
+ translate(
+ tree.getChild(1),
+ b.getComponentBinding(comp)
+ ));
+ else {
+ Binding binding = b.getComponentBinding(comp);
+ if(binding instanceof RecordBinding &&
+ ((RecordBinding)binding).getComponentCount() == 0)
+ return b.createUnchecked(comp,
+ ((RecordBinding)binding).createUnchecked());
+ else
+ typeError(tree, binding);
+ }
+ }
+ }
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(VariantBinding b) {
+ if(tree.getType() == GraphParser.VARIANT) {
+ Datatype type =
+ new DataTypeTranslator(source, problems).translate(tree.getChild(0));
+ Binding binding = Bindings.getBinding(type);
+
+ Object value = translate(tree.getChild(1), binding);
+ return b.createUnchecked(binding, value);
+ }
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+
+ @Override
+ public Object visit(MapBinding b) {
+ if(tree.getType() == GraphParser.MAP) {
+ int count = tree.getChildCount();
+ Object[] keys = new Object[count];
+ Object[] values = new Object[count];
+ Binding keyBinding = b.getKeyBinding();
+ Binding valueBinding = b.getValueBinding();
+ for(int i=0;i<count;++i) {
+ keys[i] = translate(tree.getChild(i).getChild(0), keyBinding);
+ values[i] = translate(tree.getChild(i).getChild(1), valueBinding);
+ }
+ return b.createUnchecked(keys, values);
+ }
+ typeError(tree, b);
+ return b.createDefaultUnchecked();
+ }
+ });
+ }
+
+ private void typeError(Tree tree, Binding binding) {
+ problems.add(new Problem(
+ ANTLRUtils.location(source, tree),
+ "Value does not correspond to the data type " + binding.type() + "."
+ ));
+ }
+
+}