-
-
Notifications
You must be signed in to change notification settings - Fork 1.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Buffer overflow after several repeated connections between master and slave using the tcp protocol. #759
Comments
The problem is easy to reproduce, that is, repeatedly disconnecting and reconnecting will result in a memory overflow 1015 times on time, it should be that the modbus_receive() function internally shifted the pointer, I have looked at the source code, the problem should be found in line 350 of modbus.c in int _modbus_receive_msg(modbus_t *ctx, uint8_t *msg, msg_type_t msg_type), but unfortunately I haven't found the exact problem so far! |
I turned these code snippets into runnable programs in the quickest possible way (= do not expect anything pretty)
#define BE_FASTER
#include <modbus.h>
#include <cerrno>
#include <iostream>
int main() {
// 创建 Modbus 上下文
modbus_t *ctx = modbus_new_tcp("127.0.0.1", 1502); // IP地址和端口
if (ctx == NULL)
{
std::cerr << "Unable to allocate libmodbus context\n";
return -1;
}
// 创建从站的寄存器表
modbus_mapping_t *mb_mapping;
mb_mapping = modbus_mapping_new_start_address(0, 64, 0, 64, 0, 64, 0, 64);
if (mb_mapping == NULL)
{
std::cerr << "Failed to allocate the mapping: " << modbus_strerror(errno) << "\n";
modbus_free(ctx);
return -1;
}
while (true)
{
// 连接到 Modbus 从站
if (modbus_connect(ctx) == -1)
{
std::cerr << "Connection failed: " << modbus_strerror(errno) << "\n";
break;
}
// 读取保持寄存器(示例:寄存器地址0,读取7个寄存器)
uint16_t query[1234];
int rc = modbus_read_registers(ctx, 0, 7, query);
if (rc == -1)
{
std::cerr << "Read failed: " << modbus_strerror(errno) << "\n";
modbus_close(ctx); // 关闭连接
break;
}
// 存储读取到的寄存器值到 Modbus 寄存器表
for (int i = 0; i < rc; i++)
{
mb_mapping->tab_registers[i] = query[i];
}
// 打印 Modbus 寄存器表中的值
#ifndef BE_FASTER
std::cout << "Modbus register values: ";
for (int i = 0; i < rc; i++)
{
std::cout << mb_mapping->tab_registers[i] << " ";
}
std::cout << std::endl;
#endif
modbus_close(ctx); // 关闭连接
#ifndef BE_FASTER
usleep(50000); // 等待200毫秒后再进行下一次读取
#endif
}
// 清理资源
modbus_free(ctx);
modbus_mapping_free(mb_mapping);
return 0;
}
#include <modbus.h>
#include <cstdio>
#include <cstdlib>
#include <cerrno>
#include <iostream>
int main() {
modbus_t *ctx = modbus_new_tcp("127.0.0.1", 1502);
if (ctx == NULL) {
fprintf(stderr, "Failed to create the libmodbus context\n");
return -1;
}
uint8_t* query = (uint8_t *)malloc(MODBUS_TCP_MAX_ADU_LENGTH);
if (query == NULL) {
fprintf(stderr, "Failed to allocate memory for query\n");
modbus_free(ctx);
return -1;
}
int header_length = modbus_get_header_length(ctx);
modbus_set_debug(ctx, TRUE);
modbus_mapping_t *mb_mapping = modbus_mapping_new_start_address(0, 64,
0, 64,
0, 64,
0, 64);
if (mb_mapping == NULL) {
fprintf(stderr, "Failed to allocate the mapping: %s\n", modbus_strerror(errno));
modbus_free(ctx);
free(query);
return -1;
}
mb_mapping->tab_registers[0] = 0;
mb_mapping->tab_registers[1] = 2;
mb_mapping->tab_registers[2] = 3;
mb_mapping->tab_registers[3] = 4;
mb_mapping->tab_registers[4] = 5;
mb_mapping->tab_registers[5] = 20;
mb_mapping->tab_registers[6] = 1;
int s = modbus_tcp_listen(ctx, 1);
if (s == -1) {
fprintf(stderr, "Failed to listen: %s\n", modbus_strerror(errno));
modbus_free(ctx);
modbus_mapping_free(mb_mapping);
free(query);
return -1;
}
int cnt=1;
while (true) {
modbus_tcp_accept(ctx, &s);
int rc = modbus_receive(ctx, query);
if (rc == -1) {
fprintf(stderr, "Receive failed: %s\n", modbus_strerror(errno));
break;
}
rc = modbus_reply(ctx, query, rc, mb_mapping);
if (rc == -1) {
fprintf(stderr, "Reply failed: %s\n", modbus_strerror(errno));
break;
}
std::cout<<"cnt="<<cnt++<<std::endl;
}
close(s);
modbus_mapping_free(mb_mapping);
free(query);
modbus_free(ctx);
return 0;
} Running these programs (against Debian's libmodbus5 3.1.10-2) ends up with
After adding the missing Edit: I did another attempt without my |
libmodbus version
3.1.10
OS and/or distribution
Ubuntu20.04
Environment
arm64
Description
Jetson Xavier NX
Actual behavior if applicable
The client connection from 127.0.0.1 is accepted
Waiting for an indication...
<03><00><00><00><06><03><00><00><00><07>
[03][F7][00][00][00][11][FF][03][0E][00][00][00][02][00][03][00][04][00][05][00][14][00][01]
cnt=1015
The client connection from 127.0.0.1 is accepted
Waiting for an indication...
*** buffer overflow detected ***: terminated
Aborted (core dumped)
Expected behavior or suggestion
Using tcp communication, after the master and slave have repeatedly reconnected more than 1015 times, a memory overflow interrupt occurs on the slave side, interrupted at rc = modbus_receive(ctx, query); function
Steps to reproduce the behavior (commands or source code)
slave code:
master code:
The text was updated successfully, but these errors were encountered: