Interfacing modbus as slave and arduino mega 2560 as master using RX/TXpin

hello,
i am new to use modbus interference with arduino using RX/TX pin. i want to Read some parameters from the modbus which is connected to some energy meter. The problem is that i not able to implement the library into the code .

the parameters i want to use
MODE-RTU
SLAVE ADDRESS-2
DATA BIT-8
PARITY-NONE
ADDRESING FLOW RATE-1800
LENGTH-2
TYPE-HOLDING REGISTER

LIBRARY USED-Modbus-Master-Slave-for-Arduino/ModbusRtu.h at master · smarmengol/Modbus-Master-Slave-for-Arduino · GitHub

The problem is that i not able to implement the library into the code .

The problem is that you posted no code. The problem is that you did not describe what the code that you didn't post does. The problem is that you did not describe what you expect the code that you didn't post to do.

well,here is code

#include<SoftwareSerial.h>
#include <ModbusRtu.h>

uint16_t au16data[16]; //!< data array for modbus network sharing
uint8_t u8state; //!< machine state
uint8_t u8query; //!< pointer to message query


Modbus master(0,0,0); // this is master and RS-232 or USB-FTDI

/**
 * This is an structe which contains a query to an slave device
 */
modbus_t telegram[2];

unsigned long u32wait;

void setup() {
  // telegram 0: read registers
  telegram[0].u8id = 2; // slave address
  telegram[0].u8fct = 3; // function code (this one is registers read)
  telegram[0].u16RegAdd = 1800; // start address in slave
  telegram[0].u16CoilsNo = 4; // number of elements (coils or registers) to read
  telegram[0].au16reg = au16data; // pointer to a memory array in the Arduino

  // telegram 1: write a single register
  telegram[1].u8id = 2; // slave address
  telegram[1].u8fct = 6; // function code (this one is write a single register)
  telegram[1].u16RegAdd = 1800; // start address in slave
  telegram[1].u16CoilsNo = 1; // number of elements (coils or registers) to read
  telegram[1].au16reg = au16data+4; // pointer to a memory array in the Arduino
	
  master.begin( 9600 ); // baud-rate at 19200
  master.setTimeOut( 5000 ); // if there is no answer in 5000 ms, roll over
  u32wait = millis() + 1000;
  u8state = u8query = 0; 
}

void loop() {
  switch( u8state ) {
  case 0: 
    if (millis() > u32wait) u8state++; // wait state
    break;
  case 1: 
    master.query( telegram[u8query] ); // send query (only once)
    u8state++;
	u8query++;
	if (u8query > 2) u8query = 0;
    break;
  case 2:
    master.poll(); // check incoming messages
    if (master.getState() == COM_IDLE) {
      u8state = 0;
      u32wait = millis() + 1000; 
    }
    break;
  }

  au16data[4] = analogRead( 0 );
  
}

i want to read the data from the rx tx pin on serial monitor.

What, exactly, is connected to pins 0 and 1? Why isn't that attached to a different set of pins, so Serial can be used for debugging?

What does the code actually do? What do you expect it to do?

i want to read the data from the rx tx pin on serial monitor.

Then get that device off of pins 0 and 1.

actually that device is a meter(energy meter) to which modbus is connected
i have connected the tx/rx pin of device to arduino port 0

i am confused that what the code is actually doing

i want the code to read the data from the device and print on serial monitor

parameters for connecting the device are

MODE-RTU
SLAVE ADDRESS-2
DATA BIT-8
PARITY-NONE
ADDRESING FLOW RATE-1800
LENGTH-2
TYPE-HOLDING REGISTER

i want the code to read the data from the device and print on serial monitor

Do you want the code to read from the device OR print to the serial monitor?

Pick ONE.

If you want it to do both, get the device off of pins 0 and 1. Put it on the pins for Serial1, Serial2, or Serial3, and change the constructor code to use a different instance of serial (the second argument would NOT be 0).

so, i have to change the constructer in modbusrtu.h library which i have done before
my knowledge about library writing is very limited.
i will try,thanks

so, i have to change the constructer in modbusrtu.h library

No, you don't. The second argument to the constructor defines which instance of Serial to use.
0) Use Serial

  1. Use Serial1
  2. Use Serial2
  3. Use Serial3

so you mean i have to do only the connection with arduino?

i have connected the + rs485 of device to rx 19 of mega 2560

  • rs485 to tx 18

which argument to change in code

i don't know about constructor

i changed the constructor

Modbus master(0,1,2);

but the serial monitor shows nothing
i also try to verify/change the connection but nothing worked

i changed the constructor

Did you move the device to the TX1 and RX1 pins?

but the serial monitor shows nothing

Did you add any Serial.print() statements to make that happen?

void loop() {
  if (Serial1.available()>0){
  Serial.print("yes");
  }

yes for all the above

hello mr.paul S,
good news it's printing the "yes" on serial monitor
i made some changes now i am using new library ModbusMaster.h ----link attached down

Now my concern is to read data from device and serially print to serial monitor that i see on the device screen -----a snapshot is attached of device

#include <ModbusMaster.h>
ModbusMaster node;
void setup()
{
  Serial1.begin(9600);
  Serial.begin(9600);
// communicate with Modbus slave ID 2 over Serial (port 1)
  node.begin(2, Serial1);
}
void loop()
{
  if (Serial1.available()>0){
    Serial.print("yes");
    }
  static uint32_t i;
  uint8_t j, result;
  uint16_t data[8];
  i++;
  result = node.readHoldingRegisters(1800, 2);
  // do something with data if read is successful
  if (result == node.ku8MBSuccess)
  {
    for (j = 0; j < 6; j++)
    {
      data[j] = node.getResponseBuffer(j);
      Serial.print(data[j]);
    }
    Serial.println();
  }
}

link to library -GitHub - 4-20ma/ModbusMaster: Enlighten your Arduino to be a Modbus master

Any suggestion??

Perhaps instead of expecting the Modbus library to do stuff for you, without you understanding the library, you could actually debug the library.

Or, ditch the library altogether, and start with just printing what is send to the Serial1 instance.

i expect some hexadecimel input on serial monitor which i have never done before

some idea may help me reach there

{
    if (Serial1.available()>0){
 data[j] = node.getResponseBuffer(j);     
 Serial.print(data[j]);
  }

this is what i understood from your last comment

i expect some hexadecimel input on serial monitor

You expect yourself to provide some input? So, why don't you?

If you expect some OUTPUT on the Serial Monitor, how can you reasonably expect that, when all that you make the Arduino send is "yes"? You should clearly change "yes" to "0x45 0x32 0x78" since you expect hexadecimal output.

no, i mean arduino should read the data from device which is in "hexadecimel"form should be displayed on serial monitor

no, i mean arduino should read the data from device

Well, clearly is it, since Serial1.available() says that there is some data.

which is in "hexadecimel"form

THAT is nonsense. The data is ALWAYS in binary form.

If YOU want to get the data from the serial buffer, use Serial1.read(). If YOU want to send that data to the Serial Monitor app, use Serial.print() or Serial.println().