diff --git a/AlgebraicDataflowArchitectureModel/src/algorithm/CodeGenerator.java b/AlgebraicDataflowArchitectureModel/src/algorithm/CodeGenerator.java index 61cb9b0..56a18ff 100644 --- a/AlgebraicDataflowArchitectureModel/src/algorithm/CodeGenerator.java +++ b/AlgebraicDataflowArchitectureModel/src/algorithm/CodeGenerator.java @@ -3,16 +3,195 @@ import java.util.ArrayList; import models.*; +import models.algebra.Expression; +import models.algebra.Field; +import models.algebra.InvalidMessage; +import models.algebra.Parameter; +import models.algebra.ParameterizedIdentifierIsFutureWork; +import models.algebra.Symbol; +import models.algebra.Term; +import models.algebra.Type; +import models.algebra.UnificationFailed; +import models.algebra.ValueUndefined; +import models.dataConstraintModel.ChannelMember; +import models.dataConstraintModel.DataConstraintModel; +import models.dataConstraintModel.IdentifierTemplate; import models.dataFlowModel.*; +import models.dataFlowModel.DataflowChannelGenerator.IResourceStateAccessor; public class CodeGenerator { - static public ArrayList doGenerate(ResourceDependencyGraph graph){ + static public ArrayList doGenerate(ResourceDependencyGraph graph) { ArrayList codes = new ArrayList<>(); - for(Node n:graph.getNodes()) { + IResourceStateAccessor pushAccessor = new IResourceStateAccessor() { + @Override + public Expression getCurrentStateAccessorFor(IdentifierTemplate target, IdentifierTemplate from) { + if (target.equals(from)) { + return new Field(target.getResourceName(), target.getResourceStateType() != null ? target.getResourceStateType() : DataConstraintModel.typeInt); + } + return null; + } + + @Override + public Expression getNextStateAccessorFor(IdentifierTemplate target, IdentifierTemplate from) { + return new Parameter(target.getResourceName(), target.getResourceStateType() != null ? target.getResourceStateType() : DataConstraintModel.typeInt); + } + }; + IResourceStateAccessor pullAccessor = new IResourceStateAccessor() { + @Override + public Expression getCurrentStateAccessorFor(IdentifierTemplate target, IdentifierTemplate from) { + if (target.equals(from)) { + return new Field(target.getResourceName(), target.getResourceStateType() != null ? target.getResourceStateType() : DataConstraintModel.typeInt); + } + return null; + } + + @Override + public Expression getNextStateAccessorFor(IdentifierTemplate target, IdentifierTemplate from) { + Term getter = new Term(new Symbol("get" + target.getResourceName(), 1, Symbol.Type.METHOD)); + getter.addChild(new Field(target.getResourceName(), target.getResourceStateType())); + return getter; + } + }; + codes.add("public class Main {"); + for (Node n : graph.getNodes()) { ResourceNode resource = (ResourceNode) n; - codes.add("public class " + resource.getIdentifierTemplate().getResourceName() + " {"); - ((StoreAttribute) resource.getAttribute()).isStored(); + String str = "\t" + "private " + + resource.getIdentifierTemplate().getResourceName().substring(0, 1).toUpperCase() + + resource.getIdentifierTemplate().getResourceName().substring(1) + " " + + resource.getIdentifierTemplate().getResourceName() + " = new " + + resource.getIdentifierTemplate().getResourceName().substring(0, 1).toUpperCase() + + resource.getIdentifierTemplate().getResourceName().substring(1) + "("; + + str += ");"; + codes.add(str); + } + codes.add("}"); + codes.add(""); + for (Node n : graph.getNodes()) { + ResourceNode resource = (ResourceNode) n; + String tmp; + codes.add("public class " + resource.getIdentifierTemplate().getResourceName().substring(0, 1).toUpperCase() + + resource.getIdentifierTemplate().getResourceName().substring(1) + " {"); + if (((StoreAttribute) resource.getAttribute()).isStored()) { + for (Edge e : resource.getInEdges()) { + ResourceDependency re = (ResourceDependency) e; + for(ChannelMember cm:re.getChannelGenerator().getChannelMembers()) { + try { + Expression exp = re.getChannelGenerator().deriveUpdateExpressionOf(cm, pushAccessor); + if(exp != null) { + Parameter param = exp.getSubTerms(Parameter.class).values().iterator().next(); + codes.add("\t" + "void update(" + param.getType().getImplementastionTypeName() + " " + param.toImplementation() + "){"); + tmp = "\t\t" + exp.toImplementation(); + codes.add(tmp); + codes.add("\t" + "}"); + } + } catch (ParameterizedIdentifierIsFutureWork e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (ResolvingMultipleDefinitionIsFutureWork e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (InvalidMessage e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (UnificationFailed e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (ValueUndefined e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } + } + } + for (Edge e : resource.getOutEdges()) { + ResourceDependency re = (ResourceDependency) e; + for(ChannelMember cm:re.getChannelGenerator().getChannelMembers()) { + try { + Expression exp = re.getChannelGenerator().deriveUpdateExpressionOf(cm, pushAccessor); + if(exp != null) { + Parameter param = exp.getSubTerms(Parameter.class).values().iterator().next(); + codes.add("\t" + "void update(" + param.getType().getImplementastionTypeName() + " " + param.toImplementation() + "){"); + tmp = "\t\t" + exp.toImplementation(); + codes.add(tmp); + codes.add("\t" + "}"); + } + } catch (ParameterizedIdentifierIsFutureWork e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (ResolvingMultipleDefinitionIsFutureWork e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (InvalidMessage e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (UnificationFailed e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (ValueUndefined e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } + } + } + } else { + for (Edge e : resource.getInEdges()) { + ResourceDependency re = (ResourceDependency) e; + for(ChannelMember cm:re.getChannelGenerator().getChannelMembers()) { + try { + Expression exp = re.getChannelGenerator().deriveUpdateExpressionOf(cm, pullAccessor); + if(exp != null) { + tmp = "\t" + "return " + exp.toImplementation(); + codes.add(tmp); + } + } catch (ParameterizedIdentifierIsFutureWork e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (ResolvingMultipleDefinitionIsFutureWork e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (InvalidMessage e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (UnificationFailed e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (ValueUndefined e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } + } + } + for (Edge e : resource.getOutEdges()) { + ResourceDependency re = (ResourceDependency) e; + for(ChannelMember cm:re.getChannelGenerator().getChannelMembers()) { + try { + Expression exp = re.getChannelGenerator().deriveUpdateExpressionOf(cm, pullAccessor); + if(exp != null) { + tmp = "\t" + "return " + exp.toImplementation(); + tmp = "\t" + exp.toImplementation(); + codes.add(tmp); + } + } catch (ParameterizedIdentifierIsFutureWork e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (ResolvingMultipleDefinitionIsFutureWork e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (InvalidMessage e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (UnificationFailed e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } catch (ValueUndefined e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } + } + } + } codes.add("}"); + codes.add(""); } return codes; } diff --git a/AlgebraicDataflowArchitectureModel/src/algorithm/EdgeTransitionSelectable.java b/AlgebraicDataflowArchitectureModel/src/algorithm/EdgeTransitionSelectable.java index d9268a0..8e9b51a 100644 --- a/AlgebraicDataflowArchitectureModel/src/algorithm/EdgeTransitionSelectable.java +++ b/AlgebraicDataflowArchitectureModel/src/algorithm/EdgeTransitionSelectable.java @@ -23,12 +23,15 @@ static private void trackEdges(Node n) { PushPullAttribute ppat = new PushPullAttribute(); - ppat.addOption(PushPullValue.PUSH); + ppat.addOption(PushPullValue.PUSH);/* for (Node pre : n.getPredecessors()) { for (Edge in : n.getInEdges()) { ((ResourceDependency) in).setAttribute(ppat); } trackEdges(pre); + }*/ + for(Edge e:((ResourceNode) n).getInEdges()) { + ((ResourceDependency) e).setAttribute(ppat); } } } diff --git a/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/PrototypeGenerateAction.java b/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/PrototypeGenerateAction.java index fe859cd..956f4b6 100644 --- a/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/PrototypeGenerateAction.java +++ b/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/actions/PrototypeGenerateAction.java @@ -2,7 +2,10 @@ import java.awt.event.ActionEvent; +import algorithm.CodeGenerator; +import algorithm.DataStorageDecision; import graphicalrefactor.editor.Editor; +import models.dataFlowModel.ResourceDependencyGraph; public class PrototypeGenerateAction extends AbstractEditorAction { /** @@ -16,6 +19,12 @@ @Override public void actionPerformed(ActionEvent e) { + ResourceDependencyGraph graph = editor.getResourceGraph(); + DataStorageDecision.run(graph); + editor.setCodes(CodeGenerator.doGenerate(graph)); + for(String str:editor.getCodes()) { + System.out.println(str); + } } } diff --git a/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/editor/Editor.java b/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/editor/Editor.java index 39f8a41..229b19e 100644 --- a/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/editor/Editor.java +++ b/AlgebraicDataflowArchitectureModel/src/graphicalrefactor/editor/Editor.java @@ -4,6 +4,7 @@ import java.io.File; import java.io.FileNotFoundException; import java.io.FileReader; +import java.util.ArrayList; import java.util.HashMap; import com.mxgraph.layout.mxCircleLayout; @@ -17,6 +18,9 @@ import com.mxgraph.util.mxPoint; import com.mxgraph.view.mxGraph; +import algorithm.DataStorageNecessity; +import algorithm.EdgeTransitionSelectable; +import algorithm.UpdateConflictCheck; import models.Edge; import models.Node; import models.dataFlowModel.DataFlowModel; @@ -41,10 +45,12 @@ public class Editor { final int PORT_DIAMETER = 8; final int PORT_RADIUS = PORT_DIAMETER / 2; - + private mxGraph graph = null; - private DataFlowModel model = null; - private ResourceDependencyGraph resourceDependencyGraph = null; + private DataFlowModel model = null; + private ResourceDependencyGraph resourceGraph = null; + + private ArrayList codes = null; public Editor(mxGraph graph) { this.graph = graph; @@ -65,13 +71,21 @@ public void setModel(DataFlowModel model) { this.model = model; } - - public ResourceDependencyGraph getResourceDependencyGraph() { - return resourceDependencyGraph; + + public ResourceDependencyGraph getResourceGraph() { + return resourceGraph; } - public void setResourceDependencyGraph(ResourceDependencyGraph resourceDependencyGraph) { - this.resourceDependencyGraph = resourceDependencyGraph; + public void setResourceGraph(ResourceDependencyGraph resourceGraph) { + this.resourceGraph = resourceGraph; + } + + public ArrayList getCodes() { + return codes; + } + + public void setCodes(ArrayList codes) { + this.codes = codes; } public DataFlowModel open(File file) { @@ -79,7 +93,7 @@ Parser parser = new Parser(new BufferedReader(new FileReader(file))); try { model = parser.doParse(); - + if(!UpdateConflictCheck.run(model)) return null; graph = constructGraph(model); return model; } catch (ExpectedChannel | ExpectedChannelName | ExpectedLeftCurlyBracket | ExpectedInOrOutKeyword @@ -93,8 +107,9 @@ return null; } - public mxGraph constructGraph(DataFlowModel model) { - resourceDependencyGraph = model.getResourceDependencyGraph(); + public mxGraph constructGraph(DataFlowModel model) { + ResourceDependencyGraph resourceDependencyGraph = DataStorageNecessity.run(model); + EdgeTransitionSelectable.run(resourceDependencyGraph); ((mxGraphModel) graph.getModel()).clear(); Object parent = graph.getDefaultParent(); @@ -103,21 +118,26 @@ mxGeometry geo1 = new mxGeometry(0, 0.5, PORT_DIAMETER, PORT_DIAMETER); geo1.setOffset(new mxPoint(-PORT_RADIUS, -PORT_RADIUS)); geo1.setRelative(true); - + mxGeometry geo2 = new mxGeometry(1.0, 0.5, PORT_DIAMETER, PORT_DIAMETER); geo2.setOffset(new mxPoint(-PORT_RADIUS, -PORT_RADIUS)); geo2.setRelative(true); - + HashMap channelsIn = new HashMap<>(); HashMap channelsOut = new HashMap<>(); HashMap resources = new HashMap<>(); - - for (Edge e: resourceDependencyGraph.getEdges()) { + + for (Edge e : resourceDependencyGraph.getEdges()) { if (e instanceof ResourceDependency) { ResourceDependency dependency = (ResourceDependency) e; DataflowChannelGenerator channelGen = dependency.getChannelGenerator(); - if (channelsIn.get(channelGen) == null || channelsOut.get(channelGen) == null) { - Object channel = graph.insertVertex(parent, null, channelGen.getChannelName(), 150, 20, 30, 30); // insert a channel as a vertex + if (channelsIn.get(channelGen) == null || channelsOut.get(channelGen) == null) { + Object channel = graph.insertVertex(parent, null, channelGen.getChannelName(), 150, 20, 30, 30); // insert + // a + // channel + // as + // a + // vertex mxCell port_in = new mxCell(null, geo1, "shape=ellipse;perimter=ellipsePerimeter"); port_in.setVertex(true); graph.addCell(port_in, channel); @@ -129,32 +149,35 @@ } } } - - for (Node n: resourceDependencyGraph.getNodes()) { + + for (Node n : resourceDependencyGraph.getNodes()) { if (n instanceof ResourceNode) { ResourceNode resourceNode = (ResourceNode) n; - Object resource = graph.insertVertex(parent, null, resourceNode.getIdentifierTemplate().getResourceName(), - 20, 20, 80, 30, "shape=ellipse;perimeter=ellipsePerimeter"); // insert a resource as a node + Object resource = graph.insertVertex(parent, null, + resourceNode.getIdentifierTemplate().getResourceName(), 20, 20, 80, 30, + "shape=ellipse;perimeter=ellipsePerimeter"); // insert a resource as a node resources.put(resourceNode, resource); } } - - for (Edge e: resourceDependencyGraph.getEdges()) { + + for (Edge e : resourceDependencyGraph.getEdges()) { if (e instanceof ResourceDependency) { ResourceDependency dependency = (ResourceDependency) e; - dependency.setAttribute(new PushPullAttribute(new PushPullValue[] {PushPullValue.PUSHorPULL, PushPullValue.PULL, PushPullValue.PUSH})); DataflowChannelGenerator channelGen = dependency.getChannelGenerator(); - graph.insertEdge(parent, null, dependency.getAttribute(), resources.get(dependency.getSource()), channelsIn.get(channelGen)); - graph.insertEdge(parent, null, null, channelsOut.get(channelGen), resources.get(dependency.getDestination())); + graph.insertEdge(parent, null, dependency.getAttribute(), resources.get(dependency.getSource()), + channelsIn.get(channelGen)); + graph.insertEdge(parent, null, null, channelsOut.get(channelGen), + resources.get(dependency.getDestination())); } } - + } finally { graph.getModel().endUpdate(); } setTreeLayout(); - - return graph; + setResourceGraph(resourceDependencyGraph); + + return graph; } public void setTreeLayout() { diff --git a/AlgebraicDataflowArchitectureModel/src/tests/CodeGeneratorTest.java b/AlgebraicDataflowArchitectureModel/src/tests/CodeGeneratorTest.java index bb679fe..6370c7c 100644 --- a/AlgebraicDataflowArchitectureModel/src/tests/CodeGeneratorTest.java +++ b/AlgebraicDataflowArchitectureModel/src/tests/CodeGeneratorTest.java @@ -6,7 +6,6 @@ import java.io.FileReader; import algorithm.*; -import models.Node; import models.dataFlowModel.*; import parser.*; @@ -22,7 +21,9 @@ ResourceDependencyGraph graph = DataStorageNecessity.run(model); EdgeTransitionSelectable.run(graph); DataStorageDecision.run(graph); - System.out.println(CodeGenerator.doGenerate(graph)); + for(String str:CodeGenerator.doGenerate(graph)) { + System.out.println(str); + } } catch (ExpectedChannel | ExpectedChannelName | ExpectedLeftCurlyBracket | ExpectedInOrOutKeyword | ExpectedStateTransition | ExpectedEquals | ExpectedRHSExpression | WrongLHSExpression | WrongRHSExpression | ExpectedRightBracket e) {