1

I try to communicate with 2 RS485 sensors (pH and EC), but I have some troubles with my code. First, I tried to get data from just one:

The function in charge of request sending:

String GET_probe(String probe){

if(probe == "pH"){
Serial.println("Sending request pH...");
digitalWrite(modbusModuleRE, RS485Transmit);  // Init Transceiver
digitalWrite(modbusModuleDE, RS485Transmit);  // Init Transceiver
byte  RTUrequest[] = {0x00, 0x03, 0x00, 0x00, 0x00, 0x01, 0x85, 0xDB};
RS485Serial.write(RTUrequest, sizeof(RTUrequest));
}

if(probe == "EC"){
Serial.println("Sending request EC...");          

digitalWrite(modbusModuleRE, RS485Transmit);  // Init Transceiver
digitalWrite(modbusModuleDE, RS485Transmit);  // Init Transceiver
byte  RTUrequest[] = {0x01, 0x03, 0x00, 0x00, 0x00, 0x02, 0xC4, 0x0B};
RS485Serial.write(RTUrequest, sizeof(RTUrequest));  
}

RS485Serial.flush();
RS485Serial.listen();
}

The function in charge of reading sensor's answer:

void ReadRx() {
     digitalWrite(modbusModuleRE, RS485Receive);
     digitalWrite(modbusModuleDE, RS485Receive);
     if(RS485Serial.available()) {
     Serial.print("Answer: ");
      for(int i=0; i<7; i++){  
          String myByte = String(RS485Serial.read(), HEX);// Read the byte

          if (myByte.length() == 1)
          {
            myByte = "0"+myByte;
          }
          modbusHexBuffer[i] = myByte;

          Serial.print(myByte);
          Serial.print(" "); 
      }
      Serial.println();
    }
   }

And the loop, sending the request each 5s:

void loop(){

  static uint32_t ts = millis();

  if (millis() - ts >= 5000) {
      ts = millis();
      GET_probe("pH");
  }

ReadRx();
}

The loop runs fine once and fails the second time, as shown in terminal. Can you tell me why and help me to fix it?

Sending request pH...
Answer: 00 03 02 05 78 86 f6 
Sending request pH...
  • comments: wire DE and RE to one pin; you don't need to call listen if you have only one SoftwareSerial instance; don't use String; if at least 1 byte is available you read 7 – Juraj Mar 8 at 13:41
  • Are you talking about this line?: String myByte = String(RS485Serial.read(), HEX); – Teddol Mar 8 at 13:44
  • regarding String and reading blindly, yes. use RS485Serial.readBytes(RTUresponse, 7);. readBytes will wait for the next byte – Juraj Mar 8 at 13:48
1

I have found why !!!

1st: buf[8] instead buf[7] in declaration 2nd: reinit byte buf[8] before EC request part.

So the code who works fine is:

byte buf[8];
void loop(){

      Serial.print("pH: ");   
      digitalWrite(modbusModuleRE, RS485Transmit);  // Init Transceiver
      digitalWrite(modbusModuleDE, RS485Transmit);  // Init Transceiver
      byte  pHrequest[] = {0x00, 0x03, 0x00, 0x00, 0x00, 0x01, 0x85, 0xDB}; 
      RS485Serial.write(pHrequest, sizeof(pHrequest));
      RS485Serial.flush();
      digitalWrite(modbusModuleRE, RS485Receive);
      digitalWrite(modbusModuleDE, RS485Receive);
      RS485Serial.readBytes(buf, 8);
     Serial.print(buf[3], HEX);Serial.println(buf[4], HEX);

byte buf[8];

      Serial.print("EC: "); 
      digitalWrite(modbusModuleRE, RS485Transmit);  // Init Transceiver
      digitalWrite(modbusModuleDE, RS485Transmit);  // Init Transceiver
      byte  ECrequest[] = {0x01, 0x03, 0x00, 0x00, 0x00, 0x02, 0xC4, 0x0B};
      RS485Serial.write(ECrequest, sizeof(ECrequest));
      RS485Serial.flush();
      digitalWrite(modbusModuleRE, RS485Receive);
      digitalWrite(modbusModuleDE, RS485Receive);
      RS485Serial.readBytes(buf, 8);
      Serial.print(buf[3], HEX);Serial.print(buf[4], HEX);Serial.print(buf[5], HEX);Serial.println(buf[6], HEX);

Serial.println();

}
  • 1
    rewrite it please as standalone answer – Juraj Mar 8 at 18:35

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.