RS485 SDK 控制
本章供上位机、工站及第三方 SDK 的集成人员使用,说明如何通过设备的 SDK RS485 接口查询状态、下发操作并接收结果。日常操作员不需要使用本接口;现场集成和维护时, 应先用无副作用的状态查询完成通信验证,再接入检测、参数或标定操作。
重要
本章属于授权集成附录,不是用户操作说明。设备用户应在触摸屏完成检测、维护、标定、 设置和升级;集成测试不得改变触摸屏当前选择,也不得与现场操作同时进行。
重要
本章所述“SDK RS485 接口”是设备与外部上位机通信的 Modbus RTU 接口,不是 “进水拓展板”页面中的“RS485 开关”。后者用于控制拓展板所连接的外部设备, 不能用来配置或通断本章的 SDK 通信。
适用范围与安全边界
SDK 可以用于:
查询设备和检测状态;
启动、暂停、恢复或停止检测;
读取、修改并保存允许开放的设备参数;
启动经过授权的维护、清洗或标定流程;
接收命令进度、最终响应、日志文本、参数数据和健康故障信息。
SDK 不应绕过设备屏幕上的安全提示,也不应在有人拆机、管路断开、试剂不足或设备 处于其他维护流程时强制启动动作。远程执行泵、阀、排水、标定等操作前,现场必须有 人员确认设备周围无泄漏风险。
接线
断电后完成接线,再依次给设备和上位机适配器上电。
设备端 |
上位机/转换器端 |
要求 |
|---|---|---|
|
|
同名端连接;不同厂商标注可能相反 |
|
|
同名端连接;通信失败时核对适配器说明书 |
|
信号地 |
建议连接,避免两端参考电位差过大 |
使用双绞线连接 A、B,屏蔽层按现场接地规范单点接地。
总线采用手拉手连接,不要星形分叉;较长线路在总线两端使用匹配终端电阻。
同一总线上的从站地址必须唯一。
不要带电插拔裸线,不要将 RS485 端子接到市电、网口或普通 TTL 串口。
USB 转 RS485 适配器必须支持半双工 Modbus RTU,并正确控制收发方向。
若 A/B 标识不统一,先查看转换器说明书。只有在断电状态下才能交换 A、B 试验。
默认通信参数
项目 |
默认值 |
|---|---|
协议 |
Modbus RTU |
波特率 |
|
数据位 |
|
校验 |
无 |
停止位 |
|
流控 |
无 |
设备角色 |
Modbus 从站 |
从站地址 |
|
合法从站地址 |
|
修改设备角色或从站地址后必须重启设备才会生效。常规 SDK 集成应保留设备的默认从站 角色,由 SDK 作为 Modbus 主站。除非项目明确要求多节点反向轮询,否则不要切换设备为 主站模式。
通信模型
RS485 线路上传输的是标准 Modbus RTU 帧。设备控制命令位于 Modbus Holding Register 邮箱中,不能把设备命令字节直接写到串口。
SDK 生成设备命令
-> 打包到下行邮箱
-> 0x10 写多个保持寄存器
-> 设备受理并执行
-> 设备把响应放入上行邮箱
-> SDK 用 0x03 读取保持寄存器
-> 解包并判断业务响应码
方向 |
起始寄存器 |
数量 |
Modbus 功能码 |
|---|---|---|---|
SDK -> 设备 |
|
按实际载荷计算,最多 123 |
|
设备 -> SDK |
|
固定读取 123 |
|
警告
Modbus 写入成功仅表示命令已送入通信邮箱,不表示检测、清洗、标定等业务已经完成。 SDK 必须继续读取响应邮箱,直到收到该命令的最终业务响应。
邮箱格式
相对偏移 |
内容 |
说明 |
|---|---|---|
|
|
有效字节数,范围 |
|
|
16 位消息序号 |
|
|
每个寄存器先放高字节、再放低字节 |
一次写入所需的寄存器数:
register_count = 2 + ceil(payload_length / 2)
载荷为奇数字节时,最后一个寄存器的低字节补 0x00,但补位不计入
payload_length。单条载荷最大为 242 字节,一条完整设备命令不得拆到两个邮箱序号中。
序号规则
每条新消息的序号必须与上一条已发送消息不同。
SDK 可从
1开始递增,达到65535后自然回绕。相同序号的重复消息会被设备忽略,用于避免重发造成重复动作。
不要只更新序号而保留旧长度和旧载荷,否则旧命令可能被再次执行。
SDK 也必须按上行序号去重,避免重复处理同一响应。
重连后先读取一次上行邮箱并记录当前序号,再发送新的下行序号。
第一次联调:查询检测状态
检测状态查询无副作用,适合作为首次联调命令。设备命令载荷为:
AA BB 21
假设下行序号为 1,SDK 应从寄存器 0 写入以下 4 个寄存器:
寄存器 |
值 |
说明 |
|---|---|---|
|
|
载荷长度为 3 |
|
|
序号为 1 |
|
|
帧头 |
|
|
命令 |
推荐联调步骤:
设置串口为
115200/8/N/1,从站地址设为1。用功能码
0x10从地址0写入上述 4 个寄存器。确认收到正常 Modbus 写响应。
每隔约
100 ms用功能码0x03从地址128读取 123 个寄存器。当长度为
1..242且序号变化时,按长度解包响应。解析响应正文,并依据业务响应码判断是否结束。
若第 3 步成功但始终没有业务响应,优先检查轮询的从站地址、起始寄存器和上行序号 去重逻辑,不要连续重发控制命令。
SDK 打包与解包示例
以下伪代码用于说明外部 SDK 的行为,不限定具体编程语言或 Modbus 库。
MAX_PAYLOAD = 242
UPLINK_START = 128
UPLINK_REGISTERS = 123
def pack_mailbox(payload, sequence):
assert 1 <= len(payload) <= MAX_PAYLOAD
registers = [len(payload), sequence & 0xffff]
for offset in range(0, len(payload), 2):
high = payload[offset]
low = payload[offset + 1] if offset + 1 < len(payload) else 0
registers.append((high << 8) | low)
return registers
def unpack_mailbox(registers):
length = registers[0]
sequence = registers[1]
if length == 0:
return None
if length > MAX_PAYLOAD:
raise ProtocolError("invalid mailbox length")
payload = bytearray()
for value in registers[2:]:
payload.append((value >> 8) & 0xff)
payload.append(value & 0xff)
return sequence, bytes(payload[:length])
def send_command(modbus, slave_id, command_payload, sequence):
registers = pack_mailbox(command_payload, sequence)
modbus.write_multiple_registers(slave_id, 0, registers)
def poll_new_response(modbus, slave_id, last_sequence):
registers = modbus.read_holding_registers(
slave_id, UPLINK_START, UPLINK_REGISTERS)
message = unpack_mailbox(registers)
if message is None or message[0] == last_sequence:
return None
return message
生产 SDK 还应加入串口互斥、CRC/Modbus 异常处理、超时、断线重连、响应分类、日志 脱敏和操作审计。对于泵、阀、检测、标定等非幂等动作,超时后应先查询设备状态, 不得直接以新序号盲目重发。
命令响应处理
设备可能返回 UTF-8/ASCII 状态文本,也可能返回二进制参数 BSON。文本状态通常包含:
Status code: <code>
Result: <result>
并可能附带 Action、Parameters 或 Info。SDK 应按字段解析,不要依赖某一种语言的
完整提示句。
响应码 |
SDK 处理 |
|---|---|
|
正在处理或输出分段内容;继续收取,不结束事务 |
|
命令已受理;记录事务并继续等待最终响应 |
|
成功终态;完成事务并更新界面 |
|
请求或参数错误;停止重试并提示修正输入 |
|
设备忙或流程冲突;查询状态,等待当前流程结束 |
|
操作已取消;完成事务并显示取消结果 |
|
执行失败;记录原始响应并进入故障处理 |
完整解释和操作建议见指令响应码。
异步命令
检测、维护和标定通常是异步命令。正确生命周期为:
发送命令 -> 收到该命令的 202 -> 设备执行 -> 收到该命令的最终状态
最终状态只能是 200/400/409/499/500。SDK 不得把以下情况当作完成:
收到 Modbus
0x10正常响应;收到
102或202;收到一段日志或过程文本;
收到其他操作产生的状态事件;
上行邮箱序号发生变化但正文不属于当前事务。
同一连接上一次只发起一个会改变设备状态的流程最稳妥。需要并行处理查询时,SDK 应按 命令类型、响应正文和本地事务状态做关联,并保留完整时间线。
长文本和分段结果
日志、参数列表等长内容可能被拆成多条消息。SDK 应按照消息中的 stream_id、
chunk_index、chunk_count、offset 和 total_length 重组,校验段号无缺失后再交给
用户。分段内容不是命令终态,重组完成后仍要等待最终响应码。
参数数据可能以 AA BB 60 开头,后接 BSON 文档。应使用成熟 BSON 库并依据 BSON
自身长度解析,不能通过查找 0x00 判断文档结束。
常用控制工作流
查询状态
使用 AA BB 21 查询检测状态。SDK 应在以下时机主动查询:
建立连接后;
控制命令超时后;
收到
409后;通信中断并恢复后;
操作员准备启动检测、维护或标定前。
检测控制
操作 |
设备命令 |
SDK 前置检查 |
|---|---|---|
启动检测 |
|
设备空闲、试剂和废液状态正常、检测项目合法 |
暂停检测 |
|
当前有可暂停的检测流程 |
恢复检测 |
|
当前处于暂停状态 |
停止/取消 |
|
提示用户流程将终止,并等待 |
查询状态 |
|
无副作用,可随时用于确认状态 |
启动检测载荷为:
AA BB 4F <dilution> <PH> <NH3N> <NO2> <ALK> <CA> <MG> <HARD>
项目开关使用 0 或 1。稀释倍率和项目组合应来自受控配置,不应让用户输入任意
字节。收到 202 后锁定重复启动按钮,最终响应到达后再恢复。
参数读写
0x33:按参数 ID 读取,参数 ID 为 16 位小端。0x34:按参数 ID 写入数值或 UTF-8 字符串。0x1C:将已修改参数保存到设备。0x0B:恢复默认参数,属于高风险操作,必须二次确认。
参数写入成功不一定等于已永久保存。推荐流程为“读取旧值 -> 校验新值 -> 写入 -> 读取 回验 -> 保存 -> 再次读取”。通信角色或从站地址等启动参数保存后还需要重启设备。
日志和数据
通过 SDK 获取日志或文件时,应先确认设备未处于 USB 大容量存储占用状态。长结果按分段 消息重组,并记录设备返回的实际文件名、时间范围和字节数。日常查看、下载和导出方法见 日志查看与数据下载。
标定和维护
SDK 可调用已授权的标定、清洗和维护命令,但必须复用手册中的现场前置条件:标液正确、 管路连接正确、废液容量足够、现场有人值守。SDK 界面应明确显示当前标定对象、阶段、 已用标液及最终结果。具体步骤见设备标定流程和 维护指令参考。
不要在 SDK 中向普通操作员暴露原始泵号、阀位、掩码或底层调试操作。需要底层执行器 测试时,应进入受控的工厂/工程模式,由授权人员按维修规程操作。
健康故障处理
命令响应码和健康故障码是两套独立信息:响应码说明本次命令是否受理或完成;健康故障码
说明设备当前或近期检测到的异常。一次命令返回 200,不代表设备不存在其他健康告警。
SDK 收到健康故障时应保存:
故障码和原始文本;
首次出现、最近出现和恢复时间;
当时正在执行的命令及响应码;
设备状态、连接状态和操作员;
同一时间段的相关日志。
界面应按健康管理故障码显示“现象、可能原因、设备行为和处理 方法”,并允许维护人员标记已检查项目。严重故障、漏液、异常发热或电气异味必须提示 现场立即停机断电,不能提供“一键忽略并继续运行”。
超时、重试与重连
建议将通信超时和业务超时分开配置:
通信超时:等待一次 Modbus 请求响应的时间;可有限次数重试同一 Modbus 事务。
受理超时:写入成功后等待
202或同步终态的时间。业务超时:从
202到最终状态的时间;按检测、排水、标定等流程分别设置。
对查询类命令,可以在确认无响应后使用新序号重发。对启动检测、加液、排水、清洗、 标定、参数恢复和重启等有副作用的命令,业务响应超时后应:
停止自动重发。
恢复读取上行邮箱并检查是否漏收响应。
查询设备当前状态。
根据状态决定继续等待、显示已执行、允许取消或转人工处理。
将原命令序号、时间和所有响应写入 SDK 审计日志。
断线重连后,不应假设设备回到空闲。先读取并去重当前邮箱,再执行状态查询;若设备仍在 运行原流程,SDK 应恢复监控,而不是再次启动。
多设备接入
一条 RS485 总线可以连接多个设备,但每台设备必须有唯一地址 1..247。主站依次轮询,
不得并发向总线发送多个请求。设备数量、线长和轮询频率增加时,应适当延长完整轮询周期,
并保证每台设备的上行邮箱被及时读取。
设备默认从站模式只有一个上行邮箱。若 SDK 长时间不读取,新消息可能覆盖等待中的旧消息。 因此应持续轮询,命令执行期间优先读取正在操作的设备。周期遥测在 RS485 上默认关闭; 如项目开启遥测,还应评估 242 字节邮箱限制和额外总线负载。
设备也支持特定项目使用的 Modbus 主站模式,但该模式没有广播发现,最多跟踪 8 个节点, 且外部节点必须实现从站邮箱。普通上位机 SDK 不应使用此模式。
SDK 验收清单
[ ] A/B/GND 接线、屏蔽和终端匹配符合现场规范。
[ ] 串口参数为
115200/8/N/1,从站地址正确。[ ] 支持 Modbus
0x03和0x10,CRC 由可靠协议库处理。[ ] 能正确处理奇数、偶数和最大 242 字节载荷。
[ ] 下行序号递增,上行序号去重,回绕后仍能工作。
[ ]
AA BB 21状态查询可以稳定重复执行。[ ] 能区分 Modbus 成功、
202受理和最终响应。[ ] 能处理
102/200/202/400/409/499/500。[ ] 能重组长文本,并使用 BSON 库解析参数响应。
[ ] 有副作用命令超时后先查状态,不自动重复执行。
[ ] 断线重连后能恢复当前流程监控。
[ ] 能记录响应码、故障码、原始响应和操作审计信息。
[ ] 多设备地址唯一,轮询不会造成总线冲突。
常见问题排查
现象 |
可能原因 |
处理方法 |
|---|---|---|
完全没有 Modbus 响应 |
A/B 接反、串口参数或地址错误、转换器方向控制异常 |
断电核对接线;确认 |
出现 CRC 或帧错误 |
干扰、接地不良、支线过长、终端不当或多个主站同时发送 |
检查双绞线、屏蔽、共地和终端;确保总线只有一个主站 |
|
只检查了 Modbus 响应,未轮询上行邮箱 |
从寄存器 |
状态查询只执行一次 |
后续仍使用相同下行序号 |
每条新消息使用不同序号,并同时更新完整载荷 |
同一操作执行两次 |
超时后用新序号盲目重发有副作用命令 |
停止重发,先查询设备状态并检查是否漏收最终响应 |
反复读到同一结果 |
SDK 未按上行序号去重 |
保存最后处理的上行序号,相同序号不重复通知用户 |
收到 |
设备正忙、当前流程不允许该操作 |
查询状态,等待或先按规程停止冲突流程 |
收到 |
命令长度、字段、范围或项目组合不合法 |
检查设备命令和小端字段;不要修改序号后重复旧载荷 |
收到 |
执行、硬件、存储或内部异常 |
保存完整响应和日志;结合健康故障码按排故章节处理 |
参数值乱码或无法解析 |
把 BSON 当文本、用零字节截断数据 |
识别 |
长日志缺段 |
轮询太慢或未按分段元数据重组 |
提高轮询频率;按流 ID 和段号校验,缺段时重新发起查询 |
RS485 遥测一直没有数据 |
RS485 周期遥测默认关闭 |
这不是连接故障;先用 |
进水拓展板开关无效 |
混淆了两个 RS485 概念 |
SDK 连接使用本章接口;拓展板开关仅按拓展板章节操作 |
仍无法恢复时,保留 SDK 原始 Modbus 请求/响应、邮箱序号、设备响应正文、故障码、设备 时间和接线照片,按联系支持中的清单提交。不要只提供“通信失败”截图。