gpt4 book ai didi

c - 使用 libmodbus 库从 RS485 modbus 连接读取数据超时

转载 作者:太空宇宙 更新时间:2023-11-04 03:14:49 28 4
gpt4 key购买 nike

我是 Modbus 协议(protocol)的新手。我想从 RS485 读取数据。我使用 Libmodbus 库编写了 C 代码,但无法读取数据,导致错误连接超时。我在这里使用在 windows 机器上运行的 modbus slave 从这里我从 windows 机器的 COM 端口从 USB 连接到串行电缆。到 Linux 机器的 RS485 端口,我在那里运行下面的 C 代码。

#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <stdbool.h>

#include <modbus.h>


int main()
{
modbus_t *ctx = 0;

//
// create a libmodbus context for RTU
// doesn't check if the serial is really there
//
ctx = modbus_new_rtu("/dev/ttyS2", 115200, 'N', 8, 1);

if (ctx == 0) {

fprintf(stderr, "Unable to create the libmodbus context\n");
return -1;

} else {
struct timeval old_response_timeout;
struct timeval response_timeout;

// enable debug
modbus_set_debug(ctx, true);

// initialize timeouts with default
modbus_get_response_timeout(ctx, &old_response_timeout);
response_timeout = old_response_timeout;

// set the message and charcater timeout to 2 seconds
response_timeout.tv_sec = 2;
modbus_set_response_timeout(ctx, &response_timeout);
modbus_set_byte_timeout(ctx, &response_timeout);

}

// try to connet to the first DZT on the line
// assume that line address is 1, the default
// send nothing on the line, just set the address in the context
if(modbus_set_slave(ctx, 1) == -1) {
fprintf(stderr, "Didn't connect to slave/n");
return -1;
}

// establish a Modbus connection
// in a RS-485 context that means the serial interface is opened
// but nothing is yet sent on the line
if(modbus_connect(ctx) == -1) {

fprintf(stderr, "Connection failed: %s\n", modbus_strerror(errno));
modbus_free(ctx);
return -1;

} else {

int nreg = 0;
uint16_t tab_reg[32];
// uint16_t
fprintf(stderr, "Connected\n");

//
// read all registers in DVT 6001
// the function uses the Modbus function code 0x03 (read holding registers).
//
nreg = modbus_read_registers(ctx,0,5,tab_reg);

//printf(tab_reg);
if (nreg == -1) {

fprintf(stderr, "Error reading registers: %s\n", modbus_strerror(errno));
modbus_close(ctx);
modbus_free(ctx);

return -1;

} else {
int i;

// dump all registers content

fprintf (stderr, "Register dump:\n");
for(i=0; i < nreg; i++)
printf("reg #%d: %d\n", i, tab_reg[i]);


modbus_close(ctx);
modbus_free(ctx);

return 0;
}
}
}

错误如下

Opening /dev/ttyS2 at 115200 bauds (N, 8, 1)
Connected
[01][03][00][00][00][05][85][C9]
Waiting for a confirmation...
ERROR Connection timed out: select
Error reading registers: Connection timed out

最佳答案

我首先要检查的是串行通信硬件。是否有任何其他设备可以尝试连接到两台计算机以确保每台计算机的串行端口正常工作?这将有助于验证串行端口是否已在每台计算机上正确安装和配置。 USB 到串口转换器是出了名的挑剔且难以工作。

接下来我要检查的是每台机器上的波特率和串口设置。 RS-232 和 RS-485 串行通信协议(protocol)不会自动协商/自动检测连接速度,因此两个设备需要具有相同的连接设置。

您可能还想尝试比 115200 更慢的波特率。虽然更高的波特率允许更多的带宽和吞吐量,但出错的可能性更大。我会从 19200 波特率开始,一旦你开始工作就从那里开始。

此外,您在哪个用户下运行该程序?您可能需要通过 sudo 或作为具有提升权限的用户来执行该程序。

关于c - 使用 libmodbus 库从 RS485 modbus 连接读取数据超时,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52967306/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com