--- a/etherlab/etherlab.py Sun Mar 11 21:57:00 2012 +0100
+++ b/etherlab/etherlab.py Sun Mar 18 23:57:32 2012 +0100
@@ -7,118 +7,129 @@
from xmlclass import *
from plugger import PlugTemplate
from PLCControler import UndoBuffer, LOCATION_PLUGIN, LOCATION_MODULE, LOCATION_GROUP, LOCATION_VAR_INPUT, LOCATION_VAR_OUTPUT, LOCATION_VAR_MEMORY
-from ConfigEditor import ConfigEditor, DS402NodeEditor, ETHERCAT_VENDOR, ETHERCAT_GROUP, ETHERCAT_DEVICE
+from ConfigEditor import NodeEditor, DS402NodeEditor, ETHERCAT_VENDOR, ETHERCAT_GROUP, ETHERCAT_DEVICE
+
+try:
+ from plugins.motion import Headers, AxisXSD
+ HAS_MCL = True
+except:
+ HAS_MCL = False
+
+
+TYPECONVERSION = {"BOOL" : "X", "SINT" : "B", "INT" : "W", "DINT" : "D", "LINT" : "L",
+ "USINT" : "B", "UINT" : "W", "UDINT" : "D", "ULINT" : "L",
+ "BYTE" : "B", "WORD" : "W", "DWORD" : "D", "LWORD" : "L"}
+
+DATATYPECONVERSION = {"BOOL" : "BIT", "SINT" : "S8", "INT" : "S16", "DINT" : "S32", "LINT" : "S64",
+ "USINT" : "U8", "UINT" : "U16", "UDINT" : "U32", "ULINT" : "U64",
+ "BYTE" : "U8", "WORD" : "U16", "DWORD" : "U32", "LWORD" : "U64"}
+
+VARCLASSCONVERSION = {"T": LOCATION_VAR_INPUT, "R": LOCATION_VAR_OUTPUT, "RT": LOCATION_VAR_MEMORY}
#--------------------------------------------------
-# Ethercat DS402 Node
+# Remote Exec Etherlab Commands
#--------------------------------------------------
-NODE_VARIABLES = [
- ("ControlWord", 0x6040, 0x00, "UINT", "Q"),
- ("TargetPosition", 0x607a, 0x00, "DINT", "Q"),
- ("StatusWord", 0x6041, 0x00, "UINT", "I"),
- ("ModesOfOperationDisplay", 0x06061, 0x00, "SINT", "I"),
- ("ActualPosition", 0x6064, 0x00, "DINT", "I"),
- ("ErrorCode", 0x603f, 0x00, "UINT", "I"),
-]
-
-class _EthercatDS402SlavePlug:
- XSD = """<?xml version="1.0" encoding="ISO-8859-1" ?>
- <xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">
- <xsd:element name="EtherlabDS402Slave">
- <xsd:complexType>
- <xsd:attribute name="Node_Type" type="xsd:string" use="optional"/>
- </xsd:complexType>
- </xsd:element>
- </xsd:schema>
- """
- EditorType = DS402NodeEditor
+SCAN_COMMAND = """
+import commands
+result = commands.getoutput("ethercat slaves")
+slaves = []
+for slave_line in result.splitlines():
+ chunks = slave_line.split()
+ idx, pos, state, flag = chunks[:4]
+ name = " ".join(chunks[4:])
+ alias, position = pos.split(":")
+ slave = {"idx": int(idx),
+ "alias": int(alias),
+ "position": int(position),
+ "name": name}
+ details = commands.getoutput("ethercat slaves -p %d -v" % slave["idx"])
+ for details_line in details.splitlines():
+ details_line = details_line.strip()
+ for header, param in [("Vendor Id:", "vendor_id"),
+ ("Product code:", "product_code"),
+ ("Revision number:", "revision_number")]:
+ if details_line.startswith(header):
+ slave[param] = int(details_line.split()[-1], 16)
+ break
+ slaves.append(slave)
+returnVal = slaves
+"""
+
+#--------------------------------------------------
+# Ethercat Node
+#--------------------------------------------------
+
+class _EthercatSlavePlug:
+
+ NODE_PROFILE = None
+ EditorType = NodeEditor
def ExtractHexDecValue(self, value):
return ExtractHexDecValue(value)
-
+
def GetSizeOfType(self, type):
return TYPECONVERSION.get(self.GetPlugRoot().GetBaseType(type), None)
- def _GetChildBySomething(self, something, toks):
- return self
+ def GetSlavePos(self):
+ return self.BaseParams.getIEC_Channel()
def GetParamsAttributes(self, path = None):
- infos = PlugTemplate.GetParamsAttributes(self, path = None)
- for element in infos:
- if element["name"] == "EtherlabDS402Slave":
- for child in element["children"]:
- if child["name"] == "Node_Type":
- child["type"] = [module[0] for module in self.PlugParent.GetModulesByProfile(402)]
- return infos
-
- def GetAllChannels(self):
- AllChannels = PlugTemplate.GetAllChannels(self)
- for slave_pos in self.PlugParent.GetSlaves():
- if slave_pos[0] not in AllChannels:
- AllChannels.append(slave_pos[0])
- AllChannels.sort()
- return AllChannels
-
- def GetCurrentLocation(self):
- """
- @return: Tupple containing plugin IEC location of current plugin : %I0.0.4.5 => (0,0,4,5)
- """
- return self.PlugParent.GetCurrentLocation() + self.GetSlavePos()
-
- def GetSlavePos(self):
- return self.BaseParams.getIEC_Channel(), 0
-
- def GetSlaveTypeInfos(self):
- slave_type = self.EtherlabDS402Slave.getNode_Type()
-
- for module_type, vendor_id, product_code, revision_number in self.PlugParent.GetModulesByProfile(402):
- if module_type == slave_type:
- return {"device_type": module_type,
- "vendor": GenerateHexDecValue(vendor_id),
- "product_code": GenerateHexDecValue(product_code, 16),
- "revision_number": GenerateHexDecValue(revision_number, 16)}
-
- return None
+ if path:
+ parts = path.split(".", 1)
+ if self.MandatoryParams and parts[0] == self.MandatoryParams[0]:
+ return self.MandatoryParams[1].getElementInfos(parts[0], parts[1])
+ elif self.PlugParams and parts[0] == self.PlugParams[0]:
+ return self.PlugParams[1].getElementInfos(parts[0], parts[1])
+ else:
+ params = []
+ if wx.VERSION < (2, 8, 0) and self.MandatoryParams:
+ params.append(self.MandatoryParams[1].getElementInfos(self.MandatoryParams[0]))
+ slave_type = self.PlugParent.GetSlaveType(self.GetSlavePos())
+ params.append({
+ 'use': 'required',
+ 'type': 'element',
+ 'name': 'SlaveParams',
+ 'value': None,
+ 'children': [{
+ 'use': 'optional',
+ 'type': self.PlugParent.GetSlaveTypesLibrary(self.NODE_PROFILE),
+ 'name': 'Type',
+ 'value': (slave_type["device_type"], slave_type)},
+ {'use': 'optional',
+ 'type': 'unsignedLong',
+ 'name': 'Alias',
+ 'value': self.PlugParent.GetSlaveAlias(self.GetSlavePos())}]
+ })
+ if self.PlugParams:
+ params.append(self.PlugParams[1].getElementInfos(self.PlugParams[0]))
+ return params
+
+ def SetParamsAttribute(self, path, value):
+ position = self.BaseParams.getIEC_Channel()
+ value, changed = PlugTemplate.SetParamsAttribute(self, path, value)
+ # Filter IEC_Channel, Slave_Type and Alias that have specific behavior
+ if path == "BaseParams.IEC_Channel":
+ self.PlugParent.SetSlavePosition(position, value)
+ elif path == "SlaveParams.Type":
+ self.PlugParent.SetSlaveType(position, value)
+ slave_type = self.PlugParent.GetSlaveType(self.GetSlavePos())
+ value = (slave_type["device_type"], slave_type)
+ changed = True
+ elif path == "SlaveParams.Alias":
+ self.PlugParent.SetSlaveAlias(position, value)
+ changed = True
+ return value, changed
def GetSlaveInfos(self):
- slave_typeinfos = self.GetSlaveTypeInfos()
- if slave_typeinfos is not None:
- device = self.PlugParent.GetModuleInfos(slave_typeinfos)
- if device is not None:
- infos = slave_typeinfos.copy()
- entries = device.GetEntriesList()
- entries_list = entries.items()
- entries_list.sort()
- entries = []
- current_index = None
- current_entry = None
- for (index, subindex), entry in entries_list:
- entry["children"] = []
- if index != current_index:
- current_index = index
- current_entry = entry
- entries.append(entry)
- elif current_entry is not None:
- current_entry["children"].append(entry)
- else:
- entries.append(entry)
- infos.update({"physics": device.getPhysics(),
- "sync_managers": device.GetSyncManagers(),
- "entries": entries})
- return infos
- return None
-
+ return self.PlugParent.GetSlaveInfos(self.GetSlavePos())
+
def GetVariableLocationTree(self):
- slave_typeinfos = self.GetSlaveTypeInfos()
- vars = []
- if slave_typeinfos is not None:
- vars = self.PlugParent.GetDeviceLocationTree(self.GetCurrentLocation(), slave_typeinfos)
-
return {"name": self.BaseParams.getName(),
"type": LOCATION_PLUGIN,
"location": self.GetFullIEC_Channel(),
- "children": vars}
+ "children": self.PlugParent.GetDeviceLocationTree(self.GetSlavePos(), self.GetCurrentLocation(), self.BaseParams.getName())
+ }
PluginMethods = [
{"bitmap" : os.path.join("images", "EditCfile"),
@@ -127,7 +138,6 @@
"method" : "_OpenView"},
]
-
def PlugGenerate_C(self, buildpath, locations):
"""
Generate C code
@@ -141,79 +151,111 @@
}, ...]
@return: [(C_file_name, CFLAGS),...] , LDFLAGS_TO_APPEND
"""
- current_location = self.GetCurrentLocation()
-
- location_str = "_".join(map(lambda x:str(x), current_location))
-
- slave_pos = current_location[-2:]
-
- slave_typeinfos = self.GetSlaveTypeInfos()
- device = None
- if slave_typeinfos is not None:
- device = self.PlugParent.GetModuleInfos(slave_typeinfos)
-
- if device is None:
- raise (ValueError,
- _("No information found for DS402 node \"%s\" at location %s!") % (
- slave_typeinfos["device_type"], ".".join(current_location)))
-
- self.PlugParent.FileGenerator.DeclareSlave(slave_pos, slave_typeinfos)
-
- plc_ds402node_filepath = os.path.join(os.path.split(__file__)[0], "plc_ds402node.c")
- plc_ds402node_file = open(plc_ds402node_filepath, 'r')
- plc_ds402node_code = plc_ds402node_file.read()
- plc_ds402node_file.close()
-
- from plugins.motion import Headers
-
- str_completion = {
- "location": location_str,
- "MCL_headers": Headers,
- "extern_located_variables_declaration": [],
- "entry_variables": [],
- "init_entry_variables": [],
- }
-
- for variable in NODE_VARIABLES:
- var_infos = dict(zip(["name", "index", "subindex", "var_type", "dir"], variable))
- var_infos["location"] = location_str
- var_infos["var_size"] = self.PlugParent.GetSizeOfType(var_infos["var_type"])
- var_infos["var_name"] = "__%(dir)s%(var_size)s%(location)s_%(index)d_%(subindex)d" % var_infos
-
- str_completion["extern_located_variables_declaration"].append(
- "IEC_%(var_type)s *%(var_name)s;" % var_infos)
- str_completion["entry_variables"].append(
- " IEC_%(var_type)s *%(name)s;" % var_infos)
- str_completion["init_entry_variables"].append(
- " __DS402Node_%(location)s.%(name)s = %(var_name)s;" % var_infos)
-
- self.PlugParent.FileGenerator.DeclareVariable(
- slave_pos, var_infos["index"], var_infos["subindex"],
- var_infos["var_type"], var_infos["dir"], var_infos["var_name"])
-
- for element in ["extern_located_variables_declaration",
- "entry_variables",
- "init_entry_variables"]:
- str_completion[element] = "\n".join(str_completion[element])
-
- Gen_DS402Nodefile_path = os.path.join(buildpath, "ds402node_%s.c"%location_str)
- ds402nodefile = open(Gen_DS402Nodefile_path, 'w')
- ds402nodefile.write(plc_ds402node_code % str_completion)
- ds402nodefile.close()
-
- return [(Gen_DS402Nodefile_path, '"-I%s"'%os.path.abspath(self.GetPlugRoot().GetIECLibPath()))],"",True
-
-
-
-TYPECONVERSION = {"BOOL" : "X", "SINT" : "B", "INT" : "W", "DINT" : "D", "LINT" : "L",
- "USINT" : "B", "UINT" : "W", "UDINT" : "D", "ULINT" : "L",
- "BYTE" : "B", "WORD" : "W", "DWORD" : "D", "LWORD" : "L"}
-
-DATATYPECONVERSION = {"BOOL" : "BIT", "SINT" : "S8", "INT" : "S16", "DINT" : "S32", "LINT" : "S64",
- "USINT" : "U8", "UINT" : "U16", "UDINT" : "U32", "ULINT" : "U64",
- "BYTE" : "U8", "WORD" : "U16", "DWORD" : "U32", "LWORD" : "U64"}
-
-VARCLASSCONVERSION = {"T": LOCATION_VAR_INPUT, "R": LOCATION_VAR_OUTPUT, "RT": LOCATION_VAR_MEMORY}
+ return [],"",False
+
+#--------------------------------------------------
+# Ethercat DS402 Node
+#--------------------------------------------------
+
+if HAS_MCL:
+
+ NODE_VARIABLES = [
+ ("ControlWord", 0x6040, 0x00, "UINT", "Q"),
+ ("TargetPosition", 0x607a, 0x00, "DINT", "Q"),
+ ("StatusWord", 0x6041, 0x00, "UINT", "I"),
+ ("ModesOfOperationDisplay", 0x06061, 0x00, "SINT", "I"),
+ ("ActualPosition", 0x6064, 0x00, "DINT", "I"),
+ ("ErrorCode", 0x603f, 0x00, "UINT", "I"),
+ ]
+
+ class _EthercatDS402SlavePlug(_EthercatSlavePlug):
+ XSD = """<?xml version="1.0" encoding="ISO-8859-1" ?>
+ <xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">
+ <xsd:element name="DS402SlaveParams">
+ <xsd:complexType>
+ %s
+ </xsd:complexType>
+ </xsd:element>
+ </xsd:schema>
+ """ % AxisXSD
+
+ NODE_PROFILE = 402
+ EditorType = DS402NodeEditor
+
+ def PlugGenerate_C(self, buildpath, locations):
+ """
+ Generate C code
+ @param current_location: Tupple containing plugin IEC location : %I0.0.4.5 => (0,0,4,5)
+ @param locations: List of complete variables locations \
+ [{"IEC_TYPE" : the IEC type (i.e. "INT", "STRING", ...)
+ "NAME" : name of the variable (generally "__IW0_1_2" style)
+ "DIR" : direction "Q","I" or "M"
+ "SIZE" : size "X", "B", "W", "D", "L"
+ "LOC" : tuple of interger for IEC location (0,1,2,...)
+ }, ...]
+ @return: [(C_file_name, CFLAGS),...] , LDFLAGS_TO_APPEND
+ """
+ current_location = self.GetCurrentLocation()
+
+ location_str = "_".join(map(lambda x:str(x), current_location))
+
+ plc_ds402node_filepath = os.path.join(os.path.split(__file__)[0], "plc_ds402node.c")
+ plc_ds402node_file = open(plc_ds402node_filepath, 'r')
+ plc_ds402node_code = plc_ds402node_file.read()
+ plc_ds402node_file.close()
+
+ str_completion = {
+ "location": location_str,
+ "MCL_headers": Headers,
+ "extern_located_variables_declaration": [],
+ "entry_variables": [],
+ "init_axis_params": [],
+ "init_entry_variables": [],
+ }
+
+ for variable in NODE_VARIABLES:
+ var_infos = dict(zip(["name", "index", "subindex", "var_type", "dir"], variable))
+ var_infos["location"] = location_str
+ var_infos["var_size"] = self.GetSizeOfType(var_infos["var_type"])
+ var_infos["var_name"] = "__%(dir)s%(var_size)s%(location)s_%(index)d_%(subindex)d" % var_infos
+
+ str_completion["extern_located_variables_declaration"].append(
+ "IEC_%(var_type)s *%(var_name)s;" % var_infos)
+ str_completion["entry_variables"].append(
+ " IEC_%(var_type)s *%(name)s;" % var_infos)
+ str_completion["init_entry_variables"].append(
+ " __DS402Node_%(location)s.%(name)s = %(var_name)s;" % var_infos)
+
+ self.PlugParent.FileGenerator.DeclareVariable(
+ self.GetSlavePos(), var_infos["index"], var_infos["subindex"],
+ var_infos["var_type"], var_infos["dir"], var_infos["var_name"])
+
+ params = self.PlugParams[1].getElementInfos(self.PlugParams[0])
+ for param in params["children"]:
+ if param["value"] is not None:
+ param_infos = {
+ "location": location_str,
+ "param_name": param["name"],
+ }
+ if param["type"] == "boolean":
+ param_infos["param_value"] = {True: "true", False: "false"}[param["value"]]
+ else:
+ param_infos["param_value"] = str(param["value"])
+ str_completion["init_axis_params"].append(
+ " __DS402Node_%(location)s.axis->%(param_name)s = %(param_value)s;" % param_infos)
+
+ for element in ["extern_located_variables_declaration",
+ "entry_variables",
+ "init_axis_params",
+ "init_entry_variables"]:
+ str_completion[element] = "\n".join(str_completion[element])
+
+ Gen_DS402Nodefile_path = os.path.join(buildpath, "ds402node_%s.c"%location_str)
+ ds402nodefile = open(Gen_DS402Nodefile_path, 'w')
+ ds402nodefile.write(plc_ds402node_code % str_completion)
+ ds402nodefile.close()
+
+ return [(Gen_DS402Nodefile_path, '"-I%s"'%os.path.abspath(self.GetPlugRoot().GetIECLibPath()))],"",True
#--------------------------------------------------
# Ethercat MASTER
@@ -257,18 +299,6 @@
slave_info.setProductCode(ExtractHexDecValue(type_infos["product_code"]))
slave_info.setRevisionNo(ExtractHexDecValue(type_infos["revision_number"]))
setattr(cls, "setType", setType)
-
-cls = EtherCATConfigClasses.get("Slave_Info", None)
-if cls:
-
- def getSlavePosition(self):
- return self.getPhysAddr(), self.getAutoIncAddr()
- setattr(cls, "getSlavePosition", getSlavePosition)
-
- def setSlavePosition(self, alias, pos):
- self.setPhysAddr(alias)
- self.setAutoIncAddr(pos)
- setattr(cls, "setSlavePosition", setSlavePosition)
class _EthercatPlug:
XSD = """<?xml version="1.0" encoding="ISO-8859-1" ?>
@@ -281,9 +311,10 @@
</xsd:element>
</xsd:schema>
"""
- EditorType = ConfigEditor
-
- PlugChildsTypes = [("EthercatDS402Slave", _EthercatDS402SlavePlug, "Ethercat DS402 Slave")]
+
+ PlugChildsTypes = [("EthercatSlave", _EthercatSlavePlug, "Ethercat Slave")]
+ if HAS_MCL:
+ PlugChildsTypes.append(("EthercatDS402Slave", _EthercatDS402SlavePlug, "Ethercat DS402 Slave"))
def __init__(self):
filepath = self.ConfigFileName()
@@ -314,62 +345,70 @@
def GetSlaves(self):
slaves = []
for slave in self.Config.getConfig().getSlave():
- slaves.append(slave.getInfo().getSlavePosition())
+ slaves.append(slave.getInfo().getPhysAddr())
slaves.sort()
return slaves
def GetSlave(self, slave_pos):
for slave in self.Config.getConfig().getSlave():
slave_info = slave.getInfo()
- if slave_info.getSlavePosition() == slave_pos:
+ if slave_info.getPhysAddr() == slave_pos:
return slave
return None
- def AddSlave(self):
- slaves = self.GetSlaves()
- for PlugInstance in self.IterChilds():
- slaves.append(PlugInstance.GetSlavePos())
- slaves.sort()
- if len(slaves) > 0:
- new_pos = (slaves[-1][0] + 1, 0)
- else:
- new_pos = (0, 0)
- slave = EtherCATConfigClasses["Config_Slave"]()
- slave_infos = slave.getInfo()
- slave_infos.setName("undefined")
- slave_infos.setSlavePosition(new_pos[0], new_pos[1])
- self.Config.getConfig().appendSlave(slave)
- self.BufferConfig()
- return new_pos
-
- def RemoveSlave(self, slave_pos):
+ def PlugAddChild(self, PlugName, PlugType, IEC_Channel=0):
+ """
+ Create the plugins that may be added as child to this node self
+ @param PlugType: string desining the plugin class name (get name from PlugChildsTypes)
+ @param PlugName: string for the name of the plugin instance
+ """
+ newPluginOpj = PlugTemplate.PlugAddChild(self, PlugName, PlugType, IEC_Channel)
+
+ slave = self.GetSlave(newPluginOpj.BaseParams.getIEC_Channel())
+ if slave is None:
+ slave = EtherCATConfigClasses["Config_Slave"]()
+ slave_infos = slave.getInfo()
+ slave_infos.setName("undefined")
+ slave_infos.setPhysAddr(newPluginOpj.BaseParams.getIEC_Channel())
+ slave_infos.setAutoIncAddr(0)
+ self.Config.getConfig().appendSlave(slave)
+ self.BufferConfig()
+ self.OnPlugSave()
+
+ return newPluginOpj
+
+ def _doRemoveChild(self, PlugInstance):
+ slave_pos = PlugInstance.GetSlavePos()
config = self.Config.getConfig()
for idx, slave in enumerate(config.getSlave()):
slave_infos = slave.getInfo()
- if slave_infos.getSlavePosition() == slave_pos:
+ if slave_infos.getPhysAddr() == slave_pos:
config.removeSlave(idx)
self.BufferConfig()
- return True
- return False
-
- def SetSlavePos(self, slave_pos, alias=None, position=None):
- for PlugInstance in self.IterChilds():
- if PlugInstance.BaseParams.getIEC_Channel() == alias:
- return _("Slave with alias \"%d\" already exists!" % alias)
+ self.OnPlugSave()
+ PlugTemplate._doRemoveChild(self, PlugInstance)
+
+ def SetSlavePosition(self, slave_pos, new_pos):
slave = self.GetSlave(slave_pos)
if slave is not None:
slave_info = slave.getInfo()
- new_pos = slave_pos
- if alias is not None:
- new_pos = (alias, new_pos[1])
- if position is not None:
- new_pos = (new_pos[0], position)
- if self.GetSlave(new_pos) is not None:
- return _("Slave with position \"%d:%d\" already exists!" % new_pos)
- slave_info.setSlavePosition(*new_pos)
+ slave_info.setPhysAddr(new_pos)
self.BufferConfig()
+
+ def GetSlaveAlias(self, slave_pos):
+ slave = self.GetSlave(slave_pos)
+ if slave is not None:
+ slave_info = slave.getInfo()
+ return slave_info.getAutoIncAddr()
return None
+ def SetSlaveAlias(self, slave_pos, alias):
+ slave = self.GetSlave(slave_pos)
+ if slave is not None:
+ slave_info = slave.getInfo()
+ slave_info.setAutoIncAddr(alias)
+ self.BufferConfig()
+
def GetSlaveType(self, slave_pos):
slave = self.GetSlave(slave_pos)
if slave is not None:
@@ -381,7 +420,6 @@
if slave is not None:
slave.setType(type_infos)
self.BufferConfig()
- return None
def GetSlaveInfos(self, slave_pos):
slave = self.GetSlave(slave_pos)
@@ -415,81 +453,51 @@
def GetModuleInfos(self, type_infos):
return self.PlugParent.GetModuleInfos(type_infos)
- def GetModulesByProfile(self, profile_type):
- return self.PlugParent.GetModulesByProfile(profile_type)
-
- def GetSlaveTypesLibrary(self):
- return self.PlugParent.GetModulesLibrary()
-
- def GetDeviceLocationTree(self, current_location, type_infos):
- vars = []
-
- device = self.GetModuleInfos(type_infos)
- if device is not None:
- sync_managers = []
- for sync_manager in device.getSm():
- sync_manager_control_byte = ExtractHexDecValue(sync_manager.getControlByte())
- sync_manager_direction = sync_manager_control_byte & 0x0c
- if sync_manager_direction:
- sync_managers.append(LOCATION_VAR_OUTPUT)
- else:
- sync_managers.append(LOCATION_VAR_INPUT)
-
- entries = device.GetEntriesList().items()
- entries.sort()
- for (index, subindex), entry in entries:
- var_size = self.GetSizeOfType(entry["Type"])
- if var_size is not None:
- var_class = VARCLASSCONVERSION.get(entry["PDOMapping"], None)
- if var_class is not None:
- if var_class == LOCATION_VAR_INPUT:
- var_dir = "%I"
- else:
- var_dir = "%Q"
-
- vars.append({"name": "0x%4.4x-0x%2.2x: %s" % (index, subindex, entry["Name"]),
- "type": var_class,
- "size": var_size,
- "IEC_type": entry["Type"],
- "var_name": "%s_%4.4x_%2.2x" % ("_".join(type_infos["device_type"].split()), index, subindex),
- "location": "%s%s%s"%(var_dir, var_size, ".".join(map(str, current_location +
- (index, subindex)))),
- "description": "",
- "children": []})
+ def GetSlaveTypesLibrary(self, profile_filter=None):
+ return self.PlugParent.GetModulesLibrary(profile_filter)
+
+ def GetDeviceLocationTree(self, slave_pos, current_location, device_name):
+ slave = self.GetSlave(slave_pos)
+ if slave is not None:
+ type_infos = slave.getType()
+
+ vars = []
+
+ device = self.GetModuleInfos(type_infos)
+ if device is not None:
+ sync_managers = []
+ for sync_manager in device.getSm():
+ sync_manager_control_byte = ExtractHexDecValue(sync_manager.getControlByte())
+ sync_manager_direction = sync_manager_control_byte & 0x0c
+ if sync_manager_direction:
+ sync_managers.append(LOCATION_VAR_OUTPUT)
+ else:
+ sync_managers.append(LOCATION_VAR_INPUT)
+
+ entries = device.GetEntriesList().items()
+ entries.sort()
+ for (index, subindex), entry in entries:
+ var_size = self.GetSizeOfType(entry["Type"])
+ if var_size is not None:
+ var_class = VARCLASSCONVERSION.get(entry["PDOMapping"], None)
+ if var_class is not None:
+ if var_class == LOCATION_VAR_INPUT:
+ var_dir = "%I"
+ else:
+ var_dir = "%Q"
+
+ vars.append({"name": "0x%4.4x-0x%2.2x: %s" % (index, subindex, entry["Name"]),
+ "type": var_class,
+ "size": var_size,
+ "IEC_type": entry["Type"],
+ "var_name": "%s_%4.4x_%2.2x" % ("_".join(device_name.split()), index, subindex),
+ "location": "%s%s%s"%(var_dir, var_size, ".".join(map(str, current_location +
+ (index, subindex)))),
+ "description": "",
+ "children": []})
return vars
- def GetVariableLocationTree(self):
- '''See PlugTemplate.GetVariableLocationTree() for a description.'''
-
- current_location = self.GetCurrentLocation()
-
- groups = []
- for slave_pos in self.GetSlaves():
-
- slave = self.GetSlave(slave_pos)
- if slave is not None:
- type_infos = slave.getType()
-
- vars = self.GetDeviceLocationTree(current_location + slave_pos, type_infos)
- if len(vars) > 0:
- groups.append({"name": "%s (%d,%d)" % ((type_infos["device_type"],) + slave_pos),
- "type": LOCATION_GROUP,
- "location": ".".join(map(str, current_location + slave_pos)) + ".x",
- "children": vars})
-
- return {"name": self.BaseParams.getName(),
- "type": LOCATION_PLUGIN,
- "location": self.GetFullIEC_Channel(),
- "children": groups}
-
- PluginMethods = [
- {"bitmap" : os.path.join("images", "EditCfile"),
- "name" : _("Edit Config"),
- "tooltip" : _("Edit Config"),
- "method" : "_OpenView"},
- ]
-
def PlugTestModified(self):
return self.ChangesToSave or not self.ConfigIsSaved()
@@ -548,14 +556,14 @@
for slave_pos in slaves:
slave = self.GetSlave(slave_pos)
if slave is not None:
- self.FileGenerator.DeclareSlave(slave_pos, slave.getType())
+ self.FileGenerator.DeclareSlave(slave_pos, slave.getInfo().getAutoIncAddr(), slave.getType())
for location in locations:
loc = location["LOC"][len(current_location):]
- slave_pos = loc[:2]
- if slave_pos in slaves:
+ slave_pos = loc[0]
+ if slave_pos in slaves and len(loc) == 3:
self.FileGenerator.DeclareVariable(
- slave_pos, loc[2], loc[3], location["IEC_TYPE"], location["DIR"], location["NAME"])
+ slave_pos, loc[1], loc[2], location["IEC_TYPE"], location["DIR"], location["NAME"])
return [],"",False
@@ -709,13 +717,11 @@
def __del__(self):
self.Controler = None
- def DeclareSlave(self, slave_identifier, slave):
- self.Slaves.append((slave_identifier, slave))
- self.Slaves.sort()
- return self.Slaves.index((slave_identifier, slave))
-
- def DeclareVariable(self, slave_identifier, index, subindex, iec_type, dir, name):
- slave_variables = self.UsedVariables.setdefault(slave_identifier, {})
+ def DeclareSlave(self, slave_index, slave_alias, slave):
+ self.Slaves.append((slave_index, slave_alias, slave))
+
+ def DeclareVariable(self, slave_index, index, subindex, iec_type, dir, name):
+ slave_variables = self.UsedVariables.setdefault(slave_index, {})
entry_infos = slave_variables.get((index, subindex), None)
if entry_infos is None:
@@ -752,12 +758,19 @@
for entry_infos in slave_entries.itervalues():
entry_infos["mapped"] = False
- for slave_idx, (slave_pos, type_infos) in enumerate(self.Slaves):
+ self.Slaves.sort()
+ alias = {}
+ for (slave_idx, slave_alias, type_infos) in self.Slaves:
+ if alias.get(slave_alias) is not None:
+ alias[slave_alias] += 1
+ else:
+ alias[slave_alias] = 0
+ slave_pos = (slave_alias, alias[slave_alias])
device = self.Controler.GetModuleInfos(type_infos)
if device is not None:
- slave_variables = self.UsedVariables.get(slave_pos, {})
+ slave_variables = self.UsedVariables.get(slave_idx, {})
device_entries = device.GetEntriesList()
if len(device.getTxPdo() + device.getRxPdo()) > 0 or len(slave_variables) > 0:
@@ -1306,39 +1319,45 @@
raise ValueError, "Not such group \"%\"" % device_group
vendor_category["groups"][device_group]["devices"].append((device.getType().getcontent(), device))
- def GetModulesLibrary(self):
+ def GetModulesLibrary(self, profile_filter=None):
library = []
children_dict = {}
for vendor_id, vendor in self.ModulesLibrary.iteritems():
groups = []
- library.append({"name": vendor["name"],
- "type": ETHERCAT_VENDOR,
- "children": groups})
for group_type, group in vendor["groups"].iteritems():
group_infos = {"name": group["name"],
"order": group["order"],
"type": ETHERCAT_GROUP,
+ "infos": None,
"children": children_dict.setdefault(group_type, [])}
- if group["parent"] is not None:
- parent_children = children_dict.setdefault(group["parent"], [])
- parent_children.append(group_infos)
- else:
- groups.append(group_infos)
device_dict = {}
for device_type, device in group["devices"]:
- device_infos = {"name": ExtractName(device.getName()),
- "type": ETHERCAT_DEVICE,
- "infos": {"device_type": device_type,
- "vendor": vendor_id,
- "product_code": device.getType().getProductCode(),
- "revision_number": device.getType().getRevisionNo()}}
- group_infos["children"].append(device_infos)
- device_type_occurrences = device_dict.setdefault(device_type, [])
- device_type_occurrences.append(device_infos)
+ if profile_filter is None or profile_filter in device.GetProfileNumbers():
+ device_infos = {"name": ExtractName(device.getName()),
+ "type": ETHERCAT_DEVICE,
+ "infos": {"device_type": device_type,
+ "vendor": vendor_id,
+ "product_code": device.getType().getProductCode(),
+ "revision_number": device.getType().getRevisionNo()},
+ "children": []}
+ group_infos["children"].append(device_infos)
+ device_type_occurrences = device_dict.setdefault(device_type, [])
+ device_type_occurrences.append(device_infos)
for device_type_occurrences in device_dict.itervalues():
if len(device_type_occurrences) > 1:
for occurrence in device_type_occurrences:
occurrence["name"] += _(" (rev. %s)") % occurrence["infos"]["revision_number"]
+ if len(group_infos["children"]) > 0:
+ if group["parent"] is not None:
+ parent_children = children_dict.setdefault(group["parent"], [])
+ parent_children.append(group_infos)
+ else:
+ groups.append(group_infos)
+ if len(groups) > 0:
+ library.append({"name": vendor["name"],
+ "type": ETHERCAT_VENDOR,
+ "infos": None,
+ "children": groups})
library.sort(lambda x, y: cmp(x["name"], y["name"]))
return library
@@ -1354,16 +1373,5 @@
revision_number == ExtractHexDecValue(type_infos["revision_number"])):
return device
return None
-
- def GetModulesByProfile(self, profile_type):
- modules = []
- for vendor_id, vendor in self.ModulesLibrary.iteritems():
- for group_type, group in vendor["groups"].iteritems():
- for device_type, device in group["devices"]:
- if profile_type in device.GetProfileNumbers():
- product_code = ExtractHexDecValue(device.getType().getProductCode())
- revision_number = ExtractHexDecValue(device.getType().getRevisionNo())
- modules.append((device_type, vendor_id, product_code, revision_number))
- return modules
-
-
+
+