+/* $Id: YapiProcessVisitor.java 1 2010-02-24 13:03:05Z haidw $ */
+package dol.visitor.yapi;
+
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.OutputStream;
+import java.util.Vector;
+
+import dol.datamodel.pn.Port;
+import dol.datamodel.pn.Process;
+import dol.datamodel.pn.ProcessNetwork;
+import dol.datamodel.pn.SourceCode;
+import dol.util.CodePrintStream;
+import dol.util.Sed;
+import dol.visitor.PNVisitor;
+
+/**
+ *
+ */
+public class YapiProcessVisitor extends PNVisitor {
+
+ /**
+ * Constructor.
+ */
+ public YapiProcessVisitor(String dir) {
+ _dir = dir;
+ }
+
+ /**
+ *
+ * @param x process network that needs to be rendered
+ */
+ public void visitComponent(ProcessNetwork x) {
+ try {
+ Vector<String> pList = new Vector<String>();
+
+ for (Process p : x.getProcessList()) {
+ String basename = p.getBasename();
+ if (!pList.contains(basename)) {
+ pList.add(basename);
+ p.accept(this);
+ }
+ }
+ }
+ catch (Exception e) {
+ System.out.println("Process Visitor: exception "
+ + "occured: " + e.getMessage());
+ e.printStackTrace();
+ }
+ }
+
+ /**
+ *
+ * @param p process that needs to be rendered
+ */
+ public void visitComponent(Process p) {
+ try {
+ _createCppFile(p);
+ _createHeaderFile(p);
+ _adaptSources(p);
+ }
+ catch (Exception e) {
+ System.out.println("Process Visitor: exception "
+ + "occured: " + e.getMessage());
+ e.printStackTrace();
+ }
+ }
+
+ /**
+ *
+ */
+ protected void _adaptSources(Process p) throws IOException {
+ Sed sed = new Sed();
+ for (Port port : p.getPortList()) {
+ String processHeaderFile;
+
+ for (SourceCode sr : p.getSrcList()) {
+ processHeaderFile = _dir + _delimiter + ".."
+ + _delimiter + "processes" + _delimiter
+ + sr.getLocality().
+ replaceAll("(.*)\\.[cC][pP]*[pP]*", "$1\\.h");
+
+ if (port.isOutPort()) {
+ sed.sed(processHeaderFile,
+ "(#define[ ]*PORT_\\w*[ ]*)\"?"
+ + port.getBasename() + "\"?",
+ "$1 " + "(const_cast<void *>((const void*)"
+ +"(((static_cast<" + p.getBasename()
+ + "_wrapper *>(p->wptr))->OUTPORT_"
+ + port.getBasename() + "))))");
+ }
+ else if (port.isInPort()) {
+ sed.sed(processHeaderFile,
+ "(#define[ ]*PORT_\\w*[ ]*)\"?"
+ + port.getBasename() + "\"?",
+ "$1 " + "(const_cast<void *>((const void*)"
+ +"(((static_cast<" + p.getBasename()
+ + "_wrapper *>(p->wptr))->INPORT_"
+ + port.getBasename() + "))))");
+ }
+ }
+ }
+ }
+
+ /**
+ *
+ */
+ protected void _createCppFile(Process p) throws IOException {
+ String filename = _dir + _delimiter + p.getBasename()
+ + "_wrapper.cpp";
+ OutputStream file = new FileOutputStream(filename);
+ CodePrintStream ps = new CodePrintStream(file);
+
+ String newline = System.getProperty("line.separator");
+ String code = "#include \"" + p.getBasename() + "_wrapper.h\""
+ + newline;
+ code += "#include \"dolSupport.h\"" + newline;
+ for (SourceCode sr : p.getSrcList()) {
+ code += "#include \"" + sr.getLocality() + "\"" + newline;
+ }
+
+ code += newline;
+
+ code += p.getBasename() + "_wrapper::" + p.getBasename()
+ + "_wrapper(const char* name, const Id& n";
+ for (Port port : p.getPortList()) {
+ if (port.isInPort()) {
+ code += ", In<char>& inport_" + port.getName();
+ } else {
+ code += ", Out<char>& outport_" + port.getName();
+ }
+ }
+ code += ")" + newline;
+
+ code += " : ProcessWrapper(name, n)" + newline;
+ code += " {" + newline;
+ code += " _state = (LocalState)new "
+ + p.getBasename().substring(0, 1).toUpperCase()
+ + p.getBasename().substring(1) + "_State;"
+ + newline;
+ code += " _process.local = _state;" + newline;
+ code += " _process.init = " + p.getBasename() + "_init;"
+ + newline;
+ code += " _process.fire = " + p.getBasename() + "_fire;"
+ + newline;
+ code += " _process.wptr = this;" + newline;
+ for (Port port : p.getPortList()) {
+ if (!port.getRange().equals("")) {
+ String portName =
+ port.getName().replaceAll("_([0-9])", "][$1");
+ portName += "]";
+ portName = portName.replaceFirst("]", "");
+ if (port.isOutPort()) {
+ code += " OUTPORT_" + portName
+ + " = new OutPort<char>(id(\"" + port.getName()
+ + "\"), outport_" + port.getName() + ");"
+ + newline;
+ }
+ else if (port.isInPort()) {
+ code += " INPORT_" + portName
+ + " = new InPort<char>(id(\"" + port.getName()
+ + "\"), inport_" + port.getName() + ");"
+ + newline;
+ }
+ } else {
+ if (port.isInPort()) {
+ code += " INPORT_" + port.getName()
+ + " = new InPort<char>(id(\"" + port.getName()
+ + "\"), inport_" + port.getName() + ");"
+ + newline;
+ } else {
+ code += " OUTPORT_" + port.getName()
+ + " = new OutPort<char>(id(\"" + port.getName()
+ + "\"), outport_" + port.getName() + ");"
+ + newline;
+ }
+ }
+ }
+ code += "}" + newline + newline;
+
+ code += p.getBasename() + "_wrapper::~" + p.getBasename()
+ + "_wrapper() {" + newline;
+ code += " if (_state)" + newline;
+ code += " delete ("
+ + p.getBasename().substring(0, 1).toUpperCase()
+ + p.getBasename().substring(1) + "_State*)_state;"
+ + newline;
+ for (Port port : p.getPortList()) {
+ if (!port.getRange().equals("")) {
+ String portName =
+ port.getName().replaceAll("_([0-9])", "][$1");
+ portName += "]";
+ portName = portName.replaceFirst("]", "");
+ if (port.isOutPort()) {
+ code += " if (OUTPORT_" + portName + ")" + newline;
+ code += " delete OUTPORT_" + portName + ";"
+ + newline;
+ }
+ else if (port.isInPort()) {
+ code += " if (INPORT_" + portName + ")" + newline;
+ code += " delete INPORT_" + portName + ";"
+ + newline;
+ }
+ } else {
+ if (port.isInPort()) {
+ code += " if(INPORT_" + port.getName() + ")"
+ + newline;
+ code += " delete INPORT_" + port.getName() + ";"
+ + newline;
+ } else {
+ code += " if(OUTPORT_" + port.getName() + ")"
+ + newline;
+ code += " delete OUTPORT_" + port.getName() + ";"
+ + newline;
+ }
+ }
+ }
+ code += "}" + newline + newline;
+
+ code += "const char* "
+ + p.getBasename() + "_wrapper::type() const {" + newline;
+ code += " return \"" + p.getName() + "\";" + newline;
+ code += "}" + newline + newline;
+
+ code += "void " + p.getBasename() + "_wrapper::main() {" + newline;
+ code += " _process.init(&_process);" + newline;
+ code += " while(!isDetached()) {" + newline;
+ code += " _process.fire(&_process);" + newline;
+ code += " }" + newline;
+ code += "}" + newline;
+ ps.printPrefixln(code);
+ }
+
+ protected void _createHeaderFile(Process p)
+ throws IOException {
+ String filename = _dir + _delimiter + p.getBasename()
+ + "_wrapper.h";
+ OutputStream file = new FileOutputStream(filename);
+ CodePrintStream ps = new CodePrintStream(file);
+
+ String newline = System.getProperty("line.separator");
+ String code = "#ifndef " + p.getBasename() + "_WRAPPER_H"
+ + newline;
+ code += "#define " + p.getBasename() + "_WRAPPER_H" + newline
+ + newline;
+ code += "#include \"ProcessWrapper.h\"" + newline;
+ code += newline;
+
+ code += "class " + p.getBasename() + "_wrapper : "
+ + "public ProcessWrapper {" + newline;
+ code += " public:" + newline;
+ code += " " + p.getBasename()
+ + "_wrapper(const char* name, const Id& n";
+ for (Port port : p.getPortList()) {
+ if (port.isInPort()) {
+ code += ", In<char>& inport_" + port.getName();
+ } else {
+ code += ", Out<char>& outport_" + port.getName();
+ }
+ }
+ code += ");" + newline;
+ code += " virtual ~" + p.getBasename() + "_wrapper();"
+ + newline;
+ code += " const char* type() const;" + newline;
+ code += " void main();" + newline + newline;
+
+ Vector<String> portList = new Vector<String>();
+ for (Port port : p.getPortList()) {
+ String basename = port.getBasename();
+
+ if (!portList.contains(basename)) {
+ portList.add(basename);
+
+ if (!port.getRange().equals("")) {
+ if (port.isOutPort()) {
+ code += " OutPort<char> *OUTPORT_"
+ + port.getBasename() + "["
+ + port.getRange().replaceAll(
+ ";", "\\]\\[") + "];" + newline;
+ }
+ else if (port.isInPort()) {
+ code += " InPort<char> *INPORT_"
+ + port.getBasename() + "["
+ + port.getRange().replaceAll(
+ ";", "\\]\\[") + "];" + newline;
+ }
+ }
+ else {
+ if (port.isOutPort()) {
+ code += " OutPort<char> *OUTPORT_"
+ + port.getName() + ";" + newline;
+ }
+ else if (port.isInPort()) {
+ code += " InPort<char> *INPORT_"
+ + port.getName() + ";" + newline;
+ }
+ }
+ }
+ }
+ code += newline;
+ code += " protected:" + newline;
+ code += " LocalState _state;" + newline;
+ code += "};" + newline + newline;
+ code += "#endif";
+ ps.printPrefixln(code);
+ }
+
+ protected String _dir = null;
+}