提问人:Akbarali Otakhanov 提问时间:9/7/2023 更新时间:9/7/2023 访问量:41
对象引用未设置为对象 System.IO.Ports 的实例
Object reference not set to an instance of an object System.IO.Ports
问:
我们使用 LattePanda 在 .Net Framework 上创建了一个桌面应用程序,以使用 RS485 通信协议从 PCB 读取传感器数据。在 c# 部分,我们使用了 EasyModbus 库来读取数据。该应用程序在某种程度上运行良好,但在某些时候它抛出以下错误:
Object reference not set to an instance of an object.
at System.IO.Ports.SerialStream.EventLoopRunner.CallReceiveEvents(Object state)
at System.Threading.QueueUserWorkItemCallback.Execute()
at System.Threading.ThreadPoolWorkQueue.Dispatch()
at System.Threading.PortableThreadPool.WorkerThread.WorkerThreadStart()
在下面的文章中,您可以看到用于创建 ModbusClient 对象和 ReadInputRegisters() 方法的 c# 代码。我们找不到终止的原因。
private readonly SemaphoreSlim _lock = new (1, 1);
private static ModbusClient CreateAndConnectClient(string comPort, int baudrate, byte unitIdentifier)
{
try
{
ModbusClient modbusClient = new(comPort)
{
UnitIdentifier = unitIdentifier,
Baudrate = baudrate,
Parity = Parity.None,
StopBits = StopBits.One,
ConnectionTimeout = 1000
};
modbusClient.Connect();
return modbusClient;
}
catch (ModbusException ex) {
Trace.WriteLine("ModbusException: " + ex.Message);
throw;
}
catch (Exception ex)
{
Trace.WriteLine("Unhandled Exception: " + ex.Message);
throw;
}
}
public async Task<int[]> ReadInputRegistersAsync(string comPort, int baudrate, byte unitIdentifier, int startAddress, int quantity)
{
await _lock.WaitAsync();
ModbusClient? modbusClient = null;
try
{
// Attempt to create and connect the Modbus client
modbusClient = CreateAndConnectClient(comPort, baudrate, unitIdentifier);
// Check if the client was successfully created and connected
// to avoid Exception --> "Object reference not set to an instance of an object"
if (modbusClient == null)
{
Trace.WriteLine("ModbusClient is null.");
return new int[quantity];
}
var data = modbusClient.ReadInputRegisters(startAddress, quantity) ?? new int[quantity];
return data;
}
catch (ModbusException ex)
{
Trace.WriteLine("ModbusException in ReadInputRegistersAsync: " + ex.Message);
// Return a new empty integer array
return new int[quantity];
}
catch (Exception ex)
{
Trace.WriteLine("Unhandled Exception in ReadInputRegistersAsync: " + ex.Message);
return new int[quantity];
}
finally
{
if (modbusClient!=null && modbusClient.Connected)
{
modbusClient.Disconnect();
}
_lock.Release();
}
}
然后在下面的类中,我们调用了 ReadInputRegistersAsync()
public List<RawInput> GetData(DateTime date)
{
var data = new List<RawInput>();
var items = GetSensors();
var groupeItems = items.GroupBy(i => i.SlaveID).ToList();
foreach (var itemGroup in groupeItems)
{
var sensors = itemGroup.ToList();
var sensor = sensors.OrderBy(i => i.InputCh).LastOrDefault();
if (sensor == null) continue;
var readTask = modbusManager.ReadInputRegistersAsync(
$"COM{sensor.SerPort}", 9600, (byte)itemGroup.Key, 0, sensor.InputCh);
Trace.WriteLine("^^^^^^^^^^^^^^^^^^^ READ TASK SlaveID: " + (byte)itemGroup.Key);
readTask.ContinueWith(task =>
{
if (task.IsCompletedSuccessfully)
{
var list = task.Result.ToList();
data.AddRange(sensors.ConvertAll(s =>
new RawInput()
{
ItemId = s.Id,
RawValue = list[s.InputCh - 1]
}
));
}
else
{
Trace.WriteLine("^^^^^^^^^^^^^^^^^^^ READ TASK IS NOT COMPLETED SUCCESSFULLY");
data.AddRange(sensors.ConvertAll(s => new RawInput()
{
ItemId = s.Id,
RawValue = 0
}));
}
}).Wait();
}
return data;
}
答: 暂无答案
评论