You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

三菱FX5UC PLC使用MC协议0406命令批量读取D寄存器问题

三菱FX5UC PLC MC协议0406多块读取命令帧格式问题

我使用三菱FX5UC-32MT/DSS-TS PLC,尝试通过MC协议的0406命令(QnA兼容3E帧多块批量读取)读取多个D寄存器。目前0401命令可成功单次读取单个寄存器,但需要优化为单次请求读取多块数据。参考相关教程及MELSEC通信协议手册后,仍无法正确构建0406命令的二进制帧。

现有简化版代码

多寄存器读取方法

Private Sub MultiReadDataRegister(rdAddressTextBox As TextBox, disTextBox As TextBox, rdValue As TextBox)
    Dim DeviceNo_D As String
    Dim DeviceNo2_D As String
    Dim DeviceNo15_D As String
    Dim DeviceNo16_D As String
    Dim DeviceNo17_D As String

    DeviceNo_D = rdAddressTextBox.Text

    If String.IsNullOrWhiteSpace(DeviceNo_D) OrElse Val(DeviceNo_D) < 0 Then
        rdAddressTextBox.Text = "0"
    Else
        DeviceNo_D = rdAddressTextBox.Text
    End If

    DeviceNo_D = rdAddressTextBox.Text
    DeviceNo2_D = Hex(DeviceNo_D).PadLeft(6, "0").Substring(0, 6)
    DeviceNo15_D = DeviceNo2_D.Substring(4, 2)
    DeviceNo16_D = DeviceNo2_D.Substring(2, 2)
    DeviceNo17_D = DeviceNo2_D.Substring(0, 2)

    Dim sendmessage4(22) As String
    'Binary Code
    
    sendmessage4(0) = "50" 'Subheader -  Set the fixed value (request message: '5000', response message: 'D000')
    sendmessage4(1) = "00" 'Subheader -  Set the fixed value (request message: '5000', response message: 'D000')
    sendmessage4(2) = "00" 'NetWork No.
    sendmessage4(3) = "FF" 'Pc No.
    sendmessage4(4) = "FF" 'Request destination module I/O No.
    sendmessage4(5) = "03" 'Request destination module I/O No.
    sendmessage4(6) = "00" 'Request destination Module station No
    sendmessage4(7) = "0C" 'Requested Data Length 
    sendmessage4(8) = "00" 'Requested Data Length
    sendmessage4(9) = "10"  'Monitoring timer    
    sendmessage4(10) = "00" 'Monitoring timer    
    sendmessage4(11) = "06" 'Command      
    sendmessage4(12) = "04" 'Command      
    sendmessage4(13) = "00" 'SubCommand   
    sendmessage4(14) = "00" 'SubCommand
    sendmessage4(15) = "02" 'Number of word device blocks   
    sendmessage4(16) = "00" 'Number of bit device blocks
    sendmessage4(17) = DeviceNo15_D
    sendmessage4(18) = DeviceNo16_D
    sendmessage4(19) = DeviceNo17_D
    sendmessage4(20) = "A8" 'Device Code in Hexadecimal format. It indicate Data register D^*
    sendmessage4(21) = "02" 'Number of Device Points to Read - Low byte Example: user input is D200 so it implies 3 consecutive device points, possibly D200,D201,D202 
    'sendmessage4(22) = "00" 'Number of Device Points to Read - High byte

    'Socket connected then it send And recive the message
    If _socket.Connected Then
        Dim bytereceiveMessage4 = SendAndReceive(sendmessage4)

        If bytereceiveMessage4 IsNot Nothing Then

            Dim arrays As Byte() = {bytereceiveMessage4(11), bytereceiveMessage4(12)}

            rdValue.Text = BitConverter.ToUInt16(arrays, 0)


            If rdValue.Text = 0 Then
                rdValue.BackColor = Color.Blue
                rdValue.ForeColor = Color.White
            Else
                rdValue.BackColor = Color.White
                rdValue.ForeColor = Color.Black
            End If

            disTextBox.Text = rdValue.Text / 10
        End If
    End If

End Sub

Socket通信辅助函数

Private Function SendAndReceive(sendMessage As String()) As Byte()
    Dim byteSendMessage As Byte() = StringsToBytes(sendMessage)
    _socket.Send(byteSendMessage, byteSendMessage.GetLength(0), SocketFlags.None)
    Dim byteReceiveMessage As Byte()
    Dim ReceiveSize As Integer = 0
    Do
        byteReceiveMessage = New Byte(_socket.Available - 1) {}
        ReceiveSize =
            _socket.Receive(byteReceiveMessage, byteReceiveMessage.GetLength(0), SocketFlags.None)

    Loop While ReceiveSize = 0
    Return byteReceiveMessage
End Function

Private Function StringsToBytes(src() As String) As Byte()
     Dim returnBytes(src.Length - 1) As Byte

     Dim i As Integer
     For i = 0 To src.Length - 1
         returnBytes(i) = Convert.ToByte(src(i), 16)
     Next

     Return returnBytes
End Function

已尝试操作

  • 实现VB.NET Socket通信程序,发送3E帧执行0406多块批量读取命令
  • 手动构建二进制帧,包含子头、网络站号、命令码及设备地址格式
  • 验证PLC处于RUN模式且MC协议通信已启用
  • 使用0401命令测试单块批量读取,可正常读取单个D寄存器

预期与实际结果

预期结果:PLC返回单个响应帧,包含多个D寄存器(如D200、D201、D202)的数据,以便高效解析展示。

实际情况:Socket有时会收到非有效数据帧,例如:

0 - 208
1 - 0
2 - 0
3 - 255
4 - 255
5 - 3
6 - 0
7 - 11
8 - 0
9 - 97
10 - 192
11 - 0
12 - 255
13 - 255
14 - 3
15 - 0
16 - 6
17 - 4
18 - 0
19 - 0

怀疑问题源于帧格式错误,请求协助排查并修正。


内容的提问来源于stack exchange,提问作者user31209074

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.12 13:44:55