private static void SortReadInfoDevices(SlaveReadInfo readInfo) { readInfo.Coils.Sort(); readInfo.Contacts.Sort(); Comparison <KeyValuePair <ushort, int> > comparison = (c1, c2) => { if (c1.Key > c2.Key) { return(1); } if (c1.Key < c2.Key) { return(-1); } if (c1.Value > c2.Value) { return(-1); } if (c1.Value < c2.Value) { return(1); } return(0); }; readInfo.InputRegisters.Sort(comparison); readInfo.HoldingRegisters.Sort(comparison); }
public object[] ReadOnce(ReadParameter[] readParameters) { if (readParameters == null) { return(null); } var values = new List <object>(); Dictionary <byte, SlaveReadInfo> readInfos; List <KeyValuePair <ReadParameter, byte?> > readParamSlaveAddresses; GetParametersReadInfo(readParameters, out readInfos, out readParamSlaveAddresses); var result = new Dictionary <byte, SlaveReadResult>(); foreach (var slaveReadInfo in readInfos) { byte slaveAddress = slaveReadInfo.Key; var r = new SlaveReadResult(); result.Add(slaveAddress, r); SlaveReadInfo readInfo = slaveReadInfo.Value; SortReadInfoDevices(readInfo); r.CoilsData = new Dictionary <ushort, bool>(readInfo.Coils.Count); r.ContactsData = new Dictionary <ushort, bool>(readInfo.Contacts.Count); r.InputRegistersData = new Dictionary <KeyValuePair <ushort, int>, byte[]>(readInfo.InputRegisters.Count); r.HoldingRegistersData = new Dictionary <KeyValuePair <ushort, int>, byte[]>(readInfo.HoldingRegisters.Count); ReadBits(readInfo.Coils, slaveAddress, r.CoilsData, _mb.ReadCoils, "discrete coils"); ReadBits(readInfo.Contacts, slaveAddress, r.ContactsData, _mb.ReadContacts, "discrete contacts"); ReadRegisters(readInfo.InputRegisters, slaveAddress, r.InputRegistersData, _mb.ReadInputRegisters, "input registers"); ReadRegisters(readInfo.HoldingRegisters, slaveAddress, r.HoldingRegistersData, _mb.ReadHoldingRegisters, "holding registers"); } foreach (var k in readParamSlaveAddresses) { if (k.Value == null) { values.Add(null); continue; } byte slaveAddress = k.Value.Value; SlaveReadResult r; if (!result.TryGetValue(slaveAddress, out r)) { values.Add(null); continue; } SlaveReadInfo slaveReadInfo; if (readInfos.TryGetValue(slaveAddress, out slaveReadInfo)) { ReadParameter readParameter = k.Key; ushort bitAddress; KeyValuePair <ushort, int> registerAddress; if (slaveReadInfo.CoilsAddresses.TryGetValue(readParameter, out bitAddress)) { bool value; if (r.CoilsData.TryGetValue(bitAddress, out value)) { values.Add(value); } else { values.Add(null); } } else if (slaveReadInfo.ContactsAddresses.TryGetValue(readParameter, out bitAddress)) { bool value; if (r.ContactsData.TryGetValue(bitAddress, out value)) { values.Add(value); } else { values.Add(null); } } else if (slaveReadInfo.InputRegistersAddresses.TryGetValue(readParameter, out registerAddress)) { byte[] value; values.Add(r.InputRegistersData.TryGetValue(registerAddress, out value) ? GetValue(value, readParameter.ValueType) : null); } else if (slaveReadInfo.HoldingRegistersAddresses.TryGetValue(readParameter, out registerAddress)) { byte[] value; values.Add(r.HoldingRegistersData.TryGetValue(registerAddress, out value) ? GetValue(value, readParameter.ValueType) : null); } } else { values.Add(null); } } return(values.ToArray()); }
private void GetParametersReadInfo( IEnumerable <ReadParameter> parameters, out Dictionary <byte, SlaveReadInfo> infos, out List <KeyValuePair <ReadParameter, byte?> > paramSlaveReadAddresses) { infos = new Dictionary <byte, SlaveReadInfo>(); var readParameters = parameters as ReadParameter[] ?? parameters.ToArray(); paramSlaveReadAddresses = new List <KeyValuePair <ReadParameter, byte?> >(readParameters.Count()); foreach (ReadParameter parameter in readParameters) { var regex = new Regex(DevicePattern); Match match = regex.Match(parameter.Address); if (!match.Success) { throw new Exception(parameter.Address + " is not a valid device address"); } #region Get slave address byte slaveAddress = _defaultAddress; string match1 = match.Groups[1].ToString(); if (!string.IsNullOrEmpty(match1) && match1.Length > 1) { int i; if (int.TryParse(match1.Substring(0, match1.Length - 1), out i)) { if (i >= byte.MinValue && i <= byte.MaxValue) { slaveAddress = (byte)i; } else { throw new Exception(parameter.Address + ": slave address incorrect"); } } } paramSlaveReadAddresses.Add(new KeyValuePair <ReadParameter, byte?>(parameter, slaveAddress)); #endregion Get slave address #region Get device address ushort deviceAddress; if (!ushort.TryParse(match.Groups[3].ToString(), out deviceAddress) || deviceAddress == 0) { throw new Exception(parameter.Address + ": device index not supported"); } deviceAddress -= 1; string match2 = match.Groups[2].ToString(); int? length; if (parameter.ValueType == typeof(bool)) { if (match2 != "0" && match2 != "1") { throw new Exception( "Type " + parameter.ValueType.Name + " is not supported for" + parameter.Address); } length = 1; } else { if (match2 != "3" && match2 != "4") { throw new Exception( "Type " + parameter.ValueType.Name + " is not supported for" + parameter.Address); } length = TypeToRegistersCount(parameter.ValueType); if (length == null) { throw new Exception( "Type " + parameter.ValueType.Name + " is not supported for" + parameter.Address); } } #endregion Get device address #region Check device index int deviceLength = length.Value; if (deviceLength + deviceAddress - 1 > ushort.MaxValue) { throw new Exception(parameter.Address + ": device index is out of range"); } #endregion Check device index #region ReadInfo SlaveReadInfo readInfo; if (!infos.TryGetValue(slaveAddress, out readInfo)) { readInfo = new SlaveReadInfo(); infos.Add(slaveAddress, readInfo); } #endregion ReadInfo #region Fill ReadInfo switch (match2) { case "0": if (!readInfo.Coils.Contains(deviceAddress)) { readInfo.Coils.Add(deviceAddress); } readInfo.CoilsAddresses.Add(parameter, deviceAddress); break; case "1": if (!readInfo.Contacts.Contains(deviceAddress)) { readInfo.Contacts.Add(deviceAddress); } readInfo.ContactsAddresses.Add(parameter, deviceAddress); break; case "3": var ir = new KeyValuePair <ushort, int>(deviceAddress, deviceLength); if (!readInfo.InputRegisters.Contains(ir)) { readInfo.InputRegisters.Add(ir); } readInfo.InputRegistersAddresses.Add(parameter, ir); break; case "4": var hr = new KeyValuePair <ushort, int>(deviceAddress, deviceLength); if (!readInfo.HoldingRegisters.Contains(hr)) { readInfo.HoldingRegisters.Add(hr); } readInfo.HoldingRegistersAddresses.Add(parameter, hr); break; } #endregion Fill ReadInfo } }