# Modbus ASCII

Modbus ASCII 是 Modbus 协议的一种变体，它使用 ASCII（美国标准代码信息交换）字符来编码数据包。

Modbus ASCII 和 Modbus RTU（Remote Terminal Unit）都支持串口通信。这两种变体的主要区别在于数据的编码方式不同：

Modbus RTU：使用二进制编码，传输效率高，但对干扰和距离更敏感。
Modbus ASCII：使用 ASCII 字符编码，传输效率相对较低，但更易于调试和诊断，因为传输的信息可以直接阅读。

Modbus ASCII 适合在不需要高速数据传输、调试和诊断重要性大于传输效率的场合使用。

## 添加插件

在 **配置 -> 南向设备**，点击**添加设备**来创建设备节点，输入插件名称，插件类型选择 **Modbus ASCII** 启用插件。

## 设备配置

点击插件卡片或插件列，进入**设备配置**页。配置 Neuron 与设备建立连接所需的参数，下表为插件相关配置项。

| <div style="width:100pt">参数</div>               | 说明                                                    |
| -------------------- | ------------------------------------------------------- |
| **连接超时时间** | 等待设备返回指令响应的时间。 |
| **最大重试次数** | 发送读取指令失败后最大重试次数。 |
| **指令重新发送间隔** | 发送读取指令失败后重新发送读指令时间间隔，单位为毫秒。 |
| **指令发送间隔** | 发送每条读写指令之间的等待时间。某些串口设备在较短时间内接收到连续指令时，可能会丢弃某些指令。 |
| **字节序**   | 32 位数据类型字节序，ABCD 对应 1234。 |
| **开始地址** | 点位起始地址从 1 开始或从 0 开始。 |
| **串口设备** | 串口设备的路径，如 Linux 系统中 /dev/ttyS0。 |
| **停止位** | 串口连接参数。 |
| **校验位** | 串口连接参数。 |
| **波特率** | 串口连接参数。 |
| **数据位** | 串口连接参数。 |

## 设置组和点位

完成插件的添加和配置后，要建立设备与 Neuron 之间的通信，首先为南向驱动程序添加组和点位。

完成设备配置后，在**南向设备**页，点击设备卡片/设备列进入**组列表**页。点击**创建**来创建组，设定组名称以及采集间隔。完成组的创建后，点击组名称进入**点位列表**页，添加需要采集的设备点位，包括点位地址，点位属性，数据类型等。

公共配置项部分可参考[连接南向设备](../south-devices.md)，本页将介绍支持的数据类型和地址格式部分。

### 数据类型

* INT16
* UINT16
* INT32
* UINT32
* INT64
* UINT64
* FLOAT
* DOUBLE
* BIT
* STRING
* BYTES

### 地址格式

> SLAVE!ADDRESS\[.BIT][#ENDIAN]\[.LEN\[H]\[L]\[D]\[E]]\[.BYTES]

#### **SLAVE**

必填，指从机地址或者是站点号。

#### **ADDRESS**

必填，指寄存器地址。Modbus 协议有四个区域，每个区域最大有 65536 个寄存器，每个区域的地址范围如下表所示。

| 区域                       | 地址范围          | 属性        | 寄存器大小     | 功能码        | 数据类型 |
| ------------------------- | ---------------- | ---------- | ------------- | ------------ | ------- |
| Coil（线圈）                | 000001 ~ 065536 | 读/写       | 1Bit          | 0x01, 0x05, 0x0f | BIT     |
| Input（离散量输入）          | 100001 ~ 165536 | 读          | 1Bit         | 0x02          | BIT     |
| Input Register（输入寄存器） | 300001 ~ 365536 | 读          | 16Bit, 2Byte        | 0x04          | BIT, INT16, UINT16,<br />INT32, UINT32, INT64,<br />UINT64, FLOAT,<br />DOUBLE, STRING |
| Hold Register（保持寄存器）  | 400001 ~ 465536 | 读/写       | 16Bit, 2Byte        | 0x03, 0x06, 0x10 | BIT, INT16, UINT16,<br />INT32, UINT32, INT64,<br />UINT64, FLOAT,<br /> DOUBLE, STRING |

#### **.BIT**

选填，寄存器中的特定 bit，例如：
| 地址         | 数据类型 | 说明                                                |
| ----------- | ------- | --------------------------------------------------- |
| 1!300004.0  | bit     | 指站号为1，输入寄存器区域，地址为 300004，第 0 位。    |
| 1!400010.4  | bit     | 指站号为1，保持寄存器区域，地址为 400010，第 4 位。    |
| 2!400001.15 | bit     | 指站号为2，保持寄存器区域，地址为 400001，第 15 位。   |

#### **#ENDIAN**

选填，字节顺序，适用于 int16/uint16/int32/uint32/float 数据类型，详细说明见下表。
| 符号 | 字节顺序 | 支持的数据类型        | 备注 |
| --- | ------- | ------------------ | ----- |
| #B  | 2,1     | int16/uint16       |       |
| #L  | 1,2     | int16/uint16       | 不填，默认字节顺序 |
| #LL | 1,2,3,4 | int32/uint32/float | 不填，默认字节顺序 |
| #LB | 2,1,4,3 | int32/uint32/float | |
| #BL | 3,4,1,2 | int32/uint32/float | |
| #BB | 4,3,2,1 | int32/uint32/float | |

::: tip
点位字节序优先级高于节点字节序配置。即点位配置字节序后，字节序按照点位的配置，忽略节点配置。
字节顺序可能用 ABCD 表示，只需将 1234 对应 ABCD 即可。例如 ABCD 对应默认字节序 1234 (#LL)。
:::

#### .LEN\[H]\[L]\[D]\[E]

当数据类型为 STRING 类型时，**.LEN** 是必填项，表示字符串需要占用的字节长度，每个寄存器中包含**H**，**L**，**D** 和**E** 四种存储方式，如下列表格所示。
| 符号 | 说明                                  |
| --- | ------------------------------------- |
| H   | 一个寄存器存储两个字节，高字节在前低字节在后。 |
| L   | 一个寄存器存储两个字节，低字节在前高字节在后。 |
| D   | 一个寄存器存储一个字节，且存储在低字节。      |
| E   | 一个寄存器存储一个字节，且存储在高字节。      |

#### **.BYTES**

选填，读写 bytes 类型数据的长度，适用于 bytes 数据类型。

::: tip
Modbus 驱动一个寄存器包含 2 个 byte，在以 bytes 数据类型读取和写入 Modbus 寄存器数据时，请保证 bytes 参数设置为偶数。
:::

### 地址示例

| 地址         | 数据类型 | 说明 |
| ----------- | ------- | --------- |
| 1!300004    | int16    | 指站号为 1，输入寄存器区域，地址为 300004，字节顺序为 #L |
| 1!300004#B  | int16    | 指站号为 1，输入寄存器区域，地址为 300004，字节顺序为 #B |
| 1!300004#L  | uint16   | 指站号为 1，输入寄存器区域，地址为 300004，字节顺序为 #L |
| 1!400004    | int16    | 指站号为 1，保持寄存器区域，地址为 400004，字节顺序为 #L |
| 1!400004#L  | int16    | 指站号为 1，保持寄存器区域，地址为 400004，字节顺序为 #L |
| 1!400004#B  | uint16   | 指站号为 1，保持寄存器区域，地址为 400004，字节顺序为 #B |
| 1!300004    | int32    | 指站号为 1，输入寄存器区域，地址为 300004，字节顺序为 #LL |
| 1!300004#BB | uint32   | 指站号为 1，输入寄存器区域，地址为 300004，字节顺序为 #BB |
| 1!300004#LB | uint32   | 指站号为 1，输入寄存器区域，地址为 300004，字节顺序为 #LB |
| 1!300004#BL | float    | 指站号为 1，输入寄存器区域，地址为 300004，字节顺序为 #BL |
| 1!300004#LL | int32    | 指站号为 1，输入寄存器区域，地址为 300004，字节顺序为 #LL |
| 1!400004    | int32    | 指站号为 1，保持寄存器区域，地址为 400004，字节顺序为 #LL |
| 1!400004#LB | uint32   | 指站号为 1，保持寄存器区域，地址为 400004，字节顺序为 #LB |
| 1!400004#BB | uint32   | 指站号为 1，保持寄存器区域，地址为 400004，字节顺序为 #BB |
| 1!400004#LL | int32    | 指站号为 1，保持寄存器区域，地址为 400004，字节顺序为 #LL |
| 1!400004#BL | float    | 指站号为 1，保持寄存器区域，地址为 400004，字节顺序为 #BL |
| 1!300001.10  | String  | 指站号为1，输入寄存器区域，地址为 300001，字符长度为 10，字节顺序为 L，即占用的地址为 300001 ～ 300005 |
| 1!300001.10H | String  | 指站号为1，输入寄存器区域，地址为 300001，字符长度为 10，字节顺序为 H，即占用的地址为 300001 ～ 300005 |
| 1!300001.10L | String  | 指站号为1，输入寄存器区域，地址为 300001，字符长度为 10，字节顺序为 L，即占用的地址为 300001 ～ 300005 |
| 1!400001.10  | String  | 指站号为1，保持寄存器区域，地址为 400001，字符长度为 10，字节顺序为 L，即占用的地址为 400001 ～ 400005 |
| 1!400001.10H | String  | 指站号为1，保持寄存器区域，地址为 400001，字符长度为 10，字节顺序为 H，即占用的地址为 400001 ～ 400005 |
| 1!400001.10L | String  | 指站号为1，保持寄存器区域，地址为 400001，字符长度为 10，字节顺序为 L，即占用的地址为 400001 ～ 400005 |
| 1!400001.10D | String  | 指站号为1，保持寄存器区域，地址为 400001，字符长度为 10，字节顺序为 D，即占用的地址为 400001 ～ 400010 |
| 1!400001.10E | String  | 指站号为1，保持寄存器区域，地址为 400001，字符长度为 10，字节顺序为 E，即占用的地址为 400001 ～ 400010 |

## 数据监控

完成点位的配置后，您可点击 **监控** -> **数据监控**查看设备信息以及反控设备，具体可参考[数据监控](../../../admin/monitoring.md)。
