GithubHelp home page GithubHelp logo

arduinomodbusslave's People

Contributors

andrewvoznytsa avatar cabal avatar cvanbrederode avatar d21d3q avatar darkhedie avatar device111 avatar dgoo2308 avatar falahati avatar per1234 avatar pheerawat avatar raffaeler avatar romainreignier avatar swissbyte avatar tobiasschaffner avatar valentiworklearning avatar yaacov avatar yfrimanm avatar ysmilda avatar zatalian avatar zeron avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

arduinomodbusslave's Issues

1-Wire / I2C / PWM

Is there a possibility to integrate 1-wire sensors (ds18b20), I2C sensors (BME280) and PWM in your code?

Defining serial buffer for mega2560

I can't compile last one version oof library for mega2560, where I use Serial1.
Problem was header file at line 140. I must change SERIAL_BUFFER_SIZE to SERIAL_RX_BUFFER_SIZE

Issues with high baudrates

Hi,

Thank you for sharing your library that seems very interesting as it is the only one I have found that use callback functions. I cannot imagine implementing a Modbus slave that copy the values of the registers at each iteration of the loop.
Nevertheless, I did not manage to use your simple.ino example with a baudrate higher than 9600, using qmodbus as the Master, while it works well with other libraries like this one at 19200 or 115200 baud.
I have tried to change the timeout defined in Modbus::setT35 without any success.

On qmodbus, I have the following error:

Slave threw exception "Connection timed out" or function not implemented.

I have tested it on Arduino UNO and Arduino MEGA.

Let me know if you have already encountered that issue or have any ideas.

Romain

Invalid code ("Illegal function")

Looking at the code:
https://github.com/yaacov/ArduinoModbusSlave/blob/master/src/ModbusSlave.h#L45

enum {
  CB_MIN = 0,
  CB_READ_COILS = CB_MIN,
  CB_READ_DISCRETE_INPUTS,
  CB_READ_HOLDING_REGISTERS,
  CB_READ_INPUT_REGISTERS,
  CB_WRITE_COILS,
  CB_WRITE_HOLDING_REGISTERS,
  CB_READ_EXCEPTION_STATUS,
  CB_MAX
};

The CB_READ_COILS = CB_MIN assignment looks very wrong to me. as they are compared in the poll function with the FC_xxx values.

With the code currently in master, the arduino code only return errors for any request I made from the master (I use QModMaster Windows app) whose packets are correct.

Is master tested or am I missing something? The (very) old library worked nicely but I needed to remove the CTRL pin because of a new RS485 adapter.

Broadcast messages are not captured

Hey Yaacov,

Let me first say thank you for writing this library. Saved a lot of my time here.

However, broadcast messages are not captured. These type of messages are very useful to change a holding register network-wide and are usually sent with slave id 0.
Unfortunately, however, this library only captures messages with message slave id equal to the configured slave id and ignores messages with slave id 0.

This can be fixed easily and I can submit a PR. However, I think you should decide IF and how we should inform the user of the library about these type of messages as the current implementation of the callback method is not capable of that.

Won't compile for Teensy 3.x and LC when USB type is set to 'Serial' - Must have keyboard??

Hello,

Getting bizzaro complier errors, probably a Teensy issue, but I never can tell because I'm not good at this stuff.

The simple.ino code won't compile on the Teensy 3.x and LC unless the "USB Type" includes a "keyboard"
Doesn't work under regular serial, doesn't work under NO USB. Only seems to work if Keyboard is in the mix. Here's the horrendous error:

Linking everything together...
"C:\\Program Files (x86)\\Arduino\\hardware\\teensy/../tools/arm/bin/arm-none-eabi-gcc" -O2 -Wl,--gc-sections,--relax,--defsym=__rtc_localtime=1549453279 "-TC:\\Program Files (x86)\\Arduino\\hardware\\teensy\\avr\\cores\\teensy3/mk20dx256.ld" -lstdc++ -mthumb -mcpu=cortex-m4 -fsingle-precision-constant -o "C:\\Users\\andy\\AppData\\Local\\Temp\\arduino_build_341405/simple.ino.elf" "C:\\Users\\andy\\AppData\\Local\\Temp\\arduino_build_341405\\sketch\\simple.ino.cpp.o" "C:\\Users\\andy\\AppData\\Local\\Temp\\arduino_build_341405\\libraries\\ArduinoModbusSlave\\ModbusSlave.cpp.o" "C:\\Users\\andy\\AppData\\Local\\Temp\\arduino_build_341405/..\\arduino_cache_695210\\core\\core_teensy_avr_teensy31_usb_serial,speed_96,opt_o2std,keys_en-us_4939f5412a75a8560acb0f9e98268f02.a" "-LC:\\Users\\andy\\AppData\\Local\\Temp\\arduino_build_341405" -larm_cortexM4l_math -lm
c:/program files (x86)/arduino/hardware/tools/arm/bin/../lib/gcc/arm-none-eabi/5.4.1/../../../../arm-none-eabi/lib/armv7e-m\libc.a(lib_a-writer.o): In function `_write_r':

writer.c:(.text._write_r+0x12): undefined reference to `_write'

collect2.exe: error: ld returned 1 exit status

Using library ArduinoModbusSlave at version 2.0.0 in folder: C:\Users\andy\OneDrive\Documents\Arduino\libraries\ArduinoModbusSlave 
Error compiling for board Teensy 3.2 / 3.1.

So it's all about this keyboard thing.

I tried compiling in the Arduino IDE 1.8.8 / TeensyDuino 1.45

Also in Platform.io / Visual Code with the same results.

Is it possible to change parity in 485 modbus comunication?

Dear Mr Dr. Yaacov,
I would like to know if is it possible to change parity in comunication.
For example, I can connect with 9600-8-N-1, but if I want to connect with 9600-8-O-1 (odd parity), how I can do it?
I look forward to hearing from you soon.
Thanks.

Kind regards,
Javier

EDIT: mr=>dr :-)

Strange behiavor on slave using write single register

Hi,

I'm using this library on arduino in order to make it as a Modbus Slave, the slave consists in a ATMEGA328P with a bunch of neopixel leds (8) attached, periodically - every 250ms - , the master (Library: ModbusMaster) will change the led colors, generating some random colors.

The speed is: 57600-8E1

I was experiencing very often a slave timeout on the master (226 error), even if the master timeout limit is not reached (2000ms).

After some experiments, i've found that if i add to the slave a small delay(10) at the end of the write register function, the problem almost disappears (the timeout errors will appear very few times, like one every 100 writes)

This is weird, i mean: is this a normal behavior? i need to slow down the response of my slave in order to get it work?

immagine

Responding to bogus frames

I found that the slave is responding to bad packets when it sees a command it does not recognise. This is causing collisions on the bus and corruption when other slaves are present.
The problem is that the Validate function does not check the CRC first, only after it has decoded the message. If during the decoding the validate function finds a Modbus function code it does not handle it sends a STATUS_ILLEGAL_FUNCTION message back but this is done BEFORE the CRC is checked and so could very well be due to a packet not addressed to us at all. I am seeing errors from the master where a response was received from the WRONG slave.

Moving the CRC check and adding an address check to the beginning of the validate function fixes the problem and I see no more errors reported by the master..

`bool Modbus::validateRequest()
{
// IanA - Moved CRC check so we do not attempt to dscipher any invalid messages
// Check the crc, and if it isn't correct ignore the request.
uint16_t crc = readCRC(_requestBuffer, _requestBufferLength);
if (Modbus::calculateCRC(_requestBuffer, _requestBufferLength - MODBUS_CRC_LENGTH) != crc)
{
return false;
}
// Check that the message was addressed to us
if (!Modbus::relevantAddress(_requestBuffer[MODBUS_ADDRESS_INDEX]))
{
return false;
}
// IanA - End
// The minimum buffer size (1 x Address, 1 x Function, n x Data, 2 x CRC).
uint16_t expected_requestBufferSize = MODBUS_FRAME_SIZE;

// Check the validity of the data based on the function code.
switch (_requestBuffer[MODBUS_FUNCTION_CODE_INDEX])
{
case FC_READ_EXCEPTION_STATUS:
    // Broadcast is not supported, so ignore this request.
    if (isBroadcast())
    {
        return false;
    }
    break;

case FC_READ_COILS:             // Read coils (digital read).
case FC_READ_DISCRETE_INPUT:    // Read input state (digital read).
case FC_READ_HOLDING_REGISTERS: // Read holding registers (analog read).
case FC_READ_INPUT_REGISTERS:   // Read input registers (analog read).
    // Broadcast is not supported, so ignore this request.
    if (isBroadcast())
    {
        return false;
    }
    // Add bytes to expected request size (2 x Index, 2 x Count).
    expected_requestBufferSize += 4;
    break;

case FC_WRITE_COIL:     // Write coils (digital write).
case FC_WRITE_REGISTER: // Write registers (digital write).
    // Add bytes to expected request size (2 x Index, 2 x Count).
    expected_requestBufferSize += 4;
    break;

case FC_WRITE_MULTIPLE_COILS:
case FC_WRITE_MULTIPLE_REGISTERS:
    // Add bytes to expected request size (2 x Index, 2 x Count, 1 x Bytes).
    expected_requestBufferSize += 5;
    if (_requestBufferLength >= expected_requestBufferSize)
    {
        // Add bytes to expected request size (n x Bytes).
        expected_requestBufferSize += _requestBuffer[6];
    }
    break;

default:
    // Unknown function code.
    Modbus::reportException(STATUS_ILLEGAL_FUNCTION);
    return false;
}

// If the received data is smaller than what we expect, ignore this request.
if (_requestBufferLength < expected_requestBufferSize)
{
    return false;
}

// Set the length to be read from the request to the calculated expected length.
_requestBufferLength = expected_requestBufferSize;

// This is now done at the start of the function so it is no longer needed.
// Check the crc, and if it isn't correct ignore the request.
// uint16_t crc = readCRC(_requestBuffer, _requestBufferLength);
// if (Modbus::calculateCRC(_requestBuffer, _requestBufferLength - MODBUS_CRC_LENGTH) != crc)
// {
// return false;
// }
return true;
}
`

Stuck when calling flush() in begin() when using Serial1 in Arduino MKR(Zero)

Using an Arduino MKRZero I get stuck in row 190 calling flush() when using Serial1. If I send dummy byte on the Serial1 before calling .begin() it works.

Seems the blame is in Arduino Core.
https://github.com/arduino/ArduinoCore-samd/blob/ad95d3c204d43bee789bb0c116afbec135e6ace5/cores/arduino/SERCOM.cpp
void SERCOM::flushUART()
{
// Skip checking transmission completion if data register is empty
// if(isDataRegisterEmptyUART())
// return;

// Wait for transmission to complete
while(!sercom->USART.INTFLAG.bit.TXC);
}

Change SLAVE_ID

Hello
How i can change SLAVE_ID in void loop or void setup?

Change SLAVE ADDRESS during void setup

Hi guys, what i would like to do is change the SLAVE_ID during the void setup. This because i would like to set the slave address with 5 dip switch. At the moment the SLAVE_ID is declared at the beginning and i don't kwon how to solve this problem.
The SLAVE_DIP is the int variable that i want to use as a SLAVE_ID

Below my code:

//Testato con QModMaster
//https://github.com/yaacov/ArduinoModbusSlave

// https://en.wikipedia.org/wiki/Modbus

#include <ModbusSlave.h>
#include <SoftwareSerial.h>
SoftwareSerial RS485Serial(10, 11); // RX, TX

#define SLAVE_ID 10           // The Modbus slave ID, change to the ID you want to use.
#define SERIAL_BAUDRATE 9600 // Change to the baudrate you want to use for Modbus communication.
// Comment out the following line if your not using RS485
#define RS485_CTRL_PIN 2 // Change to the pin the RE/DE pin of the RS485 controller is connected to.

#define command_open 8  
#define command_close 9  
#define command_rocking 12

#define feedback_open 3
#define feedback_close 4  
#define WatchDog 5

#define DIP_1 A0
#define DIP_2 A1
#define DIP_3 A2
#define DIP_4 A3
#define DIP_5 A4

boolean SET_1;
boolean SET_2;
boolean SET_3;
boolean SET_4;
boolean SET_5;


// Modbus object declaration
Modbus slave(RS485Serial, SLAVE_ID, RS485_CTRL_PIN);

void setup() {

    // RS485 control pin must be output
    pinMode(2, OUTPUT);

    //OUTPUT
    pinMode(command_open, OUTPUT);
    pinMode(command_close, OUTPUT);
    pinMode(command_rocking, OUTPUT);

    //INPUT
    pinMode(feedback_open, INPUT);
    pinMode(feedback_close, INPUT);
    pinMode(WatchDog, INPUT);

    //DIPSWITCH
    pinMode(DIP_1, INPUT);
    pinMode(DIP_2, INPUT);
    pinMode(DIP_3, INPUT);
    pinMode(DIP_4, INPUT);
    pinMode(DIP_5, INPUT);

    SET_1 = digitalRead(DIP_1);
    SET_2 = digitalRead(DIP_2);
    SET_3 = digitalRead(DIP_3);
    SET_4 = digitalRead(DIP_4);
    SET_5 = digitalRead(DIP_5);

    int SLAVE_DIP = (SET_1*1)+(SET_2*2)+(SET_3*4)+(SET_4*8)+(SET_5*16)+1;
    Serial.println(SLAVE_DIP);

    // Register functions to call when a certain function code is received.
    slave.cbVector[CB_WRITE_COILS] = writeDigitalOut;
    slave.cbVector[CB_READ_DISCRETE_INPUTS] = readDigitalIn;
    
    // Set the serial port and slave to the given baudrate.
    RS485Serial.begin(SERIAL_BAUDRATE);
    slave.begin(SERIAL_BAUDRATE);
    Serial.begin(9600);
}

void loop() {
    /* listen for modbus commands con serial port.
     *
     * on a request, handle the request.
     * if the request has a user handler function registered in cbVector.
     * call the user handler function.
     */ 
    slave.poll();
}


/**
 * Handle Force Single Coil (FC=05) and Force Multiple Coils (FC=15)
 * set digital output pins (coils).
 * 
 * Dalla pagina di wikipedia addr: Coil  Read-write  1 bit   00001 - 09999 
 */
uint8_t writeDigitalOut(uint8_t fc, uint16_t address, uint16_t length) {
  Serial.print("FC= ");
  Serial.println(fc);
  Serial.print("ADDRES= ");
  Serial.println(address);
  Serial.print("LENGHT= ");
  Serial.println(length);

  if (address == 3) {
    digitalWrite(command_open, slave.readCoilFromBuffer(0));

    digitalWrite(command_close, slave.readCoilFromBuffer(1));

    digitalWrite(command_rocking, slave.readCoilFromBuffer(2));
  }

    return STATUS_OK;
}


// Handle the function code Read Input Status (FC=02) and write back the values from the digital input pins (discreet input).
uint8_t readDigitalIn(uint8_t fc, uint16_t address, uint16_t length)
{       
  Serial.print("FC= ");
  Serial.println(fc);
  Serial.print("ADDRES= ");
  Serial.println(address);
  Serial.print("LENGHT= ");
  Serial.println(length);


  if (address == 0) {
    // Write the state of the digital pin to the response buffer.
        slave.writeCoilToBuffer(0, digitalRead(feedback_open));

    // Write the state of the digital pin to the response buffer.
        slave.writeCoilToBuffer(1, digitalRead(feedback_close));

    // Write the state of the digital pin to the response buffer.
        slave.writeCoilToBuffer(2, digitalRead(WatchDog));
  }
  
    return STATUS_OK;
}

Thanks
Pietro

Write Single Register 0x06 I think it works badly

Hello
If I use Write Single Register 0x06, I can not send DATA to another Register. Always DATA is saved at Register 0.
If I use Write Multiple Registers 0x10, is all ok!
Is there an error in the library?

Problem is the get INPUT registers

Hi Yaacov Zamir.

Sorry yet a new issue.
I made a simple example sketch from which you can easily see how the problem occurs, i did the "// EXAMPLES" commas tell the editing section.

In addition, it is custom edited by the full_Examples.ino sketch

Sincerely, Rauno Finland

full_Examples.zip

Enable / disable communication

I have a very specific feature request for a product our company has produced. I implemented it (and changing the Unit ID) easily enough, but thought I would add an issue. I can issue a PR with my version of it if needed.

The ability to turn communication on and off with a function call. Our product doesn't communicate at start up until a digital in is raised, then it talks on ID 1. When the digital in is lowered, it switches to a different ID according to a register. This allows us daisy chain multiple units together without having to pre-configure them; the master gives them each an address in turn.

My fix was a simple private bool, and some methods to toggle it. If the bool is false, processing of packets would stop before checking the unit Id.

[Problems] Communication

Ok, now, this might be a little picky. After all, a lot of these problems might not be so obvious when working with the library. But I was just checking the source code and decided it is best to report them here. Even tho I hope I can find some time to fix these myself; it's always better to know which parts can use improvements if I failed to do so.

  • micros( ) > timeout + last_receive_time should be replaced with micros( ) - last_receive_time ) > timeout and type to uint64_t to prevent overflow
  • Read loop now processes requests as soon as it reads some part without checking if the message is actually complete; and therefore might modify the lengthIn or reject it altogether; this should be changed so requests are processed completely at least after 1.5T silence. (half the timeout)
    OR/AND
  • Requests should be processed as received and ignored as soon as there is a problem (id not matching as an example) as a byte by byte basis, as well as for determining beforehand the number of bytes required for the message to be valid
  • Buffer size should be increased to 256 as per Modbus standard max message size
  • Library responses too fast (I had some problem with this myself). It should wait for at least 3.5T after receiving a request before sending the response. (or at least 1.5T after making sure the request ended with another 1.5T silence)

Mega2560 TX problem

Hi,
I am trying the library on Arduino Mega 2560. Receiving the queries works ok but writeRegisterToBuffer doesn't write the response to any Serial. I tried all the serials but none works.
I tried HoldingRegisters function ans also InputRegisters.
It does enter the function to handel the queries but no write to serial is being done.
Any idea?
Thanks

Problem is the get INPUT registers

Hi Yaacov Zamir

Thanks to the excellent Full modbus Arduino skelets you made.
I've added the NTC10 temperature calculation and PID control everything works as well and I can apply set values ​​in EEPROM memory ..

My only problem is the INPUT registers query
30001 = PID adjustment value (360-359 value)
30002 = NTC10 Temperature (22.6 - 22.7 C)
30003 = Blank
30004 = PWM calculation value (55-56%)
30005 = Blank

This would be my desired morbus register list.
But when I ask for one of the INPUT registers eg 30004 (57) I always get 30001 (360) value in the register.
I have tried to make the INPUT FC = 04 offset settings where I could get the correct value of it but I failed.

This writeRegisterToBuffer command confuses because I do not want to write the value directly to something I want in the registry. Do you need a new FUNKTION here?

You could look at my appendix pictures if they better tell you what it is all about.

Can you tell me how should I act to get the modbus register functions to work correctly?

I am a novice in these matters, and yet the desire is hard to understand programming and other technology packages .. Big thank you Modbus excellent program for you.

Sincerely, Rauno Finland
pic2
pic3
pic4
full_TESTI.zip
pic1

Not working with I2C communication

I had successfully implemented this library with Arduino as an I2c slave. So one arduino modbus slave + I2c slave works. But right now I have interfaced a I2C sensor with arduino, and modbus is not working, not able to scan registry on a modbus master end. Arduino modbus slave + I2C master won't work. I have tried with some flags but still not working. Any ideas on what might be the issue?

Serial initialization

Out of curiosity, why is it that the Stream interface is not started at the set baudrate inside the begin() function? If it is included it is one less step you can forget while using this library.

Exception Response , Illegal Data Address

while trying the example "simple" using "Simply Modbus" software as a master and an Arduino UNO as slave, i'm getting "Exception Response" & "Illegal Data Address"

can anybody tell me why this is happening ??

win10 Codesys ControlWin softplc

Hi,

I have a codesys controlwin softplc configured as modbus master. Communication only works if i use a arduino leonardo as slave hardware. The exact same project on a arduino uno or arduino duemilanove does not work.
Is this a know problem (and maybe a solution/workaround)?

linux modpoll

Hi,

i have following example on a atmega 4808 running and try with my linux usb-ftdi rs485 to read the registers.

include 

#define SLAVE_ID 33           // The Modbus slave ID, change to the ID you want to use.
#define SERIAL_BAUDRATE 9600 // Change to the baudrate you want to use for Modbus communication.
#define SERIAL_PORT Serial   // Serial port to use for RS485 communication, change to the port you're using.

// Comment out the following line if your not using RS485
#define RS485_CTRL_PIN PIN_PF6 // Change to the pin the RE/DE pin of the RS485 controller is connected to.

// The position in the array determines the address. Position 0 will correspond to Coil, Discrete input or Input register 0.

uint8_t analog_pins[] = {PIN_PD0, PIN_PD1, PIN_PD2}; // Add the pins you want to read as a Input register.


uint8_t analog_pins_size = sizeof(analog_pins) / sizeof(analog_pins[0]); // Get the size of the analog_pins array

#ifdef RS485_CTRL_PIN
// Modbus object declaration
Modbus slave(SERIAL_PORT, SLAVE_ID, RS485_CTRL_PIN);
#else
Modbus slave(SERIAL_PORT, SLAVE_ID);
#endif

void setup()
{


    // Set the defined analog pins to input mode.
    for (int i = 0; i < analog_pins_size; i++)
    {
        pinMode(analog_pins[i], INPUT);
    }

    slave.cbVector[CB_READ_INPUT_REGISTERS] = readAnalogIn;

    // Set the serial port and slave to the given baudrate.
    SERIAL_PORT.begin(SERIAL_BAUDRATE);
    slave.begin(SERIAL_BAUDRATE);
}

void loop()
{
    // Listen for modbus requests on the serial port.
    // When a request is received it's going to get validated.
    // And if there is a function registered to the received function code, this function will be executed.
    slave.poll();
}

// Modbus handler functions
// The handler functions must return an uint8_t and take the following parameters:
//     uint8_t  fc - function code
//     uint16_t address - first register/coil address
//     uint16_t length/status - length of data / coil status


// Handle the function code Read Input Registers (FC=04) and write back the values from analog input pins (input registers).
uint8_t readAnalogIn(uint8_t fc, uint16_t address, uint16_t length)
{
    // Check if the requested addresses exist in the array
    if (address > analog_pins_size || (address + length) > analog_pins_size)
    {
        return STATUS_ILLEGAL_DATA_ADDRESS;
    }

    // Read the analog inputs
    for (int i = 0; i < length; i++)
    {
        // Write the state of the analog pin to the response buffer.
        slave.writeRegisterToBuffer(i, analogRead(analog_pins[address + i]));
    }

    return STATUS_OK;
}

on the linux machine not sure if the Parity is none but tried the other both as well

# mbpoll /dev/ttyUSB0 -m rtu -a 33 -r 1 -c 10  -b 9600 -P none -vv
debug enabled
debug enabled
Set device=/dev/ttyUSB0
mbpoll 1.0-0 - FieldTalk(tm) Modbus(R) Master Simulator
Copyright © 2015-2019 Pascal JEAN, https://github.com/epsilonrt/mbpoll
This program comes with ABSOLUTELY NO WARRANTY.
This is free software, and you are welcome to redistribute it
under certain conditions; type 'mbpoll -w' for details.

Opening /dev/ttyUSB0 at 9600 bauds (N, 8, 1)
Set response timeout to 1 sec, 0 us
Protocol configuration: Modbus RTU
Slave configuration...: address = [33]
                        start reference = 1, count = 10
Communication.........: /dev/ttyUSB0,       9600-8N1 
                        t/o 1.00 s, poll rate 1000 ms
Data type.............: 16-bit register, output (holding) register table

-- Polling slave 33... Ctrl-C to stop)
[21][03][00][00][00][0A][C2][AD]
Waiting for a confirmation...
ERROR Connection timed out: select
Read output (holding) register failed: Connection timed out
<00>-- Polling slave 33... Ctrl-C to stop)
[21][03][00][00][00][0A][C2][AD]
Waiting for a confirmation...
ERROR Connection timed out: select
Read output (holding) register failed: Connection timed out
^C<00>--- /dev/ttyUSB0 poll statistics ---
2 frames transmitted, 0 received, 2 errors, 100.0% frame loss

everything was closed.

maybe you can help me to understand what settings i need to use on the modpoll

many thanks

Exchanging strings

This is not an issue but just a question.
What are, on your opinion, the best options to copy a string between the master and the slave?
Apparently, but I am not a modbus expert, it looks like the Read/Write File Record (0x14 / 0x15) are the best option in the specs.
Should I implement these services? What do you think?

ModbusTCP

For a project I would like to use ModbusTCP. For this I looked into using your TCP lib, but this only accepts a ESP8266 and is about 3 years old. Would it be worth the effort to fix that library, or would it be better to change this one to also accept TCP messages?

Would like to know your vision on this problem.

EEPROM Write Problem

Dear Kobi Zamir,
Hi
Please accept my thanks for your very use full Library for ARDUINO modbus slave.
i successfully uploaded full.ino code in example of library and successfully :
1.Read/Write digital pins.
2.Read Analog pins.
3.Read EEPROM registers.
and problem is here that i want to write in EEPROM using function 06(Write_Single_Register) because some Limitations.
Thanks for your support.

hi i am getting modbus poll pc application timeout error Could you please help me

#include <ModbusSlave.h>
#include <SoftwareSerial.h>
SoftwareSerial RS485Serial(10, 11); // RX, TX

Modbus slave(RS485Serial, 1, 2);

int led = 12;

int dl_ro = 2;

void setup() {

pinMode(dl_ro, OUTPUT);
pinMode(led, OUTPUT);

slave.cbVector[CB_WRITE_COILS] = writeDigitalOut;

RS485Serial.begin(9600);
slave.begin(9600);

}

void loop() {
slave.poll();
}

uint8_t writeDigitalOut(uint8_t fc, uint16_t address, uint16_t length) {
Serial.print("FC=05: ");
Serial.println(fc);
Serial.println(address);
Serial.println(length);

if (address == led) {
digitalWrite(12, slave.readCoilFromBuffer(0));
}

return STATUS_OK;

}

lack of communication from time to time

Hello
I have problem..
Every few minutes, no communication via rs485. How to reset the arduino is ok, again for about 5 minutes.
There is some command to reset only the library
Some splush? or reset port?

Doesn't work on arduino mega 2560.

Modbus :: createResponse (); If there is no delay (1) or Serial.println ("") before calling the function, it does not work properly.

communication:rs232
baudrate:9600
dataBits:8
Parity:None
StopBits:1

uint8_t Modbus::poll()
{
.....
    // Validate the incoming request.
    if (!Modbus::validateRequest())
    {
    	  Serial.println("notvalid");
        return 0;
    }
   //Serial.println("valid");
    //delay(1);
    // Execute the incoming request and create the response.
    uint8_t status = Modbus::createResponse();
}

Holding Registers

Hello I have described an Arduino pro mini ATmega328p with the full.ino in Arduino IDE. Now my problem I can not choose between digital inputs and outputs, the holding register always shows 255 when reading but writing does not always result in error: timeout with QModMaster and the digital pins stay on output.

Missing support for arduino nano every

There are problems to compile the library for the new Arduino Nano Every target.
They declared that Arduino Nano Every is compatible with Arduino Nano but that's not true.
It seems the Arduino Nano Every doesn't suppport software serial but only hardware serial.
Could it possible to modifiy the library for supporting the Arduino Nano Every too?

add callback functions

Hi,

I would like to see the CB_READ_COILS function being split into CB_READ_COILS and CB_READ_DISCRETE_INPUTS.
The same for CB_READ_REGISTERS. This one should be split into CB_READ_INPUT_REGISTERS and CB_READ_HOLDING_REGISTERS.

I think this would make the programming of the slave code a lot more intuitive. Is there a reason why this is not done in the first place?

rename writeStringToBuffer() to writeArrayToBuffer()

In my opinion this function is confusingly named as a String is typically a set of characters. I would suggest to change it to writeArrayToBuffer() as this better covers the intended purpose. This would mean a minor functionality break, but would help with readability.

Also wouldn't it be more logical to support uint16_t array's as Modbus is 16 bit values based?

Put data in a specific address

Hi,
First thank you for great work. I did test various libraries and this is the one library that work here.
I have a question:
Is possible change the start address or set a especific address using function 04? I need put data in address 4121 becouse i have one app that read data in this address and i cant change this.

Thank you one more time.

EDIT: I dont use analog in. I get one value per modbus function 03 from a equipment.
I thought to do:
uint8_t [4200] analog_pins;
and:
slave.writeRegister Buffer (4121, 1234);

Would be the solution, but it didn't work.

Last release looks broken.

Hi !
I tried the last release of the library and it looks broken.
I used the examples supplied with both ArduinoModbusSlave (full.ino) and node-modbus-serial (polling_RTU.js), and I wasn't able to make the communication work.
I only tried the ReadHoldingRegister function.

I used the following code :

#include "ModbusSlave.h"

#define SLAVE_ID 4
#define CTRL_PIN 8
#define BAUDRATE 9600

Modbus slave(SLAVE_ID, CTRL_PIN);
uint16_t value = 1234;

void setup() {
  pinMode(CTRL_PIN, OUTPUT);
  slave.cbVector[CB_READ_HOLDING_REGISTERS] = readMemory;
  Serial.begin( BAUDRATE );
  slave.begin( BAUDRATE );
  Serial.println("NEW_MODBUS_LIBRARY");
}

void loop() {
  if (slave.poll() != 0) {
    Serial.println(value);
  }
}

uint8_t readMemory(uint8_t fc, uint16_t address, uint16_t length) {
  slave.writeRegisterToBuffer(0, value);
  return STATUS_OK;
}

Here is a console record when starting the master :
new_lib

As soon as I swap the new release with the previous one, everything works fine :
old_lib

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.