如何使用libmodbus从modbus/tcp读取数据

如何使用libmodbus从modbus/tcp读取数据,c,modbus,modbus-tcp,C,Modbus,Modbus Tcp,我有一个艾条ioLogik E1214,我想使用modbus/tcp与它通信。我找到了一个可以这样做的图书馆-。首先,我从他们的网站复制了代码示例,并对其进行了一些修改,使其看起来像这样: #include <stdio.h> #ifndef _MSC_VER #include <unistd.h> #include <sys/time.h> #endif #include <string.h> #include <stdlib.h>

我有一个艾条ioLogik E1214,我想使用modbus/tcp与它通信。我找到了一个可以这样做的图书馆-。首先,我从他们的网站复制了代码示例,并对其进行了一些修改,使其看起来像这样:

#include <stdio.h>
#ifndef _MSC_VER
#include <unistd.h>
#include <sys/time.h>
#endif
#include <string.h>
#include <stdlib.h>
#include <time.h>
#include <errno.h>
#include <modbus.h>
#define G_MSEC_PER_SEC 1000

int main(int argc, char *argv[])
{
    modbus_t *mb;
    uint16_t tab_reg[30];
    int length = 6;

    mb = modbus_new_tcp("192.168.127.254", 502);
    if (modbus_connect(mb) == -1) {
        fprintf(stderr, "Connection failed: %s\n", modbus_strerror(errno));
        modbus_free(mb);
        return -1;
    }

    /* Read "length" registers from the address 0 */
    int read_val = modbus_read_registers(mb, 0, length, tab_reg);

    if(read_val==-1)
        printf("ERROR: %s\n", modbus_strerror(errno));
    else
    {
        printf("Read registers: %d\n", read_val);
        for(int i=0; i<length; i++)
        {
            printf("%d ", tab_reg[i]);
        }
        printf("\n");
    }
    modbus_close(mb);
    modbus_free(mb);
    return 0;
}
#包括
#ifndef\u理学硕士
#包括
#包括
#恩迪夫
#包括
#包括
#包括
#包括
#包括
#每1000秒定义G_MSEC_
int main(int argc,char*argv[])
{
modbus_t*mb;
uint16_t tab_reg[30];
整数长度=6;
mb=modbus_new_tcp(“192.168.127.254”,502);
如果(modbus_连接(mb)=-1){
fprintf(标准,“连接失败:%s\n”,modbus_strerror(errno));
无modbus_(mb);
返回-1;
}
/*从地址0读取“长度”寄存器*/
int read_val=modbus_read_寄存器(mb,0,长度,tab_reg);
如果(读取值==-1)
printf(“错误:%s\n”,modbus_strerror(errno));
其他的
{
printf(“读取寄存器:%d\n”,读取值);

对于(inti=0;i,您的从机似乎在地址0处并没有任何保持寄存器,因此它抱怨
非法数据地址
错误

您需要查看您拥有的Modbus寄存器映射,并相应地使用libmodbus中的正确Modbus功能。例如,如果您想读取变量
RLY\u pulseOnWidth
,您必须使用:

int read_val = modbus_read_input_registers(mb, 52, length, tab_reg);
但要阅读
RLY\u TotalCount

int read_val = modbus_read_registers(mb, 64, length, tab_reg);
您可以在此处检查与“点类型”列相关的所有Modbus功能代码:

您试图使用“读取寄存器”(int16值),而您需要的是“读取线圈”(位)。线圈和寄存器存储在单独的表中,因此地址不同

用于读取RLY_状态,因为正如您的文档所述,它是一个线圈值

您需要以不同于线圈的方式读取输入和保持寄存器。您的示例代码应该适合读取保持寄存器