libmodbus源码分析(2)主机(客户端)功能源码分析

53 篇文章 74 订阅

在上一篇文章《 libmodbus 源码分析(1)基本框架、关键数据结构、接口 》中,分析了libmodbus的源码基本框架和关键的数据结构、接口,本文就分析一下 libmodbus 作为 主机(客户端)的功能源码实现,这里我们以 modbus rtu 协议 的读 4x 区保持寄存器功能 进行举例说明,

我们简单的写一下 modbus rtu 下读 4x 区保持寄存器的 伪代码 流程:

int main()
{
    modbus_t *ctx = NULL;
    
    uint16_t tab_rp_register[200];  // 不一定是200个,根据自己的需要来定义
    
    /* 创建并初始化 modbus_t 指针 */
    ctx = modbus_new_rtu("/dev/ttyUSB1", 115200, 'N', 8, 1);

    /* 设置 错误 恢复模式 */
    modbus_set_error_recovery(ctx,
                              MODBUS_ERROR_RECOVERY_LINK |
                              MODBUS_ERROR_RECOVERY_PROTOCOL);
   
   /* 设置 从机 (服务器) 地址, 支持运行中 设定,也就是可以 实现多从机的轮询 */
   modbus_set_slave(ctx, SERVER_ID);
   
   /* 与从机建立连接 */
   modbus_connect(ctx);
   
   /* 4x区保持寄存器 的读 功能, 从 地址 start_addr开始,共读 nb 个寄存器 
    * 读到的寄存器值存放到 tab_rp_registers 中
    */
   modbus_read_registers(ctx, start_addr, nb, tab_rp_registers);
   
   /* 关闭 modbus */
   modbus_close( ctx );
   
    /* 释放 modbus 资源 */
   modbus_free( ctx );
}

 上面的伪代码是 是读1次的实现,如果想要对不同的从设备进行轮询,我们只需要在while(1)循环中 先设定 从设备地址,然后再 调用 modbus_read_registers即可。

   上面的代码中,大部分的接口函数都是比较容易理解,只有 modbus_read_registers 相对复杂一些,因为它实现的功能也比较多,分别为:

 ① 创建并打包 读命令。

 ② 发送 步骤①中的读指令。

 ③ 接收从机返回数据,分三次接收数据,先接收前2个字节(功能),再接收 第3个字节(数据长度),再接收剩下的字节数。

     选择3次进行接收,一方面是为了随时校验,在linux下接收不定长数据的实现不太方便,所以根据modbus协议框架,先接收 到总数据长度,然后就能按照指定长度进行接收。

 ④ 对返回数据 进行各种校验,比如设备地址,地址、数量、CRC校验等。

 ⑤ 将正确的返回 有效数据 存放到 我们指定的 缓存中。

 接下来就通过层层的调用关系来分析该代码功能,如下图所示:

 其他的 modbus_read_xxx和write功能代码实现与上面的类似。

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值