Help RS485 RTU Master

hello i try to read holding register on pool pump but i have no response .
i used this code who works with relay modbus card but don't work with the pump
it has work only one time by magic ?? but now i have "faild to read registers! connection timed out"

i must send 01H(Device Adress) 03H(Function code) 0AH(controller 8bit high) 00H(controller 8bit low) 00H(controller lenght 8bit high) 01H(controller lenght 8bit low) 86H(crc control 8bit low) 03H(crc control 8bit high)
so --> 00H 03H 0AH 00H 00H 01H 86H 03H

the controller slave will respond 00H 03H 01H 00H 05H 31H B7H

in the pdf i have this register table :
Adress :0x0A00 / lenght:1 / read / task: display ID
adress: 0x0A01 / lenght:1 / read,write / task : language configuration
etc etc..

did you have any idea?

#include <ArduinoModbus.h>

// How often (in milliseconds) the pump will be read.
const unsigned long REPORT_INTERVAL = 1000;

void setup() {
  Serial.begin(9600);
  while(!Serial);
  
  if (!ModbusRTUClient.begin(9600)) {
    Serial.println("Failed to start Modbus RTU Client!");
    while (1);
  }
}

// The time at which the pump were last read.
unsigned long lastMillis = 0;

void loop() {
  
  // If enough time has elapsed, read again.
  if (millis() - lastMillis > REPORT_INTERVAL) {
    lastMillis = millis();
    
    // The Modbus RTU pump:
    // Address: 0x00
    // Holding Register: 0xA0
    // Read Length: 1
    
    if (!ModbusRTUClient.requestFrom(0x00, HOLDING_REGISTERS, 0xA0, 1)) {
      Serial.print("failed to read registers! ");
      Serial.println(ModbusRTUClient.lastError());
    }
    else {
      // If the request succeeds, the pump sends the readings, that are
      // stored in the holding registers. The read() method can be used to
      // get the display id values.
      short displayid = ModbusRTUClient.read();
      
      Serial.print("DISPLAY ID: ");
      Serial.println(displayid);
      
    }
  }
    delay(100);
  }

I found using an arduino with a Max485 chip to a modbus controller was very sensitive to the resetting of the transmit line and the speed of the response. In the end I included the send and return on one subroutine to always capture the data return

Hope this helps`//Send an array to the Controller
//================================
void Send_To_Controller(unsigned char *buf,int len)
{
  // send
  Clear_ControlRX_Files();
  digitalWrite(TXpin,HIGH);    // sets Max3485 to transmit
  delay(100);
  for (int i=0;i<len;i++)      // sends message
   Serial2.write(buf[i]);
  delay(10);  
  digitalWrite(TXpin,LOW);     // sets Max3485 to recieve
  delay(100);                 // wait for return from Controller
  // recieve
  RXCount=0;
  while (Serial2.available())
    {  
    ControlRX[RXCount]=Serial2.read(); 
    RXCount++;   
    } 
// Check ControlRX array
  if (RXCount>0)
    {
    Check_ControlRX();
    Clear_ControlRX_Files();
    RXCount=0;
    }
}`

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.