3. MQTT 遗嘱消息滥用导致状态欺骗

MQTT 遗嘱消息滥用导致状态欺骗 学习卡片

遗嘱消息的触发链路与欺骗面

MQTT 遗嘱消息(Will Message)是客户端在 CONNECT 报文中预先注册的一条“最后通告”。代理只有在检测到该客户端发生非正常断开时才会代为发布遗嘱;正常发送 DISCONNECT 则不会触发。这一机制本意是让订阅者及时感知设备离线,但在未鉴权或弱鉴权场景下,攻击者可以注册一条伪造的遗嘱,再通过异常断开主动触发它,从而向订阅者注入虚假状态。

恶意客户端 clientId: fake-sensor-01 Will Topic: factory/line1/status Will Payload: {"state":"alarm"} Will QoS: 1, Retain: true MQTT 代理 Mosquitto allow_anonymous true 无 ACL 限制 遗嘱存储于会话上下文 合法订阅者 SCADA / 监控面板 订阅: factory/line1/# 信任收到的状态消息 无消息来源校验 ① CONNECT 携带 Will 字段 代理缓存遗嘱消息 等待异常断开触发 异常断开 kill -9 / 拔网线 / TCP RST 不发送 DISCONNECT ② 触发 ③ 检测到断开 代理发布遗嘱 PUBLISH → factory/line1/status Payload: {"state":"alarm"} ④ 投递 订阅者收到虚假告警 误判产线1进入告警状态 触发误操作或停机 正常场景 设备真实离线 → 遗嘱发布真实离线状态 → 订阅者正确感知 前提:遗嘱内容由合法设备注册,且代理对发布者身份有校验 恶意场景 攻击者注册伪造遗嘱 → 主动异常断开 → 代理代为发布虚假告警 根因:代理未鉴权,无法区分遗嘱注册者是否为合法设备

构造与验证步骤

以下操作在本地 Mosquitto 代理上完成,代理配置为 allow_anonymous true 且未启用 ACL,模拟未鉴权场景。攻击者使用 mosquitto_pub 的 --will-topic、--will-payload、--will-qos、--will-retain 参数注册遗嘱,然后通过强制终止进程触发异常断开。

  1. 启动代理:使用默认配置启动 Mosquitto,确认监听 1883 端口且允许匿名连接。
  2. 订阅者监听:在另一终端订阅 factory/line1/#,观察收到的所有消息。
  3. 攻击者注册遗嘱并异常断开:使用 mosquitto_pub 建立连接并注册伪造遗嘱,随后用 kill -9 强制终止进程,模拟非正常断开。
  4. 观察结果:订阅者终端应收到伪造的告警消息,验证遗嘱机制在未鉴权场景下可被滥用。
# 终端1:启动代理(默认配置,允许匿名)
mosquitto -c /etc/mosquitto/mosquitto.conf

# 终端2:订阅者监听产线1所有主题
mosquitto_sub -h 127.0.0.1 -p 1883 -t 'factory/line1/#' -v

# 终端3:攻击者注册伪造遗嘱,保持连接后强制终止
# 使用 -D 让客户端保持连接,不主动发送 DISCONNECT
mosquitto_pub -h 127.0.0.1 -p 1883 \
  -i fake-sensor-01 \
  -t factory/line1/status \
  -m '{"state":"alarm","src":"fake-sensor-01"}' \
  --will-topic factory/line1/status \
  --will-payload '{"state":"alarm","src":"fake-sensor-01"}' \
  --will-qos 1 \
  --will-retain \
  -d

# 在另一个终端强制终止该进程,触发异常断开
kill -9 $(pgrep -f 'fake-sensor-01')
关键观察点:订阅者收到的消息中 src 字段为 fake-sensor-01,但订阅者无法验证该 clientId 是否真实对应产线1的设备。如果订阅者仅根据主题和 payload 判断状态,就会误认为产线1进入告警。遗嘱消息的 retain 标志还会让后续新订阅者立即收到这条虚假状态。

欺骗风险判定与防御要点

风险维度未鉴权场景表现防御措施
遗嘱注册者身份 任意客户端可注册任意 clientId 的遗嘱 启用用户名/密码认证,绑定 clientId 与设备身份
遗嘱主题权限 可向任意主题注册遗嘱,包括其他设备的状态主题 配置 ACL,限制每个设备只能向自己的主题发布遗嘱
遗嘱内容可信度 payload 可任意伪造,订阅者无法区分真伪 应用层签名或加密,订阅者校验消息来源
retain 标志滥用 虚假状态被保留,新订阅者立即收到错误状态 对 retain 消息设置权限,或订阅者忽略 retain 标志
验证边界:本实验仅在本地隔离环境进行。遗嘱消息的触发依赖代理检测到 TCP 连接异常关闭,不同代理实现(Mosquitto、EMQX、HiveMQ)的检测超时和触发条件可能不同。在生产环境中,应结合认证、ACL 和应用层校验三层防护,不能仅依赖遗嘱机制判断设备状态。