支持“一次性使用”设备¶
https://blueprints.launchpad.net/nova/+spec/one-time-use-devices
随着直接透传加速设备的使用增加,租户之间某种使用后清理工作流程的需求也随之增加。直接透传给虚拟机的网卡可能需要重新写入已知的良好固件,以确保前一个用户没有以某种方式破坏它。GPU 内存中可能存在需要清零的敏感残留数据。NVMe 设备是一种需要擦除或丢弃的存储介质。
问题描述¶
目前,操作员没有好的方法可以在 Nova 之外定义和执行设备清理工作流程。此外,Nova 也不打算承担此类任务,以支持长期“不再进行编排”的目标。
用例¶
作为操作员,我希望向实例提供具有已知安全固件和设备状态的透传设备。
作为专用云操作员,我可能拥有需要在使用后进行特殊处理的专用硬件(电源或总线复位、配置初始化等)。
作为云操作员,我希望提供快速的直接透传存储支持,但同时避免租户之间信息泄露的风险。
作为云操作员,我希望在每次用户使用后检查我的透传 NVMe 设备的写入损耗指示器,以避免将超过安全阈值的设备分配出去。
提议的变更¶
Nova 将支持“一次性使用”设备。也就是说,我们将仅为新的实例分配该设备一次。当该实例被删除时,该设备将不会自动返回到可分配状态(就像通常发生的那样),而是会保持在保留状态,直到操作员自己的工作流程采取一些操作将其标记为可再次使用。确保此类设备在清理之前不可重新分配是一个潜在的安全敏感步骤,不能被遗漏,并且 Nova 应该自己执行此操作,即使它不会承担实际的设备清理任务。
这里的注释机制将利用 reserved 库存计数,以及 PCI-in-placement。基本上,当 Nova 要为实例分配设备时,它将通过增加 reserved 计数来跟进。当我们要释放设备时,我们将不会触碰 reserved 计数,从而使设备的资源提供者完全保留(因此不可分配)。
注意
由于一对一的资源提供者核算,预计这将仅用于 PCI-in-placement 和 PF 设备。如果确定有需要,可以通过另一种机制为 VF 启用此功能。
通过操作员决定的任何工作流程,他们都可以清理设备,并在准备好让设备重新加入可分配设备池时减少 reserved 计数。这可能包括监听已删除实例的通知并安排此类清理。
我们还将引入一个新的特性(暂定名为 HW_ONE_TIME_USE),Nova 将将其添加到它作为一次性设备管理的资源提供者。这将使操作员更容易地调查所有可能需要清理的设备提供者。这不会传达是否需要清理(由 total=1,reserved=1,used=0 信号指示),而是该设备在条件正确时可能需要清理。
实现¶
设备的保留(即“烧毁”其一次性使用)将在计算节点中发生,(临时)靠近我们在 PCI 跟踪器中执行声明和核算的位置。这将最大限度地减少设备“烧毁”但实际上未被实例使用的失败窗口。在资源跟踪器的 instance_claim() 结束时,我们当前调用 _update(),后者调用 _update_to_placement()。在那里,我们执行一些库存和分配修复,包括对 placement 跟踪的 PCI 设备。在此库存修复例程中,我们将保留分配的 PCI 设备,因为我们已经在根据需要审核(和修复/更新)库存了。
注意
从现在开始,我们将使用术语“烧毁”来指代已保留的设备,因此它将不会被重新分配。这发生在实例能够使用它的时间之前(在所有情况下),并且保持在该状态,直到外部操作将保留计数降回零。换句话说,“烧毁”意味着 reserved=total。
通过以上述方式进行操作,我们将获得设备的同步保留(即,它将在实例开始运行之前发生),并且尽可能地延迟。我们还将获得“修复”已分配设备为保留状态的能力,如果管理员稍后将其标记为一次性使用,则会发生这种情况。
移动操作将以类似的方式工作,因为 _move_claim() 方法也会在本地声明完成后同步调用 _update()。值得注意的是,具有一次性设备的实例的移动将在它开始在目标位置运行(即,当它到达验证状态时)时“烧毁”该设备,并且回滚将不会“解燃”它。
生命周期操作¶
从技术上讲,一次性使用设备应该能够完全参与所有实例生命周期操作。但是,有一些注意事项,因此下面讨论了一些情况
重建:设备可以在不采取任何其他操作的情况下原地重用
驱逐:当实例启动时,原始设备将被“烧毁”,并且在原始主机恢复并在删除原始实例的分配后,将保持如此。驱逐过程将在新主机上分配和烧毁一个新的设备,在启动过程中。
冷迁移:当实例在新位置启动时,将在目标位置分配一个新设备。一旦实例到达验证状态,目标位置的新设备将被烧毁。在确认时,源设备将保持烧毁状态,在回滚时,目标设备将被烧毁。请注意,状态设备上的状态(即数据)不会被 Nova 复制。
实时迁移:如果该设备已经可以实时迁移,那么将允许它,并且在操作完成后源设备将保持“烧毁”状态,并且目标位置的新设备将在迁移过程中被烧毁。
注意
我们需要对 placement 进行更改,以允许过度订阅的资源提供者“朝着安全”方向发展,这意味着“变得不那么过度订阅”。对于一次性设备,即使提供者由于设备被保留而从技术上讲已经过度订阅,我们也必须允许交换实例的分配与迁移 UUID 在源节点上。请注意,这已经在 Nova/Placement 中存在问题,并且我们报告了多个针对此问题的错误,即分配比率的变化导致过度订阅会阻止操作员将实例迁移走。我们需要无论如何解决这个问题,并且该修复也将适用于一次性设备。在此之前,迁移操作(冷迁移、调整大小和实时迁移)将对一次性设备(隐式)被阻止。
注意
在不咨询调度器的情况下进行驱逐可能会导致我们将实例发送到请求没有事先检查是否可分配(即,已经烧毁)的 PCI 设备的宿主机。我们需要确保在这种情况下,在将设备分配给实例之前(这应该发生在 ResourceTracker._update() 作为分配修复的一部分),计算节点上的任何操作都会失败。
备选方案¶
另一种选择是无所作为,并继续像今天一样运行。Nova 故意不提供任何设备清理能力,也没有任何真正的钩子或集成供希望使用它的人使用。
另一种选择是说这属于 Cyborg 的范围,是的。Nova 官方认可 Cyborg 是外部、有状态设备准备、清理和生命周期管理的解决方案,这并没有改变。一次性设备的想法介于“无所作为”和“在 Cyborg 中完成”之间,它对 nova 的一个非常小的更改,可以允许用于现有 API 的外部集成,以便人们在更简单的情况下执行他们需要做的事情。当然,从操作员的角度来看,如果 Cyborg 中没有对其设备的支持,那么构建一个自制解决方案的更简单的流程会更容易。对于拥有定制(可能是科学)硬件的操作员来说,要求他们编写完整的 Cyborg 驱动程序,以便在每次使用后调用 shell 脚本,这要求太高了。
数据模型影响¶
如果使用现有的 PCI dev_spec 将设备标记为 one_time_use=(yes|no),则不会对数据模型产生任何影响。这与最近的 migrate-vfio-devices-using-kernel-variant-drivers 规范类似,该规范允许操作员将其标记为 live_migratable=(yes|no)。
REST API 影响¶
无。
安全影响¶
没有直接的安全影响,尽管从理论上讲,它将允许操作员通过清理或重新初始化设备来提高设备透传工作负载的安全性。
通知影响¶
无。
其他最终用户影响¶
无(对用户不可见)。
性能影响¶
这涉及在分配设备后向 placement 发出一次额外的调用以更新库存。这在性能影响方面应该可以忽略不计,并且错误处理将与分配本身失败的情况相同。
其他部署者影响¶
不希望使用此功能的部署者将不受影响。那些使用它的人将能够通过配置为他们的 PCI 设备启用它,并编写他们自己的外部集成,前提是设备在分配后将保持保留状态。
开发人员影响¶
无
升级影响¶
无
实现¶
负责人¶
- 主要负责人
danms
功能联络人¶
- 功能联络人
N/A
工作项¶
解析 one_time_use 来自 [pci]dev_spec 配置
在 instance_claim() 路径中,在更新 placement 中的 PCI 设备的分配和库存时,添加代码以增加保留计数
添加文档和示例清理侦听器脚本
处理 placement bug_1943191(可能并行进行)
依赖项¶
这需要对 Placement 进行依赖项修复,以允许在过度订阅时交换分配。虽然不是严格必需的,但修复这个长期存在的问题将启用一次性设备的冷迁移。
测试¶
这将完全在单元/功能测试中进行测试,因为它需要使用实际设备进行 tempest 测试。
在审查和提交期间,将使用实际设备进行一次性测试。
文档影响¶
将添加操作员文档,解释该标志的含义以及操作员可以依赖的保证。将提供一个示例脚本来处理设备清理,作为起点,但关于如何稳健地执行此操作的详细文档将留给消费者。
参考资料¶
标记机制与此最近的努力几乎相同
历史¶
发布名称 |
描述 |
|---|---|
2025.2 Flamingo |
引入 |