openplc runtime v4 调试协议(英译中)
2026/3/18 12:23:06 网站建设 项目流程

调试协议

概述

OpenPLC Runtime v4 提供基于 WebSocket 的调试接口,用于实时变量检查和修改。这使得调试器(如 OpenPLC Editor)能够监控和控制 PLC 执行,而无需重复 HTTPS 连接的开销。

有关 WebSocket 连接和身份验证的详细信息,请参阅 webserver/DEBUG_WEBSOCKET.md。

连接详情

端点:wss://<主机>:8443/api/debug

身份验证:JWT 令牌(通过查询参数或认证字典)

协议:基于 WebSocket 的 Socket.IO

调试命令格式

调试命令以表示二进制协议消息的十六进制字符串形式发送。格式遵循 Modbus 风格的功能码模式。

命令结构

[功能码] [数据字节...]

所有命令和响应都以空格分隔的十六进制字节表示(例如,"41 DE AD 00 00")。

功能码

0x41 - DEBUG_INFO(调试信息)

获取 PLC 程序的调试信息。

请求:

41 DE AD 00 00

响应:

7E [信息字节...]

目的:检索已加载 PLC 程序的元数据,包括变量数量和程序哈希值。


0x42 - DEBUG_SET(设置调试)

设置变量的跟踪标志。

请求:

42 [变量索引] [跟踪标志] [附加数据...]

目的:启用或禁用特定变量的跟踪。启用跟踪后,变量值将被记录或传输以进行监控。

跟踪标志:

  • 0x00- 禁用跟踪
  • 0x01- 启用跟踪

0x43 - DEBUG_GET(获取调试)

获取变量的跟踪数据。

请求:

43 [变量索引] [数量] [附加数据...]

响应:

7E [跟踪数据字节...]

目的:检索指定变量的当前值和跟踪信息。


0x44 - DEBUG_GET_LIST(获取列表)

获取变量列表的值。

请求:

44 [数量高字节] [数量低字节] [索引1高字节] [索引1低字节] [索引2高字节] [索引2低字节] ...

示例:

44 00 03 00 00 00 01 00 02

(获取 3 个变量:索引 0, 1, 2)

响应:

7E [变量数据...]

响应格式:
响应中的每个变量包括:

  • 变量索引(2 字节)
  • 变量值(大小取决于类型)
  • 变量类型指示符

目的:在单个请求中高效地检索多个变量值。这是调试会话期间轮询变量的主要方法。


0x45 - DEBUG_GET_MD5(获取 MD5)

获取已加载 PLC 程序的 MD5 哈希值。

请求:

45 DE AD 00 00

响应:

7E [表示 MD5 哈希值的 32 个十六进制字符] 00

响应示例:

7E 61 62 63 64 65 66 31 32 33 34 35 36 37 38 39 30 31 32 33 34 35 36 37 38 39 30 31 32 33 34 35 36 00

(MD5: abcdef1234567890123456789012345678)

目的:验证调试器是否连接到预期的 PLC 程序。加载新程序时哈希值会改变。


响应格式

所有成功的响应都以0x7E(十进制 126,字符~)作为成功指示符开头。

错误响应可能返回不同的状态码或空响应。

变量类型

PLC 程序中的变量根据 IEC 61131-3 标准具有不同的类型:

布尔类型

  • BOOL- 1 位(传输为 1 字节)

整数类型

  • SINT- 8 位有符号整数
  • USINT- 8 位无符号整数
  • INT- 16 位有符号整数
  • UINT- 16 位无符号整数
  • DINT- 32 位有符号整数
  • UDINT- 32 位无符号整数
  • LINT- 64 位有符号整数
  • ULINT- 64 位无符号整数

实数类型

  • REAL- 32 位浮点数
  • LREAL- 64 位浮点数

时间类型

  • TIME- 持续时间
  • DATE- 日历日期
  • TIME_OF_DAY/TOD- 一天中的时间
  • DATE_AND_TIME/DT- 日期和时间

字符串类型

  • STRING- 可变长度字符串

位字符串类型

  • BYTE- 8 位
  • WORD- 16 位
  • DWORD- 32 位
  • LWORD- 64 位

使用示例

Python 客户端

importsocketio# 首先获取 JWT 令牌(请参阅 webserver/DEBUG_WEBSOCKET.md)TOKEN="你的_jwt_令牌_这里"sio=socketio.Client(ssl_verify=False)@sio.event(namespace='/api/debug')defdebug_response(data):ifdata.get('success'):print(f"响应:{data.get('data')}")else:print(f"错误:{data.get('error')}")# 连接sio.connect('https://localhost:8443',auth={'token':TOKEN},namespaces=['/api/debug'],transports=['websocket'])# 获取 MD5 哈希值sio.emit('debug_command',{'command':'45 DE AD 00 00'},namespace='/api/debug')# 获取变量列表(变量 0, 1, 2)sio.emit('debug_command',{'command':'44 00 03 00 00 00 01 00 02'},namespace='/api/debug')sio.sleep(2)sio.disconnect()

JavaScript 客户端

importiofrom'socket.io-client';// 首先获取 JWT 令牌consttoken='你的_jwt_令牌_这里';constsocket=io('wss://localhost:8443/api/debug',{transports:['websocket'],query:{token:token},rejectUnauthorized:false});socket.on('connected',(data)=>{console.log('已连接:',data);// 获取 MD5 哈希值socket.emit('debug_command',{command:'45 DE AD 00 00'});});socket.on('debug_response',(response)=>{if(response.success){console.log('数据:',response.data);}else{console.error('错误:',response.error);}});

轮询策略

对于变量的连续监控:

  1. 连接到 WebSocket 并使用 JWT 身份验证
  2. 获取 MD5以验证程序身份
  3. 轮询变量定期使用 DEBUG_GET_LIST(例如,每 100 毫秒)
  4. 解析响应提取变量值
  5. 断开连接当调试会话结束时

相较于 REST API 的优势:

  • 整个会话只需一次 TLS 握手
  • 延迟更低(无 HTTP 开销)
  • 双向通信
  • 持久连接

实现细节

运行时端

调试协议在 PLC 运行时核心中实现:

处理器:core/src/plc_app/debug_handler.c

关键函数:

  • process_debug_data()- 功能码的主要调度器
  • debugInfo()- 处理 DEBUG_INFO (0x41)
  • debugSetTrace()- 处理 DEBUG_SET (0x42)
  • debugGetTrace()- 处理 DEBUG_GET (0x43)
  • debugGetList()- 处理 DEBUG_GET_LIST (0x44)
  • debugGetMD5()- 处理 DEBUG_GET_MD5 (0x45)

Web 服务器端

WebSocket 接口在 Web 服务器中实现:

处理器:webserver/debug_websocket.py

关键函数:

  • init_debug_websocket()- 初始化 Socket.IO 服务器
  • handle_connect()- 验证连接
  • handle_debug_command()- 通过 Unix 套接字将命令转发到运行时

通信流程

[调试器] --WebSocket--> [Web 服务器] --Unix 套接字--> [PLC 运行时] | [调试处理器] | [变量访问]

安全性

身份验证

  • WebSocket 连接需要 JWT 令牌
  • 通过 REST API 登录端点获取令牌
  • 连接时验证令牌,并且可以撤销

授权

  • 调试访问需要经过身份验证的用户
  • 执行前验证命令
  • 命令解析中的缓冲区溢出保护

数据保护

  • 所有通信通过 WSS(WebSocket 安全)加密
  • 变量数据以二进制格式传输
  • 错误消息中不包含敏感信息

性能考虑

延迟

  • WebSocket:每个命令约 1-5 毫秒(本地网络)
  • REST API:每个请求约 10-50 毫秒(包括 TLS 握手)

吞吐量

  • 每秒可处理数百个变量读取
  • 受扫描周期时间限制(通常为 50 毫秒)
  • 使用 DEBUG_GET_LIST 进行批量请求以提高效率

资源使用

  • 每个调试会话一个 WebSocket 连接
  • CPU 开销最小(典型轮询速率下 <1%)
  • 内存使用与跟踪变量数量成正比

故障排除

连接被拒绝

原因:JWT 令牌无效或身份验证失败

解决方案:

  1. 通过/api/login获取新的 JWT 令牌
  2. 验证令牌是否正确传递(查询参数或认证字典)
  3. 检查令牌是否过期

无响应

原因:运行时未响应或命令格式错误

解决方案:

  1. 通过/api/status检查 PLC 运行时状态
  2. 验证命令格式(带空格的十六进制字符串)
  3. 检查运行时日志中的错误

无效数据

原因:变量索引超出范围或类型不匹配

解决方案:

  1. 使用 DEBUG_INFO 验证变量索引
  2. 检查 PLC 程序中的变量类型
  3. 确保程序已加载并正在运行

断开连接

原因:网络问题、超时或运行时重启

解决方案:

  1. 在客户端实现重连逻辑
  2. 重连后重新进行身份验证
  3. 重连后验证程序 MD5

相关文档

  • 编辑器集成 - OpenPLC Editor 如何连接到运行时
  • webserver/DEBUG_WEBSOCKET.md - WebSocket 连接详情
  • API 参考 - REST API 端点
  • 架构 - 系统概述
  • 安全性 - 身份验证和授权

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询