libmodbus移植到嵌入式ArmLinux(imx6ull)-- 学习记录

1.modbus 移植到 linux


1.1 modbus 源码下载



可以从 libmodbus 官网 http://libmodbus.org/download/下载 3.1.4 版本

将“libmodbus-3.1.4.tar.gz”下载。

1.2 ARM-linux 上的 modbus 移植和编译



交叉编译使用的编译器是“gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf”,如下图所示。

通过 ssh 将下载好的源码压缩包“libmodbus-3.1.4.tar.gz”拷贝到 Ubuntu 上,使用命 令“tar -xzvf libmodbus-3.1.4.tar.gz”解压,解压后生成目录“libmodbus-3.1.4”,如下 图所示。

进入 libmodbus-3.1.4,执行命令mkdir -p install创建install目录。然后执行下面配置命令

./configure ac_cv_func_malloc_0_nonnull=yes --host=arm-linux-gnueabihf --enable-static --prefix=$(pwd)/install/ 

  --host=后面的是编译器前缀,--prefix=后面的是安装目录,可根据自己环境确定,如下图所示。

如下图所示,执行完毕。

执行make命令,如下图所示。

执行make install 命令,如下图所示。

查看安装目录 install,在 install 生成三个目录:include、lib、share,如下图所示。。

查看lib的文件为32-bit的ARM格式文件。

将编译出来的 lib 路径下的所有文件拷贝到开发板的“/lib”目录下。

至此,modbus 的 arm-linux 的库文件编译完成。

2. 测试libmodbus的master主机读数据功能

 

2.1 进入libmodbus/test目录,修改unit-test-server.c (modbus主机测试) 中的”/dev/ttymxc2”,改成你测试的串口设备号

 

    ctx = modbus_new_rtu("/dev/ttymxc2", 9600, 'N', 8, 1);

修改int main主函数,如下所示:

int main(int argc, char *argv[])
{
    uint8_t *tab_rp_bits;
    uint16_t *tab_rp_registers;
    uint16_t *tab_rp_registers_bad;
    uint16_t tab_reg[64];
    modbus_t *ctx;
    int i;
    uint8_t value;
    int nb_points;
    int rc;
    float real;
    uint32_t ireal;
    struct timeval old_response_timeout;
    struct timeval response_timeout;
    int use_backend;

    ctx = modbus_new_rtu("/dev/ttymxc2", 9600, 'N', 8, 1);

    if (ctx == NULL) {
        fprintf(stderr, "Unable to allocate libmodbus context\n");
        return -1;
    }
    modbus_set_debug(ctx, TRUE);

    modbus_set_slave(ctx, 3);

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

   while(1)
   {
       printf("--------------------\n");
        rc = modbus_read_registers(ctx,0x1064,26,tab_reg);
        if(rc == -1)
        {        fprintf(stderr,"%s\n",modbus_strerror(errno));
            return -1;
        }
      for(i=0; i<26; i++)
      {
         printf("reg[%d] = %d(0x%x)\n",i,tab_reg[i],tab_reg[i]);
      }
      usleep(1000000);
   }


     modbus_close(ctx);
     modbus_free(ctx);
     return 0;
}
上面函数功能是每隔1秒读取从机3的数据,从0x1064起始地址读取26个数据。

2.2 改好后重先进行编译

 

#make clean
#make all

编译完后就生成了unit-test-server可执行文件

2.3 进入.lib目录,执行cd .libs 命令,然后复制unit-test-server可执行文件到imx6ull开发板上,如下所示操作(根据自己的开发板的路径设置拷贝)

 

在开发板上进入/home/hanhui/test目录,输入./unit-test-server执行命令,如下图所示。

从上图可以看到,成功打开/dev/ttymxc2(串口3),波特率参数为 9600 bauds (N, 8, 1)

每隔1秒发送[03] [03] [10] [64] [00] [1A] [80] [FC]读取命令,然后返回reg[0]到reg[25]的26个数据。