### 概述

Modbus 本身是一种信息交换的规范，Modbus RTU则是透过串口来实现Modbus 的一种方式，因此所有的信息都是通过串口来传输的；Modbus协议属于 C/S 架构，Modbus Rtu Slave是一种Server用来存放所有要被读取的工业设备数据；

**使用场景**

* Modbus属于C/S架构，在工业上会有Modbus slave作为server来存放所有要被读取的工业设备数据，如温度、湿度、距离等资料，Modbus主站可以通过串口连接到slave进行通讯；

**整体架构**
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/680098be49af6.png)


* Modbus Tcp是通过串口来实现Modbus的一种方式，Modbus Rtu Master可以对Rtu Slave发送读或者写的指令，Slave收到指令后会回复确认信息，整个Modbus的沟通建立在一来一回的讯息交换上；

* 下表概述了各个产品组件

| **产品组件**                      | **描述说明**               |
| ----------------------------- | ---------------------- |
| modbusslave\_0.0.5\_amd64.deb | Modbus rtu slave RTE组件 |
| modbusslave.library           | 上位机程序使用的库文件            |

---
### 安装卸载

**安装要求**

* 中科时代出厂的工智机；

* 工智机可以访问互联网；

* 熟悉基础的Linux操作命令；


**安装过程**

**工智机端安装Modbus Tcp Slave RTE组件**

* 上传deb包到工智机Linux环境的/home/sinsegye目录下

* 上传完成后在工智机上执行命令安装（参考下方截图，如果模块文件名发生变化则命令行中的文件名做相应更改）

```shell
cd $HOME
sudo dpkg -i modbusslave_0.0.5_amd64.deb
```
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/680098cbe83ee.png)



* 修改RTE的配置文件，ComponentManger字段下加入modbusslave

```shell
sudo nano /usr/local/etc/SinsegyeRTE/SinsegyeRTE.cfg
```

```shell
ComponentManager]
 Component.0=retainDeamon
 Component.1=CmpCanBusUtils
 Component.2=CmpSinsegyeLibs
 Component.3=SinsegyeCmp
 Component.4=modbusslave
```

* 重启RTE服务，使新加入的modbusslave被调用

```shell
sudo systemctl restart sinsegyerte.service
```

**Metafacture安装library**

* 打开Metafacture，点击“工具”  -- “库存储”
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/680098d381d4b.png)

* 点击“安装” -- 选中modbus slave的库文件，点击“打开”
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/680098dd3da55.png)

* 工程中点击“库管理器” -- “添加库” -- 选中modbus库点击“确定”
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/680098e59de3e.png)


**更新安装**
**工智机端升级Modbus Tcp Slave RTE组件**

* 上传deb包到工智机Linux环境的/home/sinsegye目录下

* 上传完成后在工智机上执行命令安装（参考下方截图，如果模块文件名发生变化则命令行中的文件名做相应更改）

```shell
cd $HOME
sudo dpkg -i modbusslave_0.0.5_amd64.deb
```

* 重启RTE服务，使新升级的modbusslave被调用

```shell
sudo systemctl restart sinsegyerte.service
```

**Metafacture升级library**

* 打开Metafacture，点击“工具”  -- “库存储”
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/680098f2170b9.png)

* 点击“安装” -- 选中要升级的modbus slave的库文件，点击“打开”
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/680098fb129a1.png)

* 工程中点击“库管理器” -- “添加库” -- 选中modbus库点击“确定”
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/68009902a9825.png)

**卸载过程**

**工智机端卸载Modbus Tcp Slave RTE组件**

* 工智机上执行命令卸载modbusslave

```shell
sudo dpkg -r modbusslave
```

* 修改RTE的配置文件，ComponentManger字段下去掉modbusslave

```shell
sudo nano /usr/local/etc/SinsegyeRTE/SinsegyeRTE.cfg
```

* 重启RTE服务

```shell
sudo systemctl restart sinsegyerte.service
```

**卸载MetaFacture侧的Modbus Tcp slave library**

* MetaFacture界面点击“工具” -- “库存储”&#x20;
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/6800990b8b6bf.png)

* 对话框中选中安装的modbus slave的库，点击“卸载”
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/68009914126e0.png)

---
### 技术说明

**快速启动**

**本例软、硬件配置**

**硬件：**

1. SX5100工智机 MetaOS V24.08.15\_SX5

2. Win10 PC


**软件：**

1. MetaFacutre V1.0.6.3

2. Modbus Poll主站工具

**本例实验要求及原理**

* 实验要求：按照“安装卸载”部分中的“安装过程”配置完成Modbus Rtu Slave环境

**实验原理**
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/6800991c91267.png)


* 第三方Modbus Rtu主站通过串口连接向Metafacture Modbus Rtu 从站发送请求，主要包含：功能码、目标寄存器的地址和数量、写操作时的数据；从站收到请求后先检查数据的合法性，然后执行请求的操作，响应主站请求；

* 上位机和工智机使用EtherNet连接。

* 上位机上，MetaFacture下装工程到工智机。工程中会包含下面的试验操作步骤中的配置。

* 工智机与第三方Modbus Rtu主站通过串口连接。

 **本例实验操作步骤**

**新建Modbus tcp slave工程的实验步骤如下：**

* POU中声明区域调用modbus rtu slave功能块，配置线圈、离散输入、保持寄存器、输入寄存器各2048点；

```shell
PROGRAM rtu_slave
VAR
        FB_Modbus_Com_Slave_0      : ModbusSlave.FB_Modbus_Com_Slave;
        bxEnable                   : BOOL:=TRUE;
        pbyCoilA                   : ARRAY [0..2048] OF BOOL;
        pbyDiscreteInputA          : ARRAY [0..2048] OF BOOL;
        pbyInputRegisterA          : ARRAY [0..2048] OF WORD;
        pbyHoldingRegisterA        : ARRAY [0..2048] OF word;
        bBusy                      : BOOL;
        bActive                    : BOOL;
        bError                     : BOOL;
        eError                     : BOOL;
        ulRecvCounter              : UDINT;
        ulSendCounter              : UDINT;  
END_VAR
```

* POU中程序区域调用FB\_Modbus\_Com\_Slave\_0，配置从站COM口、从站Id、串口波特率、线圈地址、保持寄存器地址、离散输入地址、输入寄存器地址等信息；

```shell
FB_Modbus_Com_Slave_0(
        bEnable               :=bxEnable ,
        uiSlaveId             :=1 ,
        comPort               :=ModbusSlave.COM_PORT.ttys6 ,   //SX5  ttys6、 SX58 ttyS0、SX2 ttyS0;
        baudrate              :=ModbusSlave.SERIAL_BAUDRATE.baudrate_115200 ,
        byteSize              :=ModbusSlave.SERIAL_DATABIT.databit_8 ,
        parity                :=ModbusSlave.SERIAL_PARITY.parity_no ,   //主站也要同步设置成这样
        stopBits              :=ModbusSlave.SERIAL_STOPBIT.stopbit_1 ,
        udiTimeOut            :=10000 ,
        psMbTest              := ,
        pbyCoil               :=ADR(pbyCoilA),
        pbyDiscreteInput      :=ADR(pbyDiscreteInputA),
        pbyInputRegister      :=ADR(pbyInputRegisterA),
        pbyHoldingRegister    :=ADR(pbyHoldingRegisterA),
        udiRwBitSize          :=SIZEOF(pbyCoilA),
        udiInBitSize          :=SIZEOF(pbyDiscreteInputA),
        udiInWordSize         :=SIZEOF(pbyInputRegisterA),
        udiRwWordSize         :=SIZEOF(pbyInputRegisterA),
        bBusy=> ,
        bActive=> ,
        bConnect=> ,
        bError=> ,
        eError=> ,
        ulRecvCounter=> ,
        ulSendCounter=> );
```

* 工程运行后即可使用Modbus Poll连接Metafacture Rtu Slave，对从站进行读写操作；主站与从站数据一致；

![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/6800992c10df3.png)

![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/68009933ce0da.png)
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/68009938b1e7f.png)

![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/6800993fe88ac.png)

---
### **创建Modbus Rtu从站**

#### 功能块FB介绍
![](https://resource.helplook.net/docker_production/3648ne/article/exvtrjKf/68009949654b4.png)


#### 参数介绍

输入参数

| 参数名称               | 参数类型            | 描述                                                                              |
| ------------------ | --------------- | ------------------------------------------------------------------------------- |
| bEnable            | BOOL            | 启动modbus rtu slave                                                              |
| uSlaveId           | UINT            | 从站id信息                                                                          |
| comPort            | COM\_PORT       | 串口号，例如COM\_PORT.ttys6                                                           |
| comPortStr         | STRING          | comPort参数只支持到/ttys8；如遇到大于8的或者其他串口设备，请使用comPortStr变量，如comPortStr := '/dev/ttys9; |
| baudrate           | SERIAL\_        | 波特率设置，有baudrate\_9600、baudrate\_115200 两种配置                                     |
| byteSize           | SERIAL\_DATABIT | 串口传输数据位,可配置databit\_4、databit\_5、databit\_6、databit\_7、databit\_8五种配置           |
| parity             | SERIAL\_PARITY  | 串口通信校验方式，有parity\_no、parity\_odd、parity\_even 三种                                |
| stopBits           | SERIAL\_STOPBIT | 串口通信停止位，有stopbit\_1、stopbit\_1\_5、stopbit\_5 三种                                 |
| udiTimeOut         | UDINT           | 超时时间                                                                            |
| psMbTest           | INT             | 默认0，Modbus测试用数据，默认不用配置                                                          |
| pbyCoil            | POINTER TO BYTE | 从站线圈，可读可写                                                                       |
| pbyDiscreteInput   | POINTER TO BYTE | 从站离散输入，只读                                                                       |
| pbyInputRegister   | POINTER TO BYTE | 从站保持寄存器，可写可读                                                                    |
| pbyHoldingRegister | POINTER TO BYTE | 从站输入寄存器，只读                                                                      |
| udiRwBitSize       | UDINT           | 以位可读写寻址的最大个数，用于线圈                                                               |
| udiInBitSize       | UDINT           | 以位可读寻址的最大个数，用于离散输入                                                              |
| udiInWordSize      | UDINT           | 以字可读寻址的最大个数，用于输入寄存器                                                             |
| udiRwWordSize      | UDINT           | 以字可读写寻址的最大个数，用于保存寄存器                                                            |

输出参数

| 参数名称          | 参数类型  | 描述                           |
| ------------- | ----- | ---------------------------- |
| bBusy         | BOOL  | 当功能块被激活时，被置为True，一直保持到收到确认信号 |
| bActive       | BOOL  | Modbus从站激活标志位                |
| bConnect      | BOOL  | Modbus连接成功标志位                |
| bError        | BOOL  | 错误标志位。True为报错，False无报错       |
| eError        | BOOL  | 错误反馈id                       |
| uIRecvCounter | ULINT | 数据接收计数器                      |
| uISendCounter | ULINT | 数据发送计数器                      |