84 lines
2.2 KiB
C#
84 lines
2.2 KiB
C#
|
using System.IO.Ports;
|
||
|
using InnovEnergy.Lib.Protocols.Modbus.Protocol;
|
||
|
|
||
|
namespace InnovEnergy.Lib.Protocols.Modbus.Connections;
|
||
|
|
||
|
public class ModbusSerialConnection : ModbusConnection
|
||
|
{
|
||
|
private String PortName { get; }
|
||
|
private Int32 BaudRate { get; }
|
||
|
private Parity Parity { get; }
|
||
|
private Int32 DataBits { get; }
|
||
|
private StopBits StopBits { get; }
|
||
|
private Int32 TimeoutMs { get; }
|
||
|
|
||
|
private Byte[] Buffer { get; } = new Byte[1024];
|
||
|
private SerialPort? _SerialPort;
|
||
|
|
||
|
public ModbusSerialConnection(String portName, Int32 baudRate, Parity parity, Int32 dataBits, StopBits stopBits, TimeSpan timeout)
|
||
|
{
|
||
|
PortName = portName;
|
||
|
BaudRate = baudRate;
|
||
|
Parity = parity;
|
||
|
DataBits = dataBits;
|
||
|
StopBits = stopBits;
|
||
|
TimeoutMs = (Int32) timeout.TotalMilliseconds;
|
||
|
}
|
||
|
|
||
|
|
||
|
public override IReadOnlyList<Byte> Receive(UInt16 bytesToRead)
|
||
|
{
|
||
|
var bytesReceived = 0;
|
||
|
var serialPort = SerialPort();
|
||
|
|
||
|
do
|
||
|
{
|
||
|
var received = serialPort.Read(Buffer, bytesReceived, Buffer.Length - bytesReceived);
|
||
|
if (received < 0)
|
||
|
throw new NotConnectedException("Serial Connection has been closed");
|
||
|
|
||
|
bytesReceived += received;
|
||
|
}
|
||
|
while (bytesReceived < bytesToRead);
|
||
|
|
||
|
return new ArraySegment<Byte>(Buffer, 0, bytesToRead);
|
||
|
}
|
||
|
|
||
|
public override void Transmit(IEnumerable<Byte> data)
|
||
|
{
|
||
|
var array = data.ToArray();
|
||
|
SerialPort().Write(array, 0, array.Length);
|
||
|
}
|
||
|
|
||
|
public override void Open() => SerialPort();
|
||
|
|
||
|
private SerialPort SerialPort()
|
||
|
{
|
||
|
if (_SerialPort == null)
|
||
|
{
|
||
|
_SerialPort = new SerialPort(PortName, BaudRate, Parity, DataBits, StopBits) { ReadTimeout = TimeoutMs, WriteTimeout = TimeoutMs};
|
||
|
_SerialPort.Open();
|
||
|
}
|
||
|
|
||
|
return _SerialPort;
|
||
|
}
|
||
|
|
||
|
public override void Close()
|
||
|
{
|
||
|
if (_SerialPort != null)
|
||
|
{
|
||
|
try
|
||
|
{
|
||
|
_SerialPort.Close();
|
||
|
_SerialPort?.Dispose();
|
||
|
}
|
||
|
catch (Exception)
|
||
|
{
|
||
|
// ignored
|
||
|
}
|
||
|
}
|
||
|
|
||
|
_SerialPort = null;
|
||
|
}
|
||
|
|
||
|
}
|