AF_XDP TX 元数据¶
本文档描述了在使用 AF_XDP 传输数据包时如何启用卸载。 有关如何在接收端访问类似元数据的信息,请参阅 XDP RX 元数据。
总体设计¶
元数据的预留空间通过 tx_metadata_len
和 struct xdp_umem_reg
中的 XDP_UMEM_TX_METADATA_LEN
标志来完成。 因此,对于共享同一 umem 的每个套接字,元数据长度都是相同的。 元数据布局是固定的 UAPI,请参阅 include/uapi/linux/if_xdp.h
中的 union xsk_tx_metadata
。 因此,通常,上面的 tx_metadata_len
字段应包含 sizeof(union xsk_tx_metadata)
。
请注意,在原始实现中,不需要 XDP_UMEM_TX_METADATA_LEN
标志。 应用程序可能会尝试先使用标志创建一个 umem,如果失败,则尝试不带标志的另一个尝试。
预留空间和元数据本身应位于 umem 帧中的 xdp_desc->addr
之前。 在一个帧中,元数据布局如下
tx_metadata_len
/ \
+-----------------+---------+----------------------------+
| xsk_tx_metadata | padding | payload |
+-----------------+---------+----------------------------+
^
|
xdp_desc->addr
AF_XDP 应用程序可以请求大于 sizeof(struct xsk_tx_metadata)
的预留空间。 内核将忽略填充(并且仍将使用 xdp_desc->addr - tx_metadata_len
来定位 xsk_tx_metadata
)。 对于不应携带任何元数据的帧(即,没有 XDP_TX_METADATA
选项的帧),内核也会忽略元数据区域。
flags 字段启用特定的卸载
XDP_TXMD_FLAGS_TIMESTAMP
:请求设备将传输时间戳放入union xsk_tx_metadata
的tx_timestamp
字段中。XDP_TXMD_FLAGS_CHECKSUM
:请求设备计算 L4 校验和。csum_start
指定应开始校验和的字节偏移量,csum_offset
指定设备应存储计算出的校验和的字节偏移量。XDP_TXMD_FLAGS_LAUNCH_TIME
:请求设备在预定的时间(称为启动时间)安排数据包的传输。 启动时间的值由union xsk_tx_metadata
的launch_time
字段指示。
除了上述标志之外,为了触发卸载,第一个数据包的 struct xdp_desc
描述符应在 options
字段中设置 XDP_TX_METADATA
位。 另请注意,在多缓冲区数据包中,只有第一块应该携带元数据。
软件 TX 校验和¶
出于开发和测试目的,可以传递 XDP_UMEM_TX_SW_CSUM
标志到 XDP_UMEM_REG
UMEM 注册调用。 在这种情况下,当以 XDK_COPY
模式运行时,TX 校验和在 CPU 上计算。 不要在生产环境中启用此选项,因为它会 негативно 影响性能。
启动时间¶
所请求的启动时间的值应基于设备的 PTP 硬件时钟 (PHC) 以确保准确性。 AF_XDP 采用与 ETF 排队规则不同的数据路径,后者组织数据包并延迟其传输。 相反,AF_XDP 会立即将数据包传递给设备驱动程序,而不会重新排列它们的顺序或在传输之前保留它们。 由于驱动程序维护 FIFO 行为并且不执行数据包重新排序,因此具有启动时间请求的数据包将阻塞同一 Tx 队列中的其他数据包,直到它被发送。 因此,建议为计划用于未来传输的流量分配单独的队列。
在启动时间卸载功能被禁用的情况下,设备驱动程序应该忽略启动时间请求。 为了正确解释和有意义的操作,启动时间永远不应设置为大于未来最远可编程时间(视界)的值。 不同的设备对启动时间卸载功能有不同的硬件限制。
stmmac 驱动程序¶
对于 stmmac,TSO 和启动时间 (TBS) 功能对于每个单独的 Tx 队列是互斥的。 默认情况下,驱动程序配置 Tx 队列 0 以支持 TSO,其余 Tx 队列支持 TBS。 可以使用 tc-etf 命令调用驱动程序的 ndo_setup_tc() 回调来启用或禁用启动时间硬件卸载功能。
在增强型正常传输描述符中编程的启动时间的值是一个 32 位值,其中最高有效 8 位表示以秒为单位的时间,其余 24 位表示以 256 纳秒为单位的时间。 编程的启动时间与 PTP 时间(bits[39:8])进行比较,并在 256 秒后翻转。 因此,dwmac4 和 dwxlgmac2 的启动时间视界是未来的 128 秒。
igc 驱动程序¶
对于 igc,所有四个 Tx 队列都支持启动时间功能。 可以使用 tc-etf 命令调用驱动程序的 ndo_setup_tc() 回调来启用或禁用启动时间硬件卸载功能。 当进入 TSN 模式时,igc 驱动程序将重置设备并创建一个默认的 Qbv 计划,周期时间为 1 秒,所有 Tx 队列始终保持打开状态。
在高级传输上下文描述符中编程的启动时间的值是相对于队列的 Qbv 传输窗口的开始时间的相对偏移量。 可以设置描述符的 Frst 标志以安排数据包用于下一个 Qbv 周期。 因此,i225 和 i226 的启动时间视界是队列的 Qbv 传输窗口的下一个周期的结束时间。 例如,当 Qbv 周期时间设置为 1 秒时,启动时间的视界范围从 1 秒到 2 秒,具体取决于 Qbv 周期当前运行的位置。
查询设备功能¶
每个设备都通过 netlink netdev 系列导出其卸载功能。 请参阅 Documentation/netlink/specs/netdev.yaml
中的 xsk-flags
功能位掩码。
tx-timestamp
:设备支持XDP_TXMD_FLAGS_TIMESTAMP
tx-checksum
:设备支持XDP_TXMD_FLAGS_CHECKSUM
tx-launch-time-fifo
:设备支持XDP_TXMD_FLAGS_LAUNCH_TIME
有关如何查询此信息,请参阅 tools/net/ynl/samples/netdev.c
。
示例¶
有关处理 TX 元数据的示例程序,请参阅 tools/testing/selftests/bpf/xdp_hw_metadata.c
。 另请参阅 https://github.com/fomichev/xskgen 以获取更简单的示例。