下午好,
我正在维护一个遗留程序,该程序通过带有 VB.Net 代码的 RS-232 物理连接与 Modbus/RTU 现场设备进行交互。挑战在于,在用较新型号替换原始现场设备后,在设备寄存器复位(写入线圈 33,值 1)和特定浮点寄存器(40005 和 40006)实际复位到0。
作为我正在尝试做的一个示例,我将重置命令作为单个 modbus 消息发送到设备。之后,我将立即尝试读取该值以验证寄存器是否已被我的命令重置。如果寄存器被重置(在这种情况下,<= 1.0),我将使用基线“0”作为此后获得的任何读数。如果它没有被重置(这是一种故障保护),我将使用寄存器中剩余的任何值作为新的基线(相对“0”),用于之后获取的任何读数。
问题是在我发出重置命令后,设备将等待至少 200 毫秒以上的时间才能真正重置寄存器。这个延迟超过了我的程序读取有问题的寄存器并建立基线(0 或新的“相对 0”)所花费的时间。因此,错误变成我的程序将假定一个相对基线,然后在经过足够的毫秒后最终重置为 0。
例如,请参见下面的代码:
Function resetflowmeter()
Dim GallonSum(0) As Single
ResetFlag4 = False 'exit reset loop
FlowMeterWStatus = flowmeter.writeCoil(1, 33, 1) 'write "1" to reset flow meter register
FlowMeterRStatus = flowmeter.readMultipleFloats(1, 5, GallonSum, 1) 'read current total gallons
If FlowMeterWStatus = 0 Then 'if modbus response message is "good"
If FlowMeterRStatus = 0 Then 'if modbus response message is "good"
FlowMeterUpStat = True
If GallonSum(0) <= 1.0 Then 'if flowmeter gallons actually were reset to 0
ResetGallons = 0 'reset new period gallons to 0
End If
If GallonSum(0) > 1.0 Then 'if not actually reset, set to current total
ResetGallons = GallonSum(0)
End If
End If
End If
If FlowMeterWStatus <> 0 Then 'if reset attempt fails
If FlowMeterRStatus = 0 Then 'if good modbus response
ResetGallons = GallonSum(0) 'set to current sum
FlowMeterUpStat = True
End If
If FlowMeterRStatus <> 0 Then 'if read attempt fails
ResetGallons = 0
ResetFlag4 = True 'reenter reset loop
End If
End If
End Function
对于解决方案,我考虑插入大约 250-500 毫秒的延迟来弥补这一点。我不喜欢这个解决方案,因为它是任意的,实际上并没有给我一种机制来在继续执行程序之前检查响应。任何想法将不胜感激。