예제 #1
0
        private async Task <ushort[]> ReadModbusRegistersAsync()
        {
            AllData = await _master.ReadHoldingRegistersAsync(WTX_SLAVE_ADDRESS, WTX_REGISTER_START_ADDRESS, WTX_REGISTER_DATAWORD_COUNT);

            CommunicationLog?.Invoke(this, new LogEventArgs("Read all: " + string.Join(",", AllData.Select(x => x.ToString("X")).ToArray())));
            return(AllData);
        }
예제 #2
0
        public static async Task <T> QueryHeliosValue <T>(this IModbusMaster modbus, VariableDeclaration <T> parameter)
        {
            Log.Debug($"Querying {parameter.Code}...");
            var bytes   = Encoding.ASCII.GetBytes($"{parameter.Code}\0");
            var ushorts = ToUShortArray(bytes);

            await modbus.WriteMultipleRegistersAsync(HeliosDefaults.SlaveAddress, HeliosDefaults.Offset, ushorts);

            var result =
                await modbus.ReadHoldingRegistersAsync(HeliosDefaults.SlaveAddress,
                                                       HeliosDefaults.Offset,
                                                       parameter.RegisterCount);

            bytes = FromShortArray(result);
            var decoded = Encoding.ASCII.GetString(bytes);

            Log.Debug($"Decoded: {decoded}");

            if (TryExtractValue(parameter.Code, decoded, out var value))
            {
                Log.Debug($"Trying to convert {value} to {typeof(T)}");
                return((T)Convert.ChangeType(value, typeof(T)));
            }

            return(default);
예제 #3
0
        public async Task <IQueryResult <ushort[]> > ReadHoldingResgistersAsync(ushort startAddress, ushort numberOfPoints, string dataTitle)
        {
            IQueryResult <ushort[]> queryResult = _queryResultFactory.CreateDefaultQueryResult <ushort[]>();

            if (!CheckConnection(queryResult))
            {
                return(queryResult);
            }
            try
            {
                queryResult.Result = await _currentModbusMaster.ReadHoldingRegistersAsync(_slaveId, startAddress, numberOfPoints);

                List <string> results = queryResult.Result.Select((arg => arg.ToString())).ToList();
                string        resStr  = "";
                foreach (var res in results)
                {
                    resStr += res;
                    resStr += " ";
                }
                queryResult.IsSuccessful = true;
            }
            catch (Exception e)
            {
                queryResult.IsSuccessful = false;
            }
            return(queryResult);
        }
예제 #4
0
        private async Task <ushort[]> TryExecuteReadQuery(ushort startAddress, ushort numberOfPoints)
        {
            try
            {
                await _semaphoreSlim.WaitAsync();

                if (!LastTransactionSucceed)
                {
                    throw new Exception("");
                }
                ushort[] bytes = await _modbusMaster.ReadHoldingRegistersAsync(1, startAddress, numberOfPoints);

                _semaphoreSlim.Release();
                return(bytes);
            }
            catch (Exception e)
            {
                _semaphoreSlim.Release();
                for (int i = 0; i < 2; i++)
                {
                    await OpenConnectionSession(true);

                    if (LastTransactionSucceed)
                    {
                        break;
                    }
                }
                if (!LastTransactionSucceed)
                {
                    throw;
                }
                return(await TryExecuteReadQuery(startAddress, numberOfPoints));
            }
        }
예제 #5
0
        //public async Task<IEnumerable<MqttInlineRegisterJsonModel>> ReadModbusToArray(SlaveInfoYaml slaves)
        //{
        //    ushort minAddr = slaves.registers.Min(x => x.address);
        //    ushort maxAddr = slaves.registers.Max(x => x.address);
        //    minAddr = (ushort)(minAddr - 1);
        //    ushort pointCnt = (ushort)((maxAddr - minAddr) + 1);
        //    ushort[] datas = null;
        //    lock (lockerObj)
        //    {
        //        switch (slaves.io_type)
        //        {
        //            case DataModel.modbus_io.ANALOG_INPUT:
        //                datas = master.ReadInputRegisters(slaves.deviceId, minAddr, pointCnt);
        //                break;
        //            case DataModel.modbus_io.HOLDING_REGISTER:
        //                datas = master.ReadHoldingRegisters(slaves.deviceId, minAddr, pointCnt);
        //                break;
        //        }
        //        Console.WriteLine("READ MODBUS_INPUT_REGISTER");
        //    }

        //    DateTime timeStamp = DateTime.Now;
        //    List<MqttRegisterJsonModel> registers = new List<MqttRegisterJsonModel>();
        //    foreach (SlaveInfoRegisterYaml register in slaves.registers)
        //    {
        //        Console.WriteLine("READ REGISTER: " + register.name);
        //        int addr = (register.address - 1) - minAddr;
        //        byte[] buffer = GetReadBytes(register, addr, datas);
        //        object value = 0f;
        //        switch (register.type)
        //        {
        //            case DataModel.modbus_type.DT_SIGNED:
        //                if (register.length > 1)
        //                    value = BitConverter.ToInt32(buffer);
        //                else
        //                    value = BitConverter.ToInt16(buffer);
        //                break;
        //            case modbus_type.DT_UNSIGNED:
        //                if (register.length > 1)
        //                    value = BitConverter.ToUInt32(buffer);
        //                else
        //                    value = BitConverter.ToUInt16(buffer);
        //                break;
        //            case modbus_type.DT_FLOAT:
        //                value = BitConverter.ToSingle(buffer);
        //                break;
        //        }
        //        registers.Add(register.CreateJsonModel(value));
        //        //registers.Add(register.ConvertRegister(Convert.ToSingle(value)));
        //    }
        //    parent.Registers = registers.ToArray();
        //    return parent;
        //}

        public async Task <List <DiMap> > ReadModbusEvent(EventGroupPoint map)
        {
            List <DiMap> result = new List <DiMap>();

            if (master == null)
            {
                return(result);
            }
            ushort[] datas = await master.ReadHoldingRegistersAsync(_config.SlaveId, map.StartAddress, (ushort)map.DigitalPoints.Count);

            int idx = 0;

            foreach (DiMap m in map.DigitalPoints)
            {
                m.Value = datas[idx++];
                result.Add(m);
            }
            return(result);
        }
        public async Task <SensorRecord> ReadSensorRecord()
        {
            ushort[] inputs = await modbusMaster.ReadHoldingRegistersAsync(AppConfig.SlaveAddress, Sensor.StartAddress, Sensor.NumberOfPoints);

            return(new SensorRecord()
            {
                RecordedOn = DateTimeOffset.Now,
                SensorName = Sensor.Name,
                SensorValue = inputs.ToFloat()
            });
        }
예제 #7
0
        public async Task TestHoldingRegisters()
        {
            var           factory = new ModbusFactory();
            IModbusMaster modbus  = factory.CreateMaster(_client);
            await _client.ConnectAsync(MODBUS_IP, MODBUS_PORT);

            ushort[] data = await modbus.ReadHoldingRegistersAsync(MODBUS_SLAVE, 0, 5);

            Assert.Equal(5, data.Length);
            await modbus.WriteMultipleRegistersAsync(MODBUS_SLAVE, 0, new ushort[] { 1, 2, 3, 4, 5 });

            data = await modbus.ReadHoldingRegistersAsync(MODBUS_SLAVE, 0, 5);

            Assert.Equal(5, data.Length);
            Assert.Equal(new ushort[] { 1, 2, 3, 4, 5 }, data);
            await modbus.WriteMultipleRegistersAsync(MODBUS_SLAVE, 0, new ushort[] { 0, 0, 0, 0, 0 });

            data = await modbus.ReadHoldingRegistersAsync(MODBUS_SLAVE, 0, 5);

            Assert.Equal(5, data.Length);
            Assert.Equal(new ushort[] { 0, 0, 0, 0, 0 }, data);
        }
예제 #8
0
        public async Task TestHoldingRegister()
        {
            var           factory = new ModbusFactory();
            IModbusMaster modbus  = factory.CreateMaster(_client);
            await _client.ConnectAsync(MODBUS_IP, MODBUS_PORT);

            ushort[] data = await modbus.ReadHoldingRegistersAsync(MODBUS_SLAVE, 0, 1);

            Assert.Single(data);
            await modbus.WriteSingleRegisterAsync(MODBUS_SLAVE, 0, 1);

            data = await modbus.ReadHoldingRegistersAsync(MODBUS_SLAVE, 0, 1);

            Assert.Single(data);
            Assert.Equal(1, data[0]);
            await modbus.WriteSingleRegisterAsync(MODBUS_SLAVE, 0, 0);

            data = await modbus.ReadHoldingRegistersAsync(MODBUS_SLAVE, 0, 1);

            Assert.Single(data);
            Assert.Equal(0, data[0]);
        }
예제 #9
0
        private async Task <ushort[]> TryExecuteReadQuery(ushort startAddress, ushort numberOfPoints)
        {
            try
            {
                await _semaphoreSlim.WaitAsync();

                if (!LastTransactionSucceed)
                {
                    throw new Exception("");
                }
                ushort[] bytes = await _modbusMaster.ReadHoldingRegistersAsync(1, startAddress, numberOfPoints);

                _semaphoreSlim.Release();
                return(bytes);
            }
            catch (StackOverflowException s)
            {
                throw;
            }
            catch (Exception e)
            {
                _semaphoreSlim.Release();
                if (!LastTransactionSucceed)
                {
                    throw;
                }

                //_modbusMaster.Dispose();
                //OpenConnectionSession(false);

                //for (loopIterator = 0; loopIterator < 2; loopIterator++)
                //{
                //    if (LastTransactionSucceed) break;
                //    await OpenConnectionSession(true);
                //}
                //loopIterator = 0;

                return(null);

                //return await TryExecuteReadQuery(startAddress, numberOfPoints);
            }
        }
예제 #10
0
        public Task <ushort[]> ReadHoldingRegistersAsync(byte slaveAddress, ushort startAddress, ushort numberOfPoints, ushort blockSize, CancellationToken cancellationToken)
        {
            return(PerformFuncAsync(async() =>
            {
                List <ushort> registers = new List <ushort>(numberOfPoints);

                int soFar = 0;
                int thisRead = blockSize;

                while (soFar < numberOfPoints)
                {
                    //If we're _not_ on the first run through here, wait for the min time
                    if (soFar > 0)
                    {
                        await Task.Delay(_minInterval, cancellationToken);
                    }

                    //Check to see if we've ben cancelled
                    cancellationToken.ThrowIfCancellationRequested();

                    if (thisRead > (numberOfPoints - soFar))
                    {
                        thisRead = numberOfPoints - soFar;
                    }

                    //Perform this operation
                    ushort[] registersFromThisRead = await _master.ReadHoldingRegistersAsync(slaveAddress, (ushort)(startAddress + soFar), (ushort)thisRead);

                    //Add these to the result
                    registers.AddRange(registersFromThisRead);

                    //Increment where we're at
                    soFar += thisRead;
                }

                return registers.ToArray();
            }, cancellationToken));
        }
예제 #11
0
        public async Task <IQueryResult <ushort[]> > ReadHoldingResgistersAsync(ushort startAddress, ushort numberOfPoints,
                                                                                string dataTitle)
        {
            await _semaphoreSlim.WaitAsync();

            IQueryResult <ushort[]> queryResult = _queryResultFactory.CreateDefaultQueryResult <ushort[]>();

            if (!CheckConnection(queryResult))
            {
                return(queryResult);
            }
            try
            {
                queryResult.Result =
                    await _currentModbusMaster.ReadHoldingRegistersAsync(_slaveId, startAddress, numberOfPoints);

                List <string> results = queryResult.Result.Select((arg => arg.ToString())).ToList();
                string        resStr  = "";
                foreach (string res in results)
                {
                    resStr += res;
                    resStr += " ";
                }

                LogQuery(true, dataTitle,
                         "Fun:3" + " Addr:" + startAddress + " Num:" + numberOfPoints + " Data:" + resStr);
                queryResult.IsSuccessful = true;
            }
            catch (Exception e)
            {
                LogQuery(false, dataTitle, "Fun:3" + " Addr:" + startAddress + " Num:" + numberOfPoints, exception: e);
                queryResult.IsSuccessful = false;
                queryResult.AddExeption(e);
            }

            _semaphoreSlim.Release(1);
            return(queryResult);
        }
예제 #12
0
        /// <inheritdoc/>
        public async Task <byte[]> Read(Register register)
        {
            MakeSureClientIsConnected();

            _logger.Information($"Getting data from slave {register.Unit} startingAdress {register.StartingAddress} size {register.Size} as DataType {Enum.GetName(typeof(DataType), register.DataType)}");

            ushort[] result;

            var size = Convert.ToUInt16(register.Size * GetDataSizeFrom(register.DataType));

            try
            {
                switch (register.FunctionCode)
                {
                case FunctionCode.HoldingRegister:
                    result = await _master.ReadHoldingRegistersAsync(register.Unit, register.StartingAddress, size);

                    break;

                case FunctionCode.InputRegister:
                    result = await _master.ReadInputRegistersAsync(register.Unit, register.StartingAddress, size);

                    break;

                default:
                    result = new ushort[0];
                    break;
                }
                var bytes = result.GetBytes(_configuration.Endianness);
                return(bytes);
            }
            catch (Exception ex)
            {
                _logger.Error(ex, $"Trouble reading register {register}");
                return(null);
            }
        }
예제 #13
0
        internal static async Task <ushort[]> GetDataByAddress(byte numOfDevice, ushort address, ushort value,
                                                               bool isQueryCritical = true)
        {
            if (_modbusMaster != null)
            {
                await _semaphoreSlim.WaitAsync();

                OnWritingStartedAction?.Invoke();
                try
                {
                    ushort[] result;
                    result = await _modbusMaster.ReadHoldingRegistersAsync(numOfDevice, address, value);

                    _semaphoreSlim.Release(1);
                    return(result);
                }
                catch (Exception e)
                {
                    _semaphoreSlim.Release(1);
                    if (isQueryCritical)
                    {
                        ConnectionLostAction?.Invoke();
                    }
                    throw e;
                }
                finally
                {
                    //_semaphoreSlim.Release();
                    OnWritingCompleteAction?.Invoke();
                }
            }
            else
            {
                throw new Exception("Не инициализирован объект связи");
            }
        }
예제 #14
0
 public async Task <ushort[]> ReadHoldingRegisters(ushort startAddress, ushort pointCount)
 {
     return(await m_modbusConnection.ReadHoldingRegistersAsync(m_unitID, startAddress, pointCount));
 }