摘要

  • OPSAWG 的 UCL 草案第 15 版为基于组身份的 ACL、按时间生效的 ACE 和 RADIUS User-Access-Group-ID 定义了数据模型;文件已进入 RFC Editor 队列,但仍是 Internet-Draft,并非 RFC 或部署证明。
  • CoA 可以改变组成员关系,却不能把 NAS、控制器和多个 PEP 压缩成一个原子动作。可靠记录必须保留决定版本、映射版本、目标 PEP 集、逐点安装与激活回执,以及真实数据包和服务结果。

变更窗口里,值班人员把一名外包工程师从普通维护组临时移入事故响应组。AAA 服务器发出 CoA-Request,NAS 更新会话,控制器重算 ACL。两台策略执行设备返回成功;第三台设备正在恢复连接,没有收到新的五元组映射。

管理界面显示“授权变更成功”。同一个用户从一条路径可以访问应急控制面,从另一条路径仍按旧组被拒绝。更危险的情况也同样可能发生:旧策略比新策略宽松,使已经撤销的权限继续存在。

这里没有一个单独的谎言。AAA 服务器确实做出了新决定,NAS 确实接受了 CoA,控制器确实产生了新配置,两台 PEP 也确实完成安装。错误来自把这些局部事实合成为一个未经证明的全局状态。

《A YANG Data Model and RADIUS Extension for Policy-Based Network Access Control》第 15 版正好把这条边界暴露出来。草案扩展 RFC 8519 的 ACL YANG 模型,增加用户、设备与应用端点组,允许 ACE 以源或目的 Group ID 匹配,并增加有效时间表。它还定义 RADIUS User-Access-Group-ID,让认证触发的接入控制能够传递用户组信息。

文件成熟度较高。Datatracker 显示它是 OPSAWG 工作组文件,目标状态为 Proposed Standard,已提交 IESG,并处于 RFC Editor 队列的最终审查阶段。IANA 审查为“OK,需采取行动”。第 15 版日期是 2026 年 4 月 2 日,2026 年 10 月 4 日到期。它仍没有 RFC 编号。标准流程进展可以证明文本走到了哪里,不能证明某张生产网络已经按同一种方式执行。

组身份解决了易变地址,却没有消灭映射

草案面对的工程问题真实存在。用户会移动,IPv6 临时地址会轮换,NAPT 会让地址与主体失去简单的一对一关系,虚拟机、容器和应用会迁移。若每条策略都直接绑定 IP 地址与传输端口,维护成本高,过期规则也很难发现。

Group ID 把较稳定的业务意图放在这些坐标之上。策略可以说“事故响应组可以访问这项服务”,而不是反复写入每个当下地址。但 PEP 最终仍要知道哪些包属于这个组。抽象层没有删除映射,只是把映射变成控制系统的一等对象。

草案给出两种主要部署方式。一种由 SDN 控制器维护 Group ID 到 IP/传输字段的动态映射,例如五元组,再把普通 ACL 下发到 PEP。另一种由设备级 PEP 理解组身份,把进入的数据包映射成源组或目的组,直接执行组 ACL。

第一种方式降低 PEP 的特殊能力要求,却让移动性与下发延迟成为核心风险。用户地址改变之后,旧 ACL 仍然可以语法正确、安装成功,只是它匹配的主体已经不是当前主体。第二种方式减少控制器频繁更新,却可能需要专用硬件或软件,甚至影响转发性能。

草案明确说,策略中的 Group ID 字符串不必与封装中的标签完全相同;字符串如何映射到标签或包头字段不在本文范围内。RFC 9638 的 GBP 只是一种示例。因此,即使 Group ID 名称没有变化,标签表仍可能变化;抓到一个标签也不能在没有版本化映射的情况下解释其含义。

第 8.3 节要求为 Group ID 到包字段的映射做充分设置,并强调当网络同时支持 RADIUS 等不同机制时,要特别注意映射得到恰当执行。这是一项运营义务,不是模型自动提供的结论。

CoA 把“当前状态”拆成多个时刻

User-Access-Group-ID 可以出现在 CoA-Request 中。这个设计允许在会话进行期间改变授权。也正因为如此,系统必须回答“哪一层的当前状态”。

在身份与制度层,人员调度决定可能已经生效。在 AAA 层,CoA 已发出。在 NAS 层,新会话属性可能已安装。在控制器层,新映射和 ACL 已生成。在各个 PEP 上,状态可能分别是待发送、已验证、已安装、已激活、失败或未知。在数据平面上,不同路径的数据包可能遇到不同版本。

把所有层折叠成 current_group=incident-response 会制造虚假原子性。更准确的模型应保留意图状态与执行状态,并为每个目标 PEP 记录事务。目标集合本身也要有版本:若资产清单漏掉一台新设备,它不会报错,因为系统从未把它列为应完成的对象。

CoA-ACK 也不能携带该属性。即使 CoA 协议层返回成功,它表达的范围仍需严格解释。它不是每个外部 PEP 的安装证明,更不是数据包已经按照新策略到达服务的证明。

失败策略不能临时猜测。某些撤权应当在无法完成全网收敛时关闭访问;某些关键服务变更则可能需要保留上一版已知策略,以免局部更新造成更大中断。领导层应提前决定哪些规则 fail closed、哪些规则保持旧状态,并要求系统把“保留旧策略”与“新策略生效”分开显示。

Access-Request 中的值只是建议

草案对 RADIUS 包类型给出不同语义。User-Access-Group-ID 可以出现在 Access-Accept;此时系统在认证后应用相关接入控制。它也可以出现在 Access-Request,但在那里只是一项偏好提示,服务器没有义务采纳。

若事件平台只抽取 user、group 和时间戳,便会丢掉谁提出、谁决定。请求方写入的偏好可能被下游误认为服务器授权。最小记录必须保留包类型、方向、客户端与服务器身份、请求/响应关联、所有属性实例以及最终决定。

Access-Reject 与 Access-Challenge 中不得出现该属性;CoA-ACK 与 CoA-NACK 中也不得出现。某个包里没有属性,并不自动构成新的成员关系声明,它可能只是遵守属性放置规则。

Access-Accept 可以包含多个 User-Access-Group-ID,表示用户属于多个组。这个能力不等于已经定义所有 ACL 冲突的统一裁决。一个组允许、另一个组拒绝;一个永久生效、另一个只在值班窗口生效;规则顺序与厂商实现都可能改变结果。若日志只留下一个“主组”,便无法解释某个包为何被允许。

多组情况下,需要保存完整成员集合、ACL 版本、候选规则、优先顺序、冲突策略与最终命中规则。Group ID 是索引,不是最终判决。

Accounting-Request 是一个观察者的陈述

User-Access-Group-ID 还可以出现在 Accounting-Request。草案说,NAS 可以借此确认它收到了该属性,并且正在执行相应策略。这是有价值的回执:它把会话、组与 NAS 的执行陈述联系起来。

但 NAS 的陈述不能代表所有 PEP。网络里还可能有边界防火墙、服务网关、交换结构或应用入口。NAS 未必知道它们各自使用的映射版本、ACL 与时间表,也未必能观察数据包离开之后的服务结果。

正确做法不是贬低 accounting,而是标注来源与范围。审计可以写成:服务器授权 A、B 两组;NAS 声明收到并执行;控制器映射版本 218;PEP-1 与 PEP-2 激活 ACL 640;PEP-3 未确认;前两个点出现预期规则计数;应用探针只验证了路径一。这样的报告没有一个简单的绿色图标,却能告诉运维人员缺失证据在哪里。

数据包计数也有边界。计数器增长证明某些包命中过规则,不能证明所有合法流量成功,也不能证明旁路不存在。允许测试、拒绝测试、路径观察与应用响应需要分别命名观察点。

时间表让策略依赖时钟

UCL 模块为 ACE 增加 effective-schedule。它可以是一段时间,也可以是复用 RFC 9922 的循环规则;如果没有配置时间表,ACE 立即且始终适用。

时间表能表达值班、维护和临时授权,也引入时区、循环、例外日期与时钟健康。两台 PEP 存储相同文本,并不一定在边界时刻同时激活。提交延迟、时区数据库差异或时钟漂移都能使结果分叉。

因此,配置读取只能证明“设备存了什么”。执行回执还应包含时区标识、规则版本、例外集合、时钟来源、激活状态与观察时刻。尤其在夏令时切换或跨时区运维中,不能以控制器时间替代设备实际使用的时间。

草案的安全考虑指出,未经授权修改有效时间表可能造成服务中断或不可用;未经授权读取则可能泄露规则何时应用,帮助攻击者选择时间。时间表既要保证完整性,也要按需要限制可见性。公开审计可以证明时间控制经过验证,而不公开实时窗口细节。

零个 YANG 错误不是零个运行风险

Datatracker 对第 15 版记录的 YANG 验证结果是零错误、零警告。这说明模块通过了相应形式检查,是重要的文档证据。它不证明两个实现对循环时间的解释完全一致,不证明控制器找到了全部 PEP,也不证明包走过预期路径。

第 14 版到第 15 版的差异主要是日期、措辞、NVO3 展开、格式以及把 YANG 编写指南更新为已发布的 RFC 9907。没有新增互操作测试、生产测量或性能数据。文章不能把成熟的标准文本误写成成熟的生产结果。

管理接口本身要使用安全传输和双向认证,NACM 可限制 NETCONF/RESTCONF 用户的操作范围。草案指出,非法改写端点组可以伪造或删除组;非法改写 ACE 的组匹配可以放行本应拒绝的访问,也可以拒绝本应允许的访问。

这些保护解决“谁能改”。它们不解决“获准的人是否把正确版本发到了正确设备”。一个完全认证的旧配置仍然是旧配置。授权链与执行链都要保留。

RADIUS 的传输也有自身安全边界。草案假定客户端与服务器之间存在可信关系,并提到 IPsec 或 TLS。RADEXT 正在推进弃用不安全实践以及新的 RadSec 文本,但那些文件也有各自状态。加密与完整性保护消息,不能让请求提示自动升级为授权,也不能让下游 PEP 自动收敛。

为变更建立最小回执

一条可复核的组策略变更至少要回答九件事:谁被认证;哪个权威决定了哪些组;是请求提示还是服务器接受;使用哪一版 Group ID 映射;哪一版 ACL 与时间表;哪些 PEP 必须变更;每个 PEP 到了哪一步;哪些数据包在何处命中;服务结果是什么。

“已发送”不是“已验证”,“已验证”不是“已安装”,“已安装”也不是“已激活”。控制器需要保存逐点事务标识与回读指纹。一个 PEP 失败时,不应把其他 PEP 回滚或重启,更不应把平均成功率显示成完整执行。

Heng Lu 的 Minimum Initial Specification 思路适合这里:共享最小的可验证交接格式,而不是强迫所有网络选择相同控制器、标签或失败策略。只要组决定、映射、ACL、目标集与结果能够对齐,本地实现仍可演进。

现实层次原则进一步解释为何要分开记录。Group ID 是符号;AAA 决定与 ACL 是制度和控制对象;设备里激活的规则是可执行状态;数据包与服务是被观察到的现实。上层正确不能自动担保下层完成。

Running-Code Primacy 要求故意制造不整齐的场景:会话中轮换 IPv6 地址,CoA 期间断开一个 PEP,把应用迁移到新容器,在时间边界制造时钟偏差,让控制器在发送与确认之间重启。安全系统不必让所有测试都成功,但必须准确保留部分成功、失败与未知。

开头那次变更真正缺少的不是另一个“成功”字段,而是一份逐层回执。CoA 证明权威决定开始移动;每个 PEP 的确认说明移动走到了哪里;数据包说明现实最终到达何处。只有三者同时被保存,Group ID 才是降低复杂度的抽象,而不是掩盖复杂度的标签。

Sources