Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Inconsistent operation with RTU client #1669

Closed
gnawdog opened this issue Jul 19, 2023 · 3 comments · Fixed by #1674
Closed

Inconsistent operation with RTU client #1669

gnawdog opened this issue Jul 19, 2023 · 3 comments · Fixed by #1674

Comments

@gnawdog
Copy link

gnawdog commented Jul 19, 2023

Versions

  • Python: 3.10.4
  • OS: macOS 10.13.6
  • Pymodbus: 3.3.2
  • Modbus Hardware: USB RS485 adapter communicating with a motor controller

Pymodbus Specific

  • Client: rtu - async

Description

A motor controller that I am trying to communicate with recognizes three commands; read holding registers, read input registers, and write holding registers. I have had inconsistent results with all three, sometimes they work, sometimes not. My hunch is that the problem is related to the fact that all the bytes transmitted are always echoed back as received data. The code that I have included reliably reads five input registers, but fails when reading four. I attached a second USB-RS485 adapter in order to monitor all the traffic on the RS485 bus and from that data stream everything looks exactly right. The response from the motor controller is correct, but pymodbus fails with a timeout error.

Code

import sys
import pymodbus
print('Python version:  ',sys.version.split(' ')[0])
print('pymodbus version:',pymodbus.__version__)
print('macOS High Sierra 10.13.6')

import asyncio
from pymodbus.client.serial import AsyncModbusSerialClient as ModbusClient

import logging
logging.basicConfig()
log = logging.getLogger()
log.setLevel(logging.DEBUG)

async def main():
    client = ModbusClient( method='rtu'
                         , port='/dev/cu.usbserial-AB0KJMPA'
                         , baudrate=19200
                         , bytesize=8, parity='N', stopbits=2
                         , handle_local_echo=True
                         , strict=False
                         , timeout=2
                         )
    await client.connect()
    for n in [5,4]:
        print('\nread %d input registers **********'%n)
        res = await client.read_input_registers( address=0
                                               , count=n
                                               , slave=1 )
        print('input register data:')
        for rv in res.registers:
            print('\t',rv)
    client.close()

if __name__ == "__main__":
    asyncio.run(main())

Log

Python version:   3.10.4
pymodbus version: 3.3.2
macOS High Sierra 10.13.6
DEBUG:asyncio:Using selector: KqueueSelector
DEBUG:pymodbus.logging:Connecting to None.
DEBUG:pymodbus.logging:Connecting comm
DEBUG:pymodbus.logging:Connected to comm

read 5 input registers **********
DEBUG:pymodbus.logging:send: 0x1 0x4 0x0 0x0 0x0 0x5 0x30 0x9
DEBUG:pymodbus.logging:Adding transaction 1
DEBUG:pymodbus.logging:recv: 0x1 0x4 0x0 0x0 0x0 0x5 0x30 0x9
DEBUG:pymodbus.logging:recv: 0x1 0x4 0x0 0x0 0x0 0x5 0x30 0x9
DEBUG:pymodbus.logging:Frame check failed, ignoring!!
DEBUG:pymodbus.logging:Resetting frame - Current Frame in buffer - 0x1 0x4 0x0 0x0 0x0 0x5 0x30 0x9
DEBUG:pymodbus.logging:Frame - [b'\x01\x04\x00\x00\x00\x050\t'] not ready
DEBUG:pymodbus.logging:recv: 0x1 0x4 0xa 0xf0 0x0 0xf0 0x1 0xf0 0x2 0x4 0x3 0x0 0x1 0x96 0xfa
DEBUG:pymodbus.logging:recv: 0x1 0x4 0xa 0xf0 0x0 0xf0 0x1 0xf0 0x2 0x4 0x3 0x0 0x1 0x96 0xfa
DEBUG:pymodbus.logging:Frame check failed, ignoring!!
DEBUG:pymodbus.logging:Resetting frame - Current Frame in buffer - 0x0 0x5 0x30 0x9 0x1 0x4 0xa 0xf0 0x0 0xf0 0x1 0xf0 0x2 0x4 0x3 0x0 0x1 0x96 0xfa
DEBUG:pymodbus.logging:Frame check failed, ignoring!!
DEBUG:pymodbus.logging:Resetting frame - Current Frame in buffer - 0x9 0x1 0x4 0xa 0xf0 0x0 0xf0 0x1 0xf0 0x2 0x4 0x3 0x0 0x1 0x96 0xfa
DEBUG:pymodbus.logging:Getting Frame - 0x4 0xa 0xf0 0x0 0xf0 0x1 0xf0 0x2 0x4 0x3 0x0 0x1
DEBUG:pymodbus.logging:Factory Response[ReadInputRegistersResponse': 4]
DEBUG:pymodbus.logging:Frame advanced, resetting header!!
DEBUG:pymodbus.logging:Getting transaction 1
input register data:
	 61440
	 61441
	 61442
	 1027
	 1

read 4 input registers **********
DEBUG:pymodbus.logging:send: 0x1 0x4 0x0 0x0 0x0 0x4 0xf1 0xc9
DEBUG:pymodbus.logging:Adding transaction 1
DEBUG:pymodbus.logging:recv: 0x1 0x4 0x0 0x0 0x0 0x4 0xf1 0xc9
DEBUG:pymodbus.logging:recv: 0x1 0x4 0x0 0x0 0x0 0x4 0xf1 0xc9
DEBUG:pymodbus.logging:Frame check failed, ignoring!!
DEBUG:pymodbus.logging:Resetting frame - Current Frame in buffer - 0x1 0x4 0x0 0x0 0x0 0x4 0xf1 0xc9
DEBUG:pymodbus.logging:Frame - [b'\x01\x04\x00\x00\x00\x04\xf1\xc9'] not ready
DEBUG:pymodbus.logging:recv: 0x1 0x4 0x8 0xf0 0x0 0xf0 0x1 0xf0 0x2 0x3 0xfb 0xd1 0xca
DEBUG:pymodbus.logging:recv: 0x1 0x4 0x8 0xf0 0x0 0xf0 0x1 0xf0 0x2 0x3 0xfb 0xd1 0xca
DEBUG:pymodbus.logging:Frame - [b'\x01\x04\x08\xf0\x00\xf0\x01\xf0\x02\x03\xfb\xd1\xca'] not ready
DEBUG:pymodbus.logging:Connection lost comm due to None
DEBUG:pymodbus.logging:Getting transaction 1
Traceback (most recent call last):
  File "/Applications/AAApplications/mambaforge/envs/mspy2/lib/python3.10/asyncio/tasks.py", line 456, in wait_for
    return fut.result()
asyncio.exceptions.CancelledError

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "/Users/analog/Projects/Current_Projects/Doug/Brushless DC motor/utilities/code_test.py", line 36, in <module>
    asyncio.run(main())
  File "/Applications/AAApplications/mambaforge/envs/mspy2/lib/python3.10/asyncio/runners.py", line 44, in run
    return loop.run_until_complete(main)
  File "/Applications/AAApplications/mambaforge/envs/mspy2/lib/python3.10/asyncio/base_events.py", line 646, in run_until_complete
    return future.result()
  File "/Users/analog/Projects/Current_Projects/Doug/Brushless DC motor/utilities/code_test.py", line 27, in main
    res = await client.read_input_registers( address=0
  File "/Users/analog/Projects/Current_Projects/Doug/Brushless DC motor/utilities/pymodbus/client/base.py", line 198, in async_execute
    resp = await asyncio.wait_for(req, timeout=self.params.timeout)
  File "/Applications/AAApplications/mambaforge/envs/mspy2/lib/python3.10/asyncio/tasks.py", line 458, in wait_for
    raise exceptions.TimeoutError() from exc
asyncio.exceptions.TimeoutError
logout
Saving session...
...copying shared history...
...saving history...truncating history files...
...completed.

[Process completed]


RS485 data stream

01 04 00 00 00 05 30 09 01 04 0A F0 00 F0 01 F0 
02 04 03 00 01 96 FA 01 04 00 00 00 04 F1 C9 01 
04 08 F0 00 F0 01 F0 02 03 FB D1 CA
@janiversen
Copy link
Collaborator

Thanks, this looks like a bug in the sync client, we have not tested that for a while (we are working on the async client), but let me test it.

@janiversen
Copy link
Collaborator

method= do not exist please read the documentation, however you might be in luck that rtu correspond to the default.

@janiversen
Copy link
Collaborator

I tested with simple_async_client (select serial and handle_local_echo) and it worked.

In order to test I patched async_io.py (the server) to return received data (echo).

You test with 3.3.2 I test with dev, there might be some commit between those 2 that solves the problem.

@github-actions github-actions bot locked as resolved and limited conversation to collaborators Jul 31, 2023
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants