libmodbus icon indicating copy to clipboard operation
libmodbus copied to clipboard

Add support for Modbus RTU Over TCP

Open marinonjalsson opened this issue 11 years ago • 14 comments

Hi

It would be a good idea to add support from Modbus RTU Over TCP. I, for one, got device supporting that protocol and not Modbus TCP!.

Below are some statements from http://www.control.com/thread/1305797461

Where Modbus over TCP means a MODBUS RTU packet wrapped in a TCP packet.

Standard Modbus RTU is meant for transmission over serial lines (RS232 or RS485 are the most common). The message starts with a one byte Slave ID and ends with a two byte CRC. Sometimes the RTU message is run through a gateway onto ethernet without actually changing any of the bytes in the message. This is commonly called "RTU over TCP".

There is a different specification for Modbus TCP where the message bytes are modified to add the 6 byte MBAP header and remove the two byte CRC.

Best regards, Marinó

marinonjalsson avatar Jan 21 '14 11:01 marinonjalsson

Hi Marinó,

If you're interested in patching libmodbus you can grab "ugly patch that breaks the design guidelines of the beautiful original code" written by Johan Englund at https://groups.google.com/forum/#!msg/libmodbus/xm8S6MMDhgM/Qd97y9_mhwgJ I'm using his patch (updated for version 3.0.6 of libmodbus) successfully since ~February 2014. To see how to use it - please check referenced above changes in my branch of check_modbus nagios/icinga plugin.

regards Mirek (sq5gvm)

sq5gvm avatar Aug 27 '14 21:08 sq5gvm

I'd like to get this as an option too. PyModbus lets you use arbitrary framers with arbitrary transports, it works quite well: https://pymodbus.readthedocs.org/en/latest/examples/changing-framers.html

I had been trying to use socat to setup a virtual serial port<->tcp port mapping, but was getting "Invalid Argument" errors from some syscall inside libmodbus. Worked around it by using pymodbus, but that's not as portable to small devices as libmodbus :)

karlp avatar Dec 09 '14 13:12 karlp

Related to #257

stephane avatar Aug 27 '15 11:08 stephane

When I see all the forks which implement that feature I think you are legion to want it!

stephane avatar May 11 '16 10:05 stephane

So , i look around and still can'not found any implementation. i implemented myself , first i am opening tcp socket and listening. and then parsing manually modbus tcp packet , find slaveid , function etc. after that polling with modbus_new_rtu , reading there and putting that values in ctx->mb_mapping then calling modbus_reply function , everything works fine.

for every tcp packet , first 5 bytes is zero. than starting the frame. i don't know why. 0x < 00 00 00 00 00 06 01 03 04 02 00 01 > this packet offset is 7.

BUT some modbus IDE's(SCH ELECTRIC ION SETUP) , just sending this packet 0x < 03 03 0B C2 00 01 26 30 > this packet offset is also 7. but when i write query[offset + 1] like that , gives me nothing.

so , i parsed like , " if first index is zero or not", if it's zero parse this index like that and so on.

BUT i can't send data to ION Setup program , modbus library send errors like unknown functions etc.

so do you guys any idea how i can handle this problem ?

cevatbostancioglu avatar Nov 23 '16 06:11 cevatbostancioglu

Hello, here is an article about Modbus over ethernet that I've found

Have anybody tested this software?

ElenRey avatar Apr 26 '17 13:04 ElenRey

+1 for Modbus-over-TCP option please.

i also found http://www.modbusdriver.com/modpoll.html can do it with the -m enc ( Encapsulated Modbus RTU over TCP ) option.

henkhoo avatar Dec 18 '17 12:12 henkhoo

Sample implementation: https://github.com/stephane/libmodbus/pull/385

v-zhuravlev avatar Dec 18 '17 13:12 v-zhuravlev

Hello! I suggest a patch for use modbus over tcp and modbus over udp. patch.zip

DmitriyVinogradov avatar Oct 12 '18 19:10 DmitriyVinogradov

Thank. I wanted to stay within the library implementation.

сб, 3 нояб. 2018 г. в 4:38, Mike Purvis [email protected]:

Here's another example implementation: https://github.com/rscada/libmodbus/blob/master/modbus/modbus-udp.c

— You are receiving this because you commented. Reply to this email directly, view it on GitHub https://github.com/stephane/libmodbus/issues/192#issuecomment-435546796, or mute the thread https://github.com/notifications/unsubscribe-auth/AqDq7BlbokO8AfcKeY6hzvIaro_1E6IRks5urOWcgaJpZM4BbSKN .

DmitriyVinogradov avatar Nov 06 '18 19:11 DmitriyVinogradov

Hello! I suggest a patch for use modbus over tcp and modbus over udp. patch.zip

how to apply the patch

ahmedyousri avatar Nov 19 '19 16:11 ahmedyousri

after applying the patch will be able to use modbus over tcp and modbus over udp. looks like that: //выбираем modbustcp - mbtcp, modbusovertcp - mbotcp, modbusoverudp - mboudp if(strcmp(ip.type, "mbtcp") == 0){ ctx = modbus_new_tcp(ip.ipaddress, ip.port); }else if(strcmp(ip.type, "mbotcp") == 0){ sprintf(service, "%d", ip.port); ctx = modbus_new_over_tcp_pi(ip.ipaddress, service); }else if(strcmp(ip.type, "mboudp") == 0){ sprintf(service, "%d", ip.port); ctx = modbus_new_over_udp_pi(ip.ipaddress, service); }

other functions are the same in the library

DmitriyVinogradov avatar Nov 25 '19 06:11 DmitriyVinogradov

after applying the patch will be able to use modbus over tcp and modbus over udp. looks like that: //выбираем modbustcp - mbtcp, modbusovertcp - mbotcp, modbusoverudp - mboudp if(strcmp(ip.type, "mbtcp") == 0){ ctx = modbus_new_tcp(ip.ipaddress, ip.port); }else if(strcmp(ip.type, "mbotcp") == 0){ sprintf(service, "%d", ip.port); ctx = modbus_new_over_tcp_pi(ip.ipaddress, service); }else if(strcmp(ip.type, "mboudp") == 0){ sprintf(service, "%d", ip.port); ctx = modbus_new_over_udp_pi(ip.ipaddress, service); }

other functions are the same in the library

The patch applies, but it doesn't seem to be working against 3.1.6. I'm getting these:

In file included from modbus.h:291,
                 from modbus.c:23:
modbus-over-udp.h:25:1: warning: function declaration isn’t a prototype [-Wstrict-prototypes]
   25 | void recbufclear();
      | ^~~~
In file included from modbus.h:291,
                 from modbus-data.c:26:
modbus-over-udp.h:25:1: warning: function declaration isn’t a prototype [-Wstrict-prototypes]
   25 | void recbufclear();
      | ^~~~
In file included from modbus.h:291,
                 from modbus-rtu.h:10,
                 from modbus-rtu.c:19:
modbus-over-udp.h:25:1: warning: function declaration isn’t a prototype [-Wstrict-prototypes]
   25 | void recbufclear();
      | ^~~~
In file included from modbus.h:291,
                 from modbus-tcp.h:10,
                 from modbus-tcp.c:58:
modbus-over-udp.h:25:1: warning: function declaration isn’t a prototype [-Wstrict-prototypes]
   25 | void recbufclear();
      | ^~~~

And these...

/usr/bin/ld: .libs/modbus-data.o:(.bss+0x0): multiple definition of `recbuf'; .libs/modbus.o:(.bss+0x0): first defined here
/usr/bin/ld: .libs/modbus-rtu.o:(.bss+0x0): multiple definition of `recbuf'; .libs/modbus.o:(.bss+0x0): first defined here
/usr/bin/ld: .libs/modbus-tcp.o:(.bss+0x0): multiple definition of `recbuf'; .libs/modbus.o:(.bss+0x0): first defined here

And the build fails here because linking fails.

~~Is there a usable implementation at the moment? I need to use this to deal with MODBUS RTU devices connected behind a Ethernet-RS485 converter that doesn't support protocol conversion (transparently converting MODBUS RTU to TCP and vice versa).~~

EDIT: I've made a fork that incorporated the changes from #445, and fixed some issues that I encountered during building. The fork now builds, and it looks like that implementation does work as intended. I'm able to correctly get data from a slave device connected behind a Serial-to-Ethernet converter without using protocol conversion (so MODBUS RTU messages are being used). This is tested on Linux.

lss4 avatar Sep 14 '20 02:09 lss4