虚拟功能初始化序列

支持单根 I/O 虚拟化 (SR-IOV) 的网络适配器必须能够支持以下硬件组件:

  • 一个 PCI Express (PCIe) 物理功能 (PF) 。 PF 始终存在于网络适配器上,并附加到 Hyper-V 父分区。

    有关此硬件组件的详细信息,请参阅 SR-IOV 物理函数 (PF)

  • 一个或多个 PCIe 虚拟函数 (VF) 。 必须先初始化每个 VF 并将其附加到 Hyper-V 子分区,然后来宾操作系统的网络组件才能通过 VF 发送或接收数据包。

    有关此硬件组件的详细信息,请参阅 SR-IOV 虚拟函数 (VF)

在 Hyper-V 父分区的管理操作系统中运行的 PF 微型端口驱动程序初始化和分配 SR-IOV 网络适配器上的 VF 的资源。 在 NDIS 调用 PF 微型端口驱动程序的 MiniportInitializeEx 函数后,NDIS 和虚拟化堆栈可以向 PF 微型端口驱动程序发出对象标识符 (OID) 请求,以执行以下操作:

  • 在网络适配器上创建 NIC 交换机。 NIC 交换机在 VF、PF 和物理网络端口之间桥接网络流量。

    有关详细信息,请参阅 NIC 开关

    注意从Windows Server 2012开始,SR-IOV 接口仅支持网络适配器上的一个 NIC 交换机。 此开关称为 默认 NIC 开关,由NDIS_DEFAULT_SWITCH_ID标识符引用。

  • 请求 PF 微型端口驱动程序为网络适配器上的 VF 初始化和分配资源。

    有关详细信息,请参阅 SR-IOV 虚拟函数 (VF)

  • 在 NIC 交换机上 (VPort) 创建虚拟端口,并将其附加到 VF。

    有关详细信息,请参阅 VPorts) (虚拟端口

下图显示了 VF 初始化所涉及的步骤。

示例 vf 初始化序列,显示从虚拟化堆栈到 ndis,再到 pf 微型端口驱动程序的调用。

NDIS、虚拟化堆栈和 PF 微型端口驱动程序在 VF 初始化序列中遵循以下步骤:

  1. NDIS 从注册表读取默认交换机配置,并发出 OID_NIC_SWITCH_CREATE_SWITCH 的 OID 方法请求,以在网络适配器中预配交换机。 在此 OID 请求中传递的参数包括有关如何配置重要硬件资源(如 VF 和 VPort)的信息。 它还包括有关如何在附加到 PF 的非默认 VPort 和默认 VPort 之间分配资源的信息。

    PF 微型端口驱动程序成功完成 OID 后,NIC 交换机已准备好用于创建 VPort 并为其分配 VF。

    有关如何创建 NIC 交换机的详细信息,请参阅 创建 NIC 交换机

  2. VF 被视为虚拟机 (VM) 网络适配器的卸载机制。 此适配器在 Hyper-V 子分区中运行的来宾操作系统中公开。 默认情况下,来宾操作系统中的网络组件通过基于软件的合成数据路径发送和接收数据包。 但是,如果为 VF 卸载启用了子分区,则虚拟化堆栈会向 PF 微型端口驱动程序发出 OID 请求,以便进行 VF 的资源分配和初始化。 将 VF 附加到子分区和 NIC 交换机上的 VPort 后,网络组件通过 VF 数据路径发送和接收数据包。 有关这些数据路径的详细信息,请参阅 SR-IOV 数据路径

    如果为 VF 卸载启用了 Hyper-V 子分区,则虚拟化堆栈会向 PF 微型端口驱动程序发出 OID_NIC_SWITCH_ALLOCATE_VF 的 OID 方法请求。 在此 OID 请求中传递的参数包括分配 VF 的 NIC 交换机的标识符。 其他参数包括 VF 将附加到的子分区的标识符。

    PF 微型端口驱动程序为 VF 分配必要的硬件和软件资源。 PF 微型端口驱动程序还通过调用 NdisMGetVirtualFunctionLocation 来确定 VF 的 PCIe 请求者标识符 (RID) 。 当 VF 生成 DMA 请求和中断时,RID 用于 DMA 和中断重新映射。

    RID 和 VF 标识符在 PF 微型端口驱动程序成功完成 OID_NIC_SWITCH_ALLOCATE_VF 请求时返回。

    有关 VF 的资源分配的详细信息,请参阅 为虚拟函数分配资源

  3. 虚拟化堆栈通过向 PF 微型端口驱动程序发出 OID_NIC_SWITCH_CREATE_VPORT 的 OID 方法请求,在 NIC 交换机上创建 VPort。 在此 OID 请求中传递的参数包括要创建 VPort 的 NIC 交换机的标识符。 其他参数包括 VPort 将附加到的 VF 的标识符。

    注意 NIC 交换机上的默认 VPort 始终存在并附加到 PF。 只能创建一个非默认 VPort 并将其附加到 VF。

    在 NDIS 将 OID 请求转发到 PF 微型端口驱动程序之前,它会分配在网络适配器上唯一的有效 VPort 标识符。

    当 PF 微型端口驱动程序处理 OID 请求时,它会分配 VPort 所需的硬件资源,并保留 VPort 的标识符。 此标识符用于以后的 OID 请求和 SR-IOV 函数调用。

    有关如何创建 VPort 的详细信息,请参阅 创建虚拟端口

  4. Hyper-V 子分区可能在分配 VF 和 VPort 之前很久启动。 在此期间,来宾操作系统中的网络组件通过综合数据路径发送和接收数据包。 这涉及到通过附加到 PF 的默认 VPort 的数据包流量。 为了将流量桥接到子分区,虚拟化堆栈会为子分区的 VM 网络适配器配置媒体访问控制 (MAC) 和虚拟 LAN (VLAN) 筛选器。

    分配 VF 和 VPort 的资源后,虚拟化堆栈会向 PF 微型端口驱动程序发出 OID_RECEIVE_FILTER_MOVE_FILTER 的 OID 方法请求。 此 OID 请求将 VM 网络适配器的 MAC 和 VLAN 筛选器从默认 VPort 移动到附加到 VF 的 VPort。 这会导致匹配这些筛选器的数据包通过 VF 数据路径转发到 VF VPort。

    注意 可以使用 OID_RECEIVE_FILTER_MOVE_FILTER将现有接收筛选器从默认 VPort 移动到 VF VPort。 此外,可以使用 OID_RECEIVE_FILTER_SET_FILTER 在 VF VPort 上设置新筛选器。

成功创建 VF 和 VPort 并在 VPort 上设置 MAC 筛选器后,虚拟化堆栈会通知虚拟 PCI (VPCI) 虚拟服务提供商 (VSP) 。 此 VSP 在 Hyper-V 父分区的管理操作系统中运行。 通知通知 VPCI VSP 已成功分配并附加到子分区的 VF。 VPCI VSP 通过虚拟机总线 (VMBus) 将消息发送到在子分区的来宾操作系统中运行的 VSC (VSC) 的 VPCI 虚拟服务客户端。 VPCI VSC 是一个总线驱动程序,用于公开 VF 网络适配器的 PCI 设备。

VF 网络适配器公开后,在来宾操作系统中运行的 PnP 子系统将检测适配器并加载 VF 微型端口驱动程序。 此驱动程序注册到 NDIS。 初始化 VF 微型端口驱动程序并在 VF 网络适配器上配置相应的数据包筛选器后,VF 数据路径将完全正常运行。 因此,来宾操作系统中的数据包流量从综合数据路径切换到此数据路径。