我使用Python 2.7.5向modbus tcp模拟器发送消息。我不明白为什么python在sendall上发送两次最后一个字节:
这是python脚本根据我的代码(下面)打印出来的......
S: 00020000000c1110000400030600790083008d
R: 000200000006111000040003
R: 8d0000000003d8f603
模拟器将此记录在哪里(从脚本接收TX并将RX发送到脚本)...
TX: 00020000000c1110000400030600790083008d
RX: 000200000006111000040003
TX: 8d
Modbus message in error x03
RX: 8d0000000003d8f603
所以问题是......为什么8d发送两次(根据modbus模拟器监听)?模拟器因为它而抛出错误...... 代码摘录:
def writeMultipleHoldingRegister(socket, transactionid, unitid, address,valuesToWrite):
TRANSACT_ID_BYTES = convertIntToBytes(int(transactionid))
DATA_ADDRESS_BYTES = convertIntToBytes(int(address))
FUNCTIONCODE_BYTES = '10'
NUMREGISTERS_BYTES = convertIntToBytes(len(valuesToWrite))
NUMBYTES = len(valuesToWrite)*2
NUMBYTES_BYTES = str(('%04X' % NUMBYTES)[2:4])
MESSAGE_LENGTH_BYTES = convertIntToBytes(int(6+(len(valuesToWrite)*2)))
modbustcp_write = (TRANSACT_ID_BYTES + '0000' + MESSAGE_LENGTH_BYTES + unitid + FUNCTIONCODE_BYTES + DATA_ADDRESS_BYTES + NUMREGISTERS_BYTES + NUMBYTES_BYTES).decode('hex')
for value in valuesToWrite:
modbustcp_write = modbustcp_write + convertIntToBytes(int(value)).decode('hex')
print 'S:', binascii.hexlify(modbustcp_write)
socket.sendall(modbustcp_write) #modbus tcp
data = socket.recv(12)
print 'R:', binascii.hexlify(data)
HOST = 'localhost'
PORT = 502
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((HOST, PORT))
writeMultipleHoldingRegister(s, 2, '11', 4, [121, 131, 141])
print 'R:', binascii.hexlify(s.recv(100))
s.close()
评论中留下了以下建议。 Process Monitor向我显示了流量,但没有显示字节本身。所以我下载并运行了RawCAP并在Wireshark中查看了输出。用来解释......在哪里' S'是由模拟器发送的' R'是模拟器收到的......
R: 00020000000c1110000400030600790083008d (modbus request recv)
S: 000200000006111000040003 (modbus ack good request sent)
S: 8d0000000003d8f603 (modbus error notification sent...wtf)
我从未见过' 8d'收到两次......所以我不知道这里发生了什么。也许是模拟器中的一个错误... http://www.plcsimulator.org/