CPU 资源跟踪¶
https://blueprints.launchpad.net/nova/+spec/cpu-resources
我们希望简化计算节点在 CPU 资源清单方面的配置,并使专用 CPU 资源的定量跟踪与通过 Placement API 跟踪共享 CPU 资源保持一致。
问题描述¶
目前 Nova 中 CPU 资源的跟踪方式过于复杂,并且由于 CPU pinning 与 NUMA 相关概念在 InstanceNUMATopology 和 NUMATopology(宿主机)对象内的耦合,难以用与 Nova 中其他资源类别一致的方式进行推理。
专用 CPU 资源的跟踪未使用 Placement API 进行,因此无法查看系统中的物理处理器使用情况。围绕宿主机 CPU 清单和客户机 CPU pinning 的 CONF 选项和额外规格/镜像属性难以理解,尽管已经努力记录它们,但只有少数人知道如何“正确”配置计算节点以托管某些工作负载。
我们希望简化计算节点在 CPU 资源清单方面的配置,并使专用 CPU 资源的定量跟踪与通过 Placement API 跟踪共享 CPU 资源保持一致。
定义¶
- 物理处理器
宿主机上的单个逻辑处理器,与物理 CPU 核心或超线程相关联
- 专用 CPU
已标记为仅供单个客户机使用的物理处理器
- 共享 CPU
已标记为供多个客户机使用的物理处理器
- 客户机 CPU
在客户机中配置的逻辑处理器
- vCPU
代表单个客户机的 CPU 资源单元,近似于单个物理处理器的处理能力
- PCPU
代表单个客户机的专用 CPU 数量的资源类别
- CPU pinning
确定应将哪个客户机 CPU 分配给哪个专用 CPU 的过程
- pinset
一组物理处理器
- pinset 字符串
一种专门编码的字符串,指示一组特定的物理处理器
- NUMA 配置的宿主机系统
具有多个物理处理器以非均匀内存访问架构排列的宿主机计算机。
- 客户机虚拟 NUMA 拓扑
当客户机希望其 CPU 资源以特定的非均匀内存架构布局排列时。客户机的虚拟 NUMA 拓扑可能与底层宿主系统的物理 NUMA 拓扑匹配,也可能不匹配。
- 模拟器线程
QEMU 创建的操作系统线程,用于对客户机 VM 执行某些维护活动
- I/O 线程
QEMU 创建的操作系统线程,代表客户机 VM 执行磁盘或网络 I/O
- vCPU 线程
QEMU 创建的操作系统线程,代表客户机 VM 执行 CPU 指令
用例¶
作为一个 NFV 编排系统,我希望能够区分需要稳定性能的 CPU 资源和可以容忍不一致性能的 CPU 资源
作为一个边缘云部署者,我希望指定哪些物理处理器应用于专用 CPU,哪些应用于共享 CPU
作为 VNF 供应商,我希望向基础设施指定我的 VNF 是否可以将超线程兄弟用作专用 CPU
提议的变更¶
添加 PCPU 资源类别¶
为了在 Placement 服务中跟踪专用 CPU 资源,我们需要一个新的资源类别来区分由共享在许多客户机之间(或许多客户机 vCPU 线程)的主机 CPU 提供的客户机 CPU 资源,以及由单个主机 CPU 提供的客户机 CPU 资源。
将为此创建一个新的 PCPU 资源类别。它将代表由专用主机 CPU 提供的客户机 CPU 资源的单位。此外,将添加一个新的配置选项,[compute] cpu_dedicated_set,以跟踪将分配给 PCPU 清单的主机 CPU。这将补充现有的 [compute] cpu_shared_set 配置选项,现在将用于跟踪将分配给 VCPU 清单的主机 CPU。这两个集合必须是不相交的集合。如果这两个值不相交,我们将以错误消息启动失败。如果它们是,则未包含在组合集合中的任何主机 CPU 都将被视为保留给宿主机。
Flavor.vcpus 字段将继续代表实例使用的 CPU 总数,无论它们是专用(PCPU)还是共享(VCPU)。此外,cpu_allocation_ratio 将仅适用于 VCPU 资源,因为对专用资源进行超额承诺没有意义。
注意
这会对现有的配置选项(如 vcpu_pin_set 和 [compute] cpu_shared_set)产生重大影响。这些内容在 下面 讨论。
添加 HW_CPU_HYPERTHREADING 特性¶
Nova 将硬件线程作为单独的“核心”公开,这意味着具有例如两个 Intel Xeon E5-2620 v3 CPU 的宿主机将报告 24 个核心 - 2 个插槽 * 6 个核心 * 2 个线程。但是,硬件线程不是真正的 CPU,因为它们与其他线程共享许多组件。因此,在这些核心上运行的进程可能会受到争用的影响。这对于需要无争用的工作负载(例如:实时工作负载)来说可能是一个问题。
我们支持名为“CPU 线程策略”的功能,该功能首次在 Mitaka 中添加,它为用户提供了一种控制这些线程如何被实例使用的机制。此功能支持的策略之一,isolate,允许用户将给定 CPU 的线程兄弟标记为保留,从而避免资源争用,但代价是无法将这些核心用于任何其他工作负载。但是,在典型的基于 x86 的平台(启用超线程)上,这可能会导致实例消耗 2 倍于预期的核心数量,基于 Flavor.vcpus 的值。这些未跟踪的分配不能在 Placement 环境中支持,因为我们需要知道在调度时请求多少 PCPU 资源,并且我们不能在没有绝对确定每个宿主机都启用了超线程的情况下增加此数字。因此,我们需要提供另一种跟踪宿主机是否具有超线程的方法。为此,我们将添加新的 HW_CPU_HYPERTHREADING 特性,该特性将在检测到超线程时报告。
注意
这会对现有的 CPU 线程策略功能产生重大影响。这些内容在 下面 讨论。
示例宿主机配置¶
考虑一个具有 24 个宿主机物理 CPU 核心并启用超线程的计算节点。操作员希望为宿主机处理(不用于客户机实例)保留 1 个物理 CPU 核心及其线程兄弟。此外,操作员希望使用 8 个宿主机物理 CPU 核心及其线程兄弟作为专用客户机 CPU 资源。剩余的 15 个宿主机物理 CPU 核心及其线程兄弟将用于共享客户机 vCPU 使用,这些物理处理器用于共享客户机 CPU 资源的分配率为 8:1。
操作员可以配置 nova.conf 如下
[DEFAULT]
cpu_allocation_ratio=8.0
[compute]
cpu_dedicated_set=2-17
cpu_shared_set=18-47
virt 驱动程序将构建一个包含单个资源提供程序表示计算节点的提供程序树,并相应地报告 PCPU 和 VCPU 的清单
COMPUTE NODE provider
PCPU:
total: 16
reserved: 0
min_unit: 1
max_unit: 16
step_size: 1
allocation_ratio: 1.0
VCPU:
total: 30
reserved: 0
min_unit: 1
max_unit: 30
step_size: 1
allocation_ratio: 8.0
示例 flavor 配置¶
考虑以下示例 flavor/镜像配置,按复杂程度递增排序。
一个简单的 Web 应用程序服务器工作负载需要几个 CPU 资源。该工作负载不需要任何专用 CPU 资源
resources:VCPU=2
例如
$ openstack flavor create --vcpus 2 ... example-1 $ openstack flavor set --property resources:VCPU=2 example-1
或者,您可以跳过显式资源请求,这将由默认提供。这是当前行为
$ openstack flavor create --vcpus 2 ... example-1
一个数据库服务器需要 8 个 CPU 资源,并且该工作负载需要专用 CPU 资源以最大程度地减少同一硬件上托管的其他工作负载的影响
resources:PCPU=8
例如
$ openstack flavor create --vcpus 8 ... example-2 $ openstack flavor set --property resources:PCPU=8 example-2
或者,您可以跳过显式资源请求并使用遗留的
hw:cpu_policyflavor 额外规格代替$ openstack flavor create --vcpus 8 ... example-2 $ openstack flavor set --property hw:cpu_policy=dedicated example-2
在这种遗留情况下,
hw:cpu_policy充当resources=PCPU:${flavor.vcpus}的别名,如 稍后 所讨论。一个运行分组核心处理应用程序的虚拟网络功能需要 8 个 CPU 资源。VNF 指定其收到的专用 CPU 不应是超线程兄弟(换句话说,它希望为其专用 CPU 资源获得完整的核心)
resources:PCPU=8 trait:HW_CPU_HYPERTHREADING=forbidden
例如
$ openstack flavor create --vcpus 8 ... example-3 $ openstack flavor set --property resources:PCPU=8 \ --property trait:HW_CPU_HYPERTHREADING=forbidden example-3或者,您可以跳过显式资源请求和特性请求,并使用遗留的
hw:cpu_policy和hw:cpu_thread_policyflavor 额外规格代替$ openstack flavor create --vcpus 8 ... example-3 $ openstack flavor set --property hw:cpu_policy=dedicated \ --property hw:cpu_thread_policy=isolate example-3在这种遗留情况下,
hw:cpu_policy充当resources=PCPU:${flavor.vcpus}的别名,而hw:cpu_thread_policy充当required=!HW_CPU_HYPERTHREADING的别名,如 稍后 所讨论。注意
使用遗留额外规格不会与以前完全相同,因为具有超线程的宿主机将被排除在外,而不是使用但隔离其线程兄弟。这是不可避免的,如 下面 所讨论。
注意
最初将无法在同一请求中请求 PCPU 和 VCPU。此功能以后可能会添加,但在此之前将拒绝此类请求。
注意
您会注意到资源请求仅包含实例所需的 PCPU 和 VCPU 资源总量。完全由 nova.virt.hardware 模块负责将客户机 CPU 适当地固定到宿主机 CPU,例如考虑 NUMA 亲和性。Placement 服务将返回与请求的 PCPU 资源量匹配的提供程序树。但是 Placement 不会进行特定 CPU 的分配,只会将 CPU 资源量分配给这些资源的特定提供程序。
备选方案¶
关于 Flavor.vcpus 同时引用 VCPU 和 PCPU 资源类别,肯定会造成一些混淆。为了避免这种情况,我们可以将 PCPU 资源类别称为 CPU_DEDICATED,以更明确地表明其用途。但是,我们将继续使用 VCPU 资源类别来表示共享 CPU 资源,并且 PCPU 似乎是现有 VCPU 资源类别的更好逻辑对应物。
另一个选项是将 PCPU 资源类别称为 VCPU_DEDICATED。这强调了术语vCPU 指的是实例的 CPU(而不是宿主机 CPU),但名称很笨拙,仍然有些令人困惑。
数据模型影响¶
NUMATopology 对象需要更新,以包含一个新的 pcpuset 字段,该字段补充了现有的 cpuset 字段。将来,我们可能希望将这些字段重命名为例如 cpu_shared_set 和 cpu_dedicated_set。
REST API 影响¶
无。
安全影响¶
无。
通知影响¶
无。
其他最终用户影响¶
这个提议实际上应该使 CPU 资源跟踪更容易推理和理解,因为它可以使共享和专用 CPU 资源的清单保持一致。
性能影响¶
Placement 服务能够完成 NUMATopologyFilter 当前所做的大部分工作,应该会对性能产生积极影响。NUMATopologyFilter 将被缩减到仅处理关于特定线程分配策略(超线程的容忍度)是否可以由计算节点满足的问题。传递给 NUMATopologyFilter 的 HostInfo 对象数量将已经减少到仅具有所需数量的专用和共享 CPU 资源的那些宿主机。
请注意,在计算节点能够将 NUMA 节点表示为提供程序树中的子资源提供程序之前,NUMATopologyFilter 仍然需要包含围绕 CPU pinning 和理解 NUMA 节点 CPU 数量的更深奥和复杂的逻辑。
其他部署者影响¶
主要而言,对部署者的影响将体现在文档方面。需要提供良好的文档,例如上述风味配置示例,向运维人员展示需要配置哪些资源和特性规格,才能获得特定的行为,以及哪些配置选项已更改。
开发人员影响¶
无。
升级影响¶
此功能的升级影响很大,虽然我们会尽力减少对最终用户的影响,但仍会造成一定程度的干扰。以下描述了各种影响。在阅读这些内容之前,可能值得阅读以下文章,这些文章描述了 nova 在各种情况下的当前行为
一个关键点是,在 Train 版本中,新的行为必须是选择加入的。我们认识到运维人员可能需要时间来升级关键数量的计算节点,以便它们报告 PCPU 类。这一点在以下多个地方都有体现。
配置选项¶
- 概要:
用户必须取消设置
vcpu_pin_set和reserved_host_cpus配置选项,并设置现有的[compute] cpu_shared_set和新的[compute] cpu_dedicated_set选项之一或两者。
我们将在 Train 版本中弃用 vcpu_pin_set 配置选项。如果在 Train 版本中同时设置了 [compute] cpu_dedicated_set 和 [compute] cpu_shared_set 配置选项,则将完全忽略 vcpu_pin_set 选项,并使用 [compute] cpu_shared_set 来计算每个计算节点报告的 VCPU 资源数量。如果未在 Train 版本中设置 [compute] cpu_dedicated_set 选项,我们将发出警告,并回退到使用 vcpu_pin_set 作为分配 PCPU 资源的主机逻辑处理器集合。这些 CPU 不会从用于生成 VCPU 资源清单的主机逻辑处理器列表中排除,因为 vcpu_pin_set 对于所有基于 NUMA 的实例都很有用,而不仅仅是那些具有固定 CPU 的实例,因此我们不能假设这些实例将仅由固定实例使用。但是,这种双重报告清单并不被认为是一个问题,因为我们长期以来的建议是使用主机聚合来分组固定和未固定的实例。因此,我们不应该在同一主机上遇到这两种类型的实例,并且 VCPU 或 PCPU 清单中的一个将被未使用。如果未使用主机聚合,并且云中同时存在固定和未固定的实例,用户将已经看到过度分配问题:即,未固定的实例不遵守固定实例的固定约束,并且可能在应该“专用”于固定实例的核心上浮动。
我们还将在 Train 版本中弃用 reserved_host_cpus 配置选项。如果在 Train 版本中设置了 [compute] cpu_dedicated_set 或 [compute] cpu_shared_set 配置选项之一,则将忽略 reserved_host_cpus 配置选项的值,并且 VCPU 或 PCPU 清单将不会具有保留值,除非通过放置 API 显式设置。
如果未设置 [compute] cpu_dedicated_set 或 [compute] cpu_shared_set 选项,将记录一条警告,说明 reserved_host_cpus 已弃用,并且运维人员应设置 [compute] cpu_shared_set 和 [compute] cpu_dedicated_set 之一。
此功能将更改 [compute] cpu_shared_set 的含义,从用于模拟器线程的主机 CPU 列表更改为用于模拟器线程和 VCPU 资源的主机 CPU 列表。请注意,由于此选项已经存在,我们不能依赖其存在来执行诸如忽略 vcpu_pin_set 之类的操作,如前所述,而必须依赖 [compute] cpu_dedicated_set。出于同样的原因,只有在 vcpu_pin_set 未设置的情况下,我们才会使用 [compute] cpu_shared_set 来确定 VCPU 资源的数量。如果设置了 vcpu_pin_set,将记录一条警告,并且 vcpu_pin_set 将继续用于计算可用的 VCPU 资源,而 [compute] cpu_shared_set 将继续仅用于模拟器线程。
注意
可能已经存在具有设置 [compute] cpu_shared_set 但未设置 vcpu_pin_set 的主机。我们认为这种情况极不可能发生,并故意忽略这种组合。定义 [compute] cpu_shared_set 在 Stein 或更早版本中的唯一原因是为了使用模拟器线程卸载,用于隔离模拟器需要执行的额外工作与客户操作系统执行的工作。它主要用于实时用例。在未使用 vcpu_pin_set 的情况下使用 [compute] cpu_shared_set 可能会导致实例 vCPU 固定到任何主机核心,包括列在 cpu_shared_set 中的那些核心。这将破坏该功能的全部目的,并且不太可能由该功能的性能敏感用户配置,因此忽略该场景的原因。
最后,我们将更改 cpu_allocation_ratio 配置选项的文档,使其明确表明此选项仅适用于 VCPU 而不适用于 PCPU 资源
风味额外规格和镜像元数据属性¶
- 概要:
我们将尝试将旧版风味额外规格和镜像元数据属性重写为新的资源类型和特性,并在找不到匹配项时回退。
我们将别名旧版风味额外规格 hw:cpu_policy 和 hw:cpu_thread_policy 及其镜像元数据对应项 hw_cpu_policy 和 hw_cpu_thread_policy 到放置请求。
风味额外规格 hw:cpu_policy 和镜像元数据选项 hw_cpu_policy 将别名为 resources=(V|P)CPU:${flavor.vcpus}。对于使用 shared 策略的风味/镜像,调度程序会将此替换为 resources=VCPU:${flavor.vcpus} 额外规格,对于使用 dedicated 策略的风味/镜像,我们将替换为 resources=PCPU:${flavor.vcpus} 额外规格。请注意,这与我们当前将 Flavour.vcpus 转换为调度期间的 VCPU 资源放置请求的方式类似,但并不相同。
风味额外规格 hw:cpu_thread_policy 和镜像元数据选项 hw_cpu_thread_policy 将别名为 trait:HW_CPU_HYPERTHREADING。对于使用 isolate 策略的风味/镜像,我们将将其替换为 trait:HW_CPU_HYPERTHREADING=forbidden,对于使用 require 策略的风味/镜像,我们将替换为 trait:HW_CPU_HYPERTHREADING=required 额外规格。
如果匹配这些请求的放置库存请求失败,我们将恢复到旧行为并再次查询放置。第二次请求可能会返回已升级的主机,但一旦实例到达计算节点,驱动程序将拒绝这些请求。
放置库存¶
- 概要:
我们将自动重塑使用固定 CPU 的现有实例的库存,以使用
PCPU资源类而不是VCPU资源类。这将在设置[compute] cpu_dedicated_set配置选项后发生。
对于具有使用专用 CPU 的客户的现有计算节点,virt 驱动程序需要将现有 VCPU 资源(实际上正在使用专用主机 CPU)的库存移动到新的 PCPU 资源类。此外,这些计算节点上客户的现有分配记录需要从 VCPU 资源类更新为 PCPU 资源类。
此外,对于具有使用专用 CPU 并且使用 isolate CPU 线程策略的客户的现有计算节点,可能需要增加分配的 PCPU 资源数量,以考虑主机“保留”的额外 CPU。在启用超线程的 x86 主机上,这将导致保留 2 倍数量的 PCPU(N 个 PCPU 资源用于实例本身,以及 N 个 PCPU 分配以避免另一个实例使用它们)。这将被视为旧行为,并且不会为新实例支持。
总结¶
最终的升级过程将类似于标准的升级,但有一些细微的变化是必要的
升级控制器
分批更新计算节点
对于托管固定实例的计算节点
如果已设置,则取消设置
vcpu_pin_set并设置[compute] cpu_dedicated_set。如果未设置,则将[compute] cpu_dedicated_set设置为整个主机 CPU 范围。
对于托管未固定实例的计算节点
如果已设置,则取消设置
vcpu_pin_set并设置[compute] cpu_shared_set。如果未设置,则无需采取任何操作,除非如果已设置,则取消设置
reserved_host_cpus并设置[compute] cpu_shared_set为整个主机核心范围减去您希望保留的主机核心数量。
实现¶
负责人¶
主要负责人
stephenfin
tetsuro nakamura
jaypipes
cfriesen
bauzas
工作项¶
创建
PCPU资源类创建
[compute] cpu_dedicated_set和[compute] cpu_shared_set选项修改 virt 代码,使用上述新配置选项来计算将用于专用和共享 CPU 的主机 CPU 集合
修改从风味额外规格和镜像属性创建请求组的代码,以便在找到
hw:cpu_policy=dedicated规格时为PCPU资源构造请求(从旧版平稳过渡)修改当前查看
hw:cpu_thread_policy=isolate|share额外规格/镜像属性的代码,以将required=HW_CPU_HYPERTHREADING或required=!HW_CPU_HYPERTHREADING添加到放置请求修改 virt 代码,以重塑具有专用 CPU 的实例的资源分配,以使用
PCPU资源而不是VCPU资源
依赖项¶
无。
测试¶
需要对上述用例中列出的各种场景进行大量的功能测试。
文档影响¶
关于配置专用和共享 CPU 资源的管理员指南文档
关于解释共享和专用 CPU 资源差异的用户指南文档
关于运维人员如何配置单个主机以支持容忍线程兄弟作为专用 CPU 的客户以及不能容忍的客户的文档
参考资料¶
历史¶
发布名称 |
描述 |
|---|---|
Rocky |
最初提出,未被接受 |
Stein |
再次提出,未被接受 |
Train |
再次提出 |
Ussuri |
根据最终实现更新 |