emelianov / modbus-esp8266

Most complete Modbus library for Arduino. A library that allows your Arduino board to communicate via Modbus protocol, acting as a master, slave or both. Supports network transport (Modbus TCP) and Serial line/RS-485 (Modbus RTU). Supports Modbus TCP Security for ESP8266/ESP32.

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

ModbusTCP, esp8266 can't connect on device and read registry

tomdelahaba opened this issue · comments

I have basically the same question as it appeared in here multiple times. I am trying to connect my heat pump and read the registry via ESP8266. I am using the example code to get started, unfortunately the respond is always 0.

I went through the issues in here (mostly the closed ones already) but nothing helped. I made sure that I am setting the slave (unitId) as it was a problem in my python code in the past which is working already. Unfortunately I am not able to get it done with your library.

My c code (based on your examples with some small changes which can't affect the functionality except the UnitID is defined for the readHreg (unfortunately my code never appears in this condition, the device can't login):

#include <ESP8266WiFi.h>
#include <ModbusIP_ESP8266.h>

#define PUMP_UNIT_ID 1

const char* ssid = "router_ssid";
const char* password = "pass";

const int REG = 126;               // Modbus Hreg Offset
IPAddress remote(xxx, xxx, xxx, xxx);  // Address of Modbus Slave device
const int LOOP_COUNT = 10;
ModbusIP mb;  //ModbusIP object

void setup() {
  Serial.begin(115200);
 
  WiFi.begin(ssid, password);
  
  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }
 
  Serial.println("");
  Serial.println("WiFi connected");  
  Serial.println("IP address: ");
  Serial.println(WiFi.localIP());

  mb.client();
}

uint16_t res = 0;
uint8_t show = LOOP_COUNT;
uint16_t port = 502;

void loop() {
  if (mb.isConnected(remote)) {   // Check if connection to Modbus Slave is established
    Serial.println("Modbus is connected");
    //mb.readHreg(remote, REG, &res);  // Initiate Read Coil from Modbus Slave
    mb.readHreg(remote, REG, &res, 1, nullptr, PUMP_UNIT_ID);
  } else {
    Serial.println("Connecting to modbus");
    mb.connect(remote, port);           // Try to connect if no connection
  }
  mb.task();                      // Common local Modbus task
  delay(100);                     // Pulling interval
  if (!show--) {                   // Display Slave register value one time per second (with default settings)
    Serial.println("Decreasing loops");
    Serial.println(res);
    show = LOOP_COUNT;
  }

  mb.disconnect(remote);
}

Unfortunately, I aways receive just 0 for the res. My python code which is working together with pymodbus:

from pymodbus.client import ModbusTcpClient

print('====== STARTING APPLICATION')

port = 502
ip_addr = 'xxx.xxx.xxx.xxx'
slave = 0x01

client = ModbusTcpClient(
    ip_addr,
    port,
    )
client.connect()
result = client.read_input_registers(126, 1, slave=slave) **// THIS SLAVE IS I GUESS THE UNITID ***
print('Value from registry:', result.registers[0])
client.close()
print('====== APP ENDS')

What I get from the console is only:

04:15:41.990 -> WiFi connected
04:15:41.990 -> IP address: 
04:15:41.990 -> xxx.xxx.xxx.xxx
04:15:41.990 -> Connecting to modbus
04:15:47.204 -> Connecting to modbus
04:15:52.448 -> Connecting to modbus
04:15:57.692 -> Connecting to modbus
04:16:02.934 -> Connecting to modbus
04:16:08.242 -> Connecting to modbus
04:16:13.493 -> Connecting to modbus
04:16:18.711 -> Connecting to modbus
04:16:23.955 -> Connecting to modbus
04:16:29.198 -> Connecting to modbus
04:16:34.450 -> Connecting to modbus
04:16:39.691 -> Decreasing loops
04:16:39.691 -> 0
04:16:39.691 -> Connecting to modbus

and this keeps looping and looping unfortunately it never connects

Basing on your debug output it looks like ESP unable to connect to modbus server device. It's probably because of network issue.

@emelianov >
To be honest I am sure it is no network issue as I am able to access that device immediately before and immediately after running that code with my python / go code... before and after, as the device (and probably all modbus devices) allows only 1 connection at time. And as well as this I am able to connect to the network with the esp8266.

Don't you have any other idea, do you? Or is there any possible tracing?

@emelianov >
What I found out so far is, it seems that the device is properly connecting as exactly in the "meantime" of processing the commands, from my computer I am not able to access that device and from time to time I get "the target machine is refusing active connection"... While with ESP turned off, I do not get this error and I get proper values.

I tried the same with another computer (connecting 2 computers to the device) and on one of them I get always similar error). So it seems, the ESP is really connected on that device, unfortunately (somehow and for me inconceivably) Instead of reading the registry, the mb.isConnected always return false even when the device seems to be connected (as written above). Well, maybe the device is refusing the connection for the esp as well, can't tell... But this is what I found....

So because of that the res is always 0. Wonder how can I connect that device or sent the registry read command when its always seems to be disconnected but it is probably connected

Ok found the reason. The very first loop, the esp connects, while I am disconnecting the device at the end of the loop... This is the reason why in new iteration of the loop it has to connect again, which is usually fine but in this case (wonder why) I receive just 0... If I remove the disconnecting, the first iteration of the loop it returns me 0, but in next iterations, the values are properly set...

So I just wonder how I should disconnect the device.