『7x24小时有问必答』
主站死机了,电机还在转?
CANopen 心跳机制,一次讲明白
设想这样一个场景:一台三轴设备正在运行,主站 PLC 突然死机。总线上没有任何报错,三个伺服驱动器也一切正常——它们只是收不到新指令了。
然后呢?如果没做任何防护,电机会按照收到的最后一条指令继续跑下去。
CANopen 里防这件事的机制叫心跳(Heartbeat)。名字听着简单,但真正用对的人不多——大部分人只做了一半。这篇我们把它讲透。
一、心跳到底是什么
一句话:每个节点按固定周期主动广播一条报文,等于定期喊一声「我还在」。监听方在约定时间内没听到这一声,就判定这个节点掉线了。
它的实现极其轻量。
▲ 心跳报文只有 1 个字节,内容是节点当前的 NMT 状态
报文的 COB-ID 是  0x700 加上节点号,所以 3 号节点的心跳就是 0x703。数据部分只有  1 个字节,内容是这个节点当前的 NMT 状态。
数值
状态
含义
0x00
Boot-up
节点刚上电或复位完成,只发一次
0x7F
Pre-operational
预运行,能收发邮箱报文但不交换过程数据
0x05
Operational
运行中,PDO 正常收发
0x04
Stopped
已停止,只响应 NMT 命令
  
注意这个设计的巧妙之处:心跳报的不只是「我活着」,还顺带说明了「我现在处在哪个状态」。所以主站靠这一个字节,就能发现某个从站是不是悄悄从 Operational 掉回了 Pre-operational——这种情况下节点还活着,PDO 却已经停了,如果只监测「有没有报文」是发现不了的。
二、两个对象,必须配套设
心跳涉及对象字典里的两项,一个管发、一个管收。
对象
名称
作用
怎么设
1017h
生产者心跳时间
本节点每隔多久发一次心跳
单位 ms,写 0 表示不发
1016h
消费者心跳时间
本节点要监视谁、超时多少
每个子索引一项,高 16 位放被监视节点的 Node-ID,低 16 位放超时毫秒数
  
1017h 是生产者时间,配置的是「我自己多久发一次」。设成 200,就是每 200ms 广播一条。设成 0,这个节点就不发心跳。
1016h 是消费者时间,配置的是「我要盯着谁、多久没消息算掉线」。它的值是 32 位的,高 16 位填被监视节点的 Node-ID,低 16 位填超时毫秒数。想同时监视多个节点,就在不同的子索引里各配一项。
这里有个最容易出错的地方,单独拎出来说。
三、超时时间怎么定
规则只有一条:消费者的超时时间必须大于生产者的发送周期。<o:page></o:page>
▲ 生产者定期发,消费者超时未收到就判定掉线
常见做法是取  1.5 到 2 倍。比如从站的 1017h 设成 200ms,主站监视它的超时就配 300 到 400ms。
为什么不能设成一样?因为总线上的报文到达时刻本来就有抖动——总线忙的时候,一条心跳晚个几毫秒是很正常的事。两个数字设成相等,等于要求心跳每次都准时零误差到达,稍有波动就会误报掉线。设备明明好好的,主站却隔三差五报节点丢失,多半就是这个原因。
反过来也别设得太大。超时配成 2 秒,意味着节点掉线两秒后主站才知道,对运动设备来说这两秒已经足够出事了。
四、和节点保护有什么区别
老一点的工程师可能更熟悉节点保护(Node Guarding)。这两个机制目的一样,做法完全不同。
<o:page></o:page>
▲ 节点保护要一问一答,心跳只需单向广播一帧
节点保护是主站主导:主站用远程帧逐个去问「你还在吗」,被问到的节点回一帧。一问一答,每个节点每个周期要占用两帧报文。
心跳是节点主导:节点自己按时广播,不需要有人来问。一帧搞定,报文量直接减半。而且因为是广播,同一条心跳可以被多个消费者同时监听——主站在盯着它,旁边另一个从站也可以同时盯着它。
CiA 301 规范之后推荐使用心跳,节点保护主要是为了兼容老设备而保留。实际配置时两者不要同时打开,容易互相干扰,也没有必要。
五、最容易被漏掉的那一半
现在回到开头那个场景。
绝大多数人配心跳时,脑子里想的是「主站监视从站」——从站掉线了主站要知道。这个方向当然要做,但只做这一个方向,主站死机的时候,谁来发现?
▲ 让从站也监视主站,才是完整的兜底
答案是让主站也发心跳,让伺服驱动器作为消费者去监视主站。
具体配置就是:主站的 1017h 设一个周期(比如 200ms),每台驱动器的 1016h 里加一项,监视主站的 Node-ID,超时设 400ms。这样一旦主站死机、程序跑飞或者网线被拔,驱动器在 400ms 内就能察觉,然后按预设动作停机。
对多轴设备来说,这是一条基本的安全兜底。只做单向监视,等于把设备的安全完全押在主站不出问题上。
六、几个实用细节<o:page></o:page>
●Boot-up 报文和心跳共用同一个 COB-ID。节点复位后进入 Pre-operational 时,会发一条数据为 0x00 的报文。主站可以拿它当作「这个节点重启了」的信号,用来触发重新下发配置——这比等心跳超时再重连要快得多。
●超时之后干什么,标准没规定。CiA 301 只定义了「检测到心跳事件」这件事,具体反应属于应用层。常见做法是主站把全网切回 Pre-operational,或者按错误行为对象(1029h)里的设定来处理。这部分要自己在程序里写清楚。
●心跳周期不是越短越好。它占的是总线带宽。10 个节点各发 100ms 心跳,就是每秒 100 帧报文。节点多的时候,200 到 500ms 通常够用,别为了「反应快」把周期压到几十毫秒。
●Node-ID 改了要同步改 1016h。消费者配置里存的是被监视节点的 Node-ID,从站换了地址而主站的监视配置没跟着改,结果就是永远等不到那条心跳,一上电就报掉线。
●EtherCAT 上没有这套机制。做过 CANopen 转 EtherCAT 的会发现,CoE 里并不用心跳——EtherCAT 靠工作计数器(WKC)和从站状态机来做在线监测,机制不一样,别照搬配置习惯。
把心跳配好,本质上是给系统装了一层「互相确认还活着」的保险。它不解决任何功能问题,平时也完全看不出效果——但主站真出问题的那一次,有没有配它,结果可能差得很远。
下一篇我们接着讲 EtherCAT 从站的落地方案:ESC 专用芯片和 FPGA 到底怎么选、成本和开发周期各是什么量级。欢迎关注我们,一起把这些看着唬人的技术名词一个个拆明白。
#工业总线 #CANopen #CAN总线 #伺服驱动器 #工业通信<o:page></o:page>

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?立即注册

x
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

上一主题上一主题         下一主题下一主题
QQ手机版小黑屋粤ICP备17165530号

关于我们·投诉举报· 用户帮助· 联系我们 · 本站服务 · 版权声明· 隐私政策 · 投搞指南

法律保护:PLC技术网,plcjs.com,plcjs.net等字样
Copyright 2010-2030. All rights reserved. 


微信公众号二维码 抖音二维码 百家号二维码 今日头条二维码哔哩哔哩二维码