PLCControler.py
changeset 684 f10449b18dbe
parent 681 c141dad94ff4
child 687 629680fb0582
--- a/PLCControler.py	Sat May 12 12:33:17 2012 +0200
+++ b/PLCControler.py	Fri May 18 18:49:49 2012 +0200
@@ -75,6 +75,11 @@
                    "InOut" :    (plcopen.interface_inOutVars,    ITEM_VAR_INOUT)
                   }
 
+POU_TYPES = {"program": ITEM_PROGRAM,
+             "functionBlock": ITEM_FUNCTIONBLOCK,
+             "function": ITEM_FUNCTION,
+            }
+
 LOCATIONS_ITEMS = [LOCATION_CONFNODE,
                    LOCATION_MODULE,
                    LOCATION_GROUP,
@@ -376,12 +381,259 @@
                     resources["values"].append(resource_infos)
                 config_infos["values"] = [resources]
                 configurations["values"].append(config_infos)
-            infos["values"] = [{"name": PROPERTIES, "type": ITEM_PROPERTIES, "values": []},
-                               datatypes, pou_types["function"], pou_types["functionBlock"], 
+            infos["values"] = [datatypes, pou_types["function"], pou_types["functionBlock"], 
                                pou_types["program"], configurations]
             return infos
         return None
 
+    def GetPouVariableInfos(self, project, variable, var_class, debug=False):
+        vartype_content = variable.gettype().getcontent()
+        if vartype_content["name"] == "derived":
+            var_type = vartype_content["value"].getname()
+            pou_type = None
+            pou = project.getpou(var_type)
+            if pou is not None:
+                pou_type = pou.getpouType()
+            edit = debug = pou_type is not None
+            if pou_type is None:
+                block_infos = self.GetBlockType(var_type, debug = debug)
+                pou_type = block_infos["type"]
+            if pou_type is not None:
+                var_class = None
+                if pou_type == "program":
+                    var_class = ITEM_PROGRAM
+                elif pou_type != "function":
+                    var_class = ITEM_FUNCTIONBLOCK
+                if var_class is not None:
+                    return {"name": variable.getname(), 
+                            "type": var_type, 
+                            "class": var_class,
+                            "edit": edit,
+                            "debug": debug}
+            elif var_type in self.GetDataTypes(debug = debug):
+                return {"name": variable.getname(), 
+                        "type": var_type, 
+                        "class": var_class,
+                        "edit": False,
+                        "debug": False}
+        elif vartype_content["name"] in ["string", "wstring"]:
+            return {"name": variable.getname(), 
+                    "type": vartype_content["name"].upper(), 
+                    "class": var_class,
+                    "edit": False,
+                    "debug": True}
+        else:
+            return {"name": variable.getname(),
+                    "type": vartype_content["name"], 
+                    "class": var_class,
+                    "edit": False,
+                    "debug": True}
+        return None
+
+    def GetPouVariables(self, tagname, debug = False):
+        vars = []
+        pou_type = None
+        project = self.GetProject(debug)
+        if project is not None:
+            words = tagname.split("::")
+            if words[0] == "P":
+                pou = project.getpou(words[1])
+                if pou is not None:
+                    pou_type = pou.getpouType()
+                    if (pou_type in ["program", "functionBlock"] and 
+                        pou.interface is not None):
+                        # Extract variables from every varLists
+                        for varlist_type, varlist in pou.getvars():
+                            var_infos = VAR_CLASS_INFOS.get(varlist_type, None)
+                            if var_infos is not None:
+                                var_class = var_infos[1]
+                            else:
+                                var_class = ITEM_VAR_LOCAL
+                            for variable in varlist.getvariable():
+                                var_infos = self.GetPouVariableInfos(project, variable, var_class, debug)
+                                if var_infos is not None:
+                                    vars.append(var_infos)
+                        return {"class": POU_TYPES[pou_type],
+                                "type": words[1],
+                                "variables": vars,
+                                "edit": True,
+                                "debug": True}
+                else:
+                    block_infos = self.GetBlockType(words[1], debug = debug)
+                    if (block_infos is not None and 
+                        block_infos["type"] in ["program", "functionBlock"]):
+                        for varname, vartype, varmodifier in block_infos["inputs"]:
+                            vars.append({"name" : varname, 
+                                         "type" : vartype, 
+                                         "class" : ITEM_VAR_INPUT,
+                                         "edit": False,
+                                         "debug": True})
+                        for varname, vartype, varmodifier in block_infos["outputs"]:
+                            vars.append({"name" : varname, 
+                                         "type" : vartype, 
+                                         "class" : ITEM_VAR_OUTPUT,
+                                         "edit": False,
+                                         "debug": True})
+                        return {"class": POU_TYPES[block_infos["type"]],
+                                "type": None,
+                                "variables": vars,
+                                "edit": False,
+                                "debug": False}
+            elif words[0] in ['C', 'R']:
+                if words[0] == 'C':
+                    pou_type = ITEM_CONFIGURATION
+                    element = project.getconfiguration(words[1])
+                    for resource in element.getresource():
+                        vars.append({"name": resource.getname(),
+                                     "type": None,
+                                     "class": ITEM_RESOURCE,
+                                     "edit": True,
+                                     "debug": False})
+                elif words[0] == 'R':
+                    pou_type = ITEM_RESOURCE
+                    element = project.getconfigurationResource(words[1], words[2])
+                    for task in element.gettask():
+                        for pou in task.getpouInstance():
+                            vars.append({"name": pou.getname(),
+                                         "type": pou.gettypeName(),
+                                         "class": ITEM_PROGRAM,
+                                         "edit": True,
+                                         "debug": True})
+                    for pou in element.getpouInstance():
+                        vars.append({"name": pou.getname(),
+                                     "type": pou.gettypeName(),
+                                     "class": ITEM_PROGRAM,
+                                     "edit": True,
+                                     "debug": True})
+                for varlist in element.getglobalVars():
+                    for variable in varlist.getvariable():
+                        var_infos = self.GetPouVariableInfos(project, variable, ITEM_VAR_GLOBAL, debug)
+                        if var_infos is not None:
+                            vars.append(var_infos)
+                return {"class": pou_type,
+                        "type": None,
+                        "variables": vars,
+                        "edit": True,
+                        "debug": False}
+        return None
+
+    def RecursiveSearchPouInstances(self, project, pou_type, parent_path, varlists, debug = False):
+        instances = []
+        for varlist in varlists:
+            for variable in varlist.getvariable():
+                vartype_content = variable.gettype().getcontent()
+                if vartype_content["name"] == "derived":
+                    var_path = "%s.%s" % (parent_path, variable.getname())
+                    var_type = vartype_content["value"].getname()
+                    if var_type == pou_type:
+                        instances.append(var_path)
+                    else:
+                        pou = project.getpou(var_type)
+                        if pou is not None:
+                            instances.extend(
+                                self.RecursiveSearchPouInstances(
+                                    project, pou_type, var_path, 
+                                    [varlist for type, varlist in pou.getvars()], 
+                                    debug))
+        return instances
+                        
+    def SearchPouInstances(self, tagname, debug = False):
+        project = self.GetProject(debug)
+        if project is not None:
+            words = tagname.split("::")
+            if words[0] == "P":
+                instances = []
+                for config in project.getconfigurations():
+                    config_name = config.getname()
+                    instances.extend(
+                        self.RecursiveSearchPouInstances(
+                            project, words[1], config_name, 
+                            config.getglobalVars(), debug))
+                    for resource in config.getresource():
+                        res_path = "%s.%s" % (config_name, resource.getname())
+                        instances.extend(
+                            self.RecursiveSearchPouInstances(
+                                project, words[1], res_path, 
+                                resource.getglobalVars(), debug))
+                        pou_instances = resource.getpouInstance()[:]
+                        for task in resource.gettask():
+                            pou_instances.extend(task.getpouInstance())
+                        for pou_instance in pou_instances:
+                            pou_path = "%s.%s" % (res_path, pou_instance.getname())
+                            pou_type = pou_instance.gettypeName()
+                            if pou_type == words[1]:
+                                instances.append(pou_path)
+                            pou = project.getpou(pou_type)
+                            if pou is not None:
+                                instances.extend(
+                                    self.RecursiveSearchPouInstances(
+                                        project, words[1], pou_path, 
+                                        [varlist for type, varlist in pou.getvars()], 
+                                        debug))
+                return instances
+            elif words[0] == 'C':
+                return [words[1]]
+            elif words[0] == 'R':
+                return ["%s.%s" % (words[1], words[2])]
+        return []
+    
+    def RecursiveGetPouInstanceTagname(self, project, pou_type, parts):
+        pou = project.getpou(pou_type)
+        if pou is not None:
+            if len(parts) == 0:
+                return self.ComputePouName(pou_type)
+            
+            for varlist_type, varlist in pou.getvars():
+                for variable in varlist.getvariable():
+                    vartype_content = variable.gettype().getcontent()
+                    if vartype_content["name"] == "derived":
+                        return self.RecursiveGetPouInstanceTagname(
+                                        project, 
+                                        vartype_content["value"].getname(),
+                                        parts[1:])
+        return None
+    
+    def GetPouInstanceTagname(self, instance_path, debug = False):
+        parts = instance_path.split(".")
+        if len(parts) == 1:
+            return self.ComputeConfigurationName(parts[0])
+        elif len(parts) == 2:
+            return self.ComputeConfigurationResourceName(parts[0], parts[1])
+        else:
+            project = self.GetProject(debug)
+            for config in project.getconfigurations():
+                if config.getname() == parts[0]:
+                    for resource in config.getresource():
+                        if resource.getname() == parts[1]:
+                            pou_instances = resource.getpouInstance()[:]
+                            for task in resource.gettask():
+                                pou_instances.extend(task.getpouInstance())
+                            for pou_instance in pou_instances:
+                                if pou_instance.getname() == parts[2]:
+                                    if len(parts) == 3:
+                                        return self.ComputePouName(
+                                                    pou_instance.gettypeName())
+                                    else:
+                                        return self.RecursiveGetPouInstanceTagname(
+                                                    project,
+                                                    pou_instance.gettypeName(),
+                                                    parts[3:])
+        return None
+    
+    def GetInstanceInfos(self, instance_path):
+        tagname = self.GetPouInstanceTagName(instance_path)
+        if tagname is not None:
+            return self.Controler.GetPouVariables(tagname, self.Debug)
+        else:
+            pou_path, var_name = tagname.rsplit(".", 1)
+            tagname = self.Controler.GetPouInstanceTagName(pou_path)
+            if tagname is not None:
+                pou_infos = self.Controler.GetPouVariables(tagname, self.Debug)
+                for var_infos in pou_infos["variables"]:
+                    if var_infos["name"] == var_name:
+                        return var_infos
+        return None
+        
     # Return project topology informations
     def GetProjectTopology(self, debug = False):
         project = self.GetProject(debug)
@@ -495,7 +747,7 @@
                 for varname, vartype, varmodifier in block_infos["inputs"]:
                     pou_infos["values"].append({"name" : varname, "elmt_type" : vartype, "type" : ITEM_VAR_INPUT, "values" : []})
                 for varname, vartype, varmodifier in block_infos["outputs"]:
-                    pou_infos["values"].append({"name" : varname, "elmt_type" : vartype, "type" : ITEM_VAR_INPUT, "values" : []})
+                    pou_infos["values"].append({"name" : varname, "elmt_type" : vartype, "type" : ITEM_VAR_OUTPUT, "values" : []})
                 return pou_infos
             
             if type in self.GetDataTypes(debug = debug):
@@ -2739,7 +2991,7 @@
         for child in tree.childNodes:
             if child.nodeType == tree.ELEMENT_NODE and child.nodeName == "project":
                 try:
-                    result = self.Project.loadXMLTree(child, ["xmlns", "xmlns:xhtml", "xmlns:xsi", "xsi:schemaLocation"])
+                    result = self.Project.loadXMLTree(child)
                 except ValueError, e:
                     return _("Project file syntax error:\n\n") + str(e)
                 self.SetFilePath(filepath)