alejoseb / Modbus-STM32-HAL-FreeRTOS

Modbus TCP and RTU, Master and Slave for STM32 using Cube HAL and FreeRTOS
GNU Lesser General Public License v2.1
539 stars 183 forks source link

1 Master and Multiple Slave Error is back? #43

Closed emptor8 closed 2 years ago

emptor8 commented 2 years ago

Hmm is anyone else seeing the problem noted here? https://github.com/alejoseb/Modbus-STM32-HAL-FreeRTOS/issues/17

This issue seems to have re-appeared on the latest version of this library.

I am seeing one of my Modbus slave devices stop working after a few minutes, and the failure I'm seeing seems to match the previous issue linked above.

I'm using a standard Modbus RTU configuration over RS-485 with the DE pin.

emptor8 commented 2 years ago

An update: Adding a small delay after swapping from transmitter to receiver and vice versa seems to "fix" this issue. Is there a better way to handle this? It seems like maybe the transmitter/receiver are being switched too quickly?

    //enable transmitter, disable receiver to avoid echo on RS485 transceivers
    HAL_HalfDuplex_EnableTransmitter(modH->port);
    HAL_GPIO_WritePin(modH->EN_Port, modH->EN_Pin, GPIO_PIN_SET);
    osDelay(10);
     //return RS485 transceiver to receive mode
    HAL_GPIO_WritePin(modH->EN_Port, modH->EN_Pin, GPIO_PIN_RESET);
    //enable receiver, disable transmitter
    HAL_HalfDuplex_EnableReceiver(modH->port);
    osDelay(10);
alejoseb commented 2 years ago

I don't believe switching too quickly is the reason. It is possible, however, that you are using a very high baudrate. If the MCU is not able to serve the ISR on time because of the high baudrate, the USART can overflow. If that is the case, then the USART will stop working. The library requires a callback to handle this type of error, it is missed right now. You can create this callback and check if it is executed, if that is the case, then in the callback you need to clean the USART state, clean the ring buffer and start again the USART to receive the modbus data.

emptor8 commented 2 years ago

I'm using a baud rate of 115200. Would that be considered too high?

Where/how would I go about creating this callback?

alejoseb commented 2 years ago

That baudrate has been tested without issues. Check the UARTCallback.c file of the library it already has an error callback but only enabled for DMA mode, you can create a callback that works also with the standard mode.

emptor8 commented 2 years ago

Thanks.

Do you know what's the best way to clean the USART state (e.g. which HAL functions)? And, is there a difference in what I need to do if I'm using DMA?

For cleaning the ring buffer, I assume you mean calling RingClear()?

emptor8 commented 2 years ago

Hey @alejoseb, sorry to bother you - did you get a chance to look at my question?

alejoseb commented 2 years ago

I will update the library to include the error management for all modes as soon as I have some free time, but this might not solve your particular issue.

Besides, you should check the examples for DMA, and read the HAL documentation and test by yourself in your particular environment. RingClear cleans the ring.

saeidshokoufi commented 2 years ago

Dear

Thanks for your Library,

How to set start address of Registers in modebus in this library?

Best Regards