dpdk - 正确的 DPDK 设备和端口初始化以进行传输
问题描述
在编写一个简单的 DPDK 数据包生成器时,我注意到可靠和成功的数据包传输所需的一些额外的初始化步骤:
- 打电话
rte_eth_link_get()
或rte_eth_timesync_enable()
之后rte_eth_dev_start()
- 在发送第一个数据包之前等待 2 秒
rte_eth_tx_burst()
因此,当我将 ixgbe DPDK vfio 驱动程序与 Intel X553 NIC 一起使用时,这些步骤是必要的。
当我使用AF_PACKET
DPDK 驱动程序时,它无需那些额外的步骤即可工作。
- 这是错误还是功能?
- 有没有比在第一次发送前等待 2 秒更好的方法?
- 为什么 ixgbe 驱动程序需要等待?这是该 NIC 或相关交换机(带有 Marvell 芯片组的 Mikrotik CRS326)的限制吗?
- 是否有比
rte_eth_link_get()
为了完成传输的设备初始化更惯用的函数来调用? - 是否有某种方法可以保持 VFIO NIC 初始化(同时保持其链接正常)以避免在通常的编辑/编译/测试周期中一遍又一遍地重新初始化它?(即加快那个周期......)
附加信息:当我将 NIC 连接到镜像端口(通过 Mikrotik 的 mirror-source/mirror-target 以太网交换机设置配置)并被删除时,sleep(2)
我看到第一个数据包传输到镜像目标但没有传输到主要目标. 因此,似乎有必要在链接启动后(在 dpdk 程序启动后)给开关一些时间以完全初始化其转发表或类似的东西?
在第一次传输之前仅等待 1 秒的可靠性较低,即数据包仅每隔奇数时间到达接收器。
我的设备/端口初始化过程实现了以下设置序列:
rte_eth_dev_count_avail()
rte_eth_dev_is_valid_port()
rte_eth_dev_info_get()
rte_eth_dev_adjust_nb_rx_tx_desc()
rte_eth_dev_configure(port_id, 0 /* rxrings */, 1 /* txrings */, &port_conf)
rte_eth_tx_queue_setup()
rte_eth_dev_start()
rte_eth_macaddr_get()
rte_eth_link_get() // <-- REQUIRED!
rte_eth_dev_get_mtu()
如果没有rte_eth_link_get()
(或rte_eth_timesync_enable()
),第一个传输的数据包甚至不会出现在镜像端口上。
上述功能(和rte_eth_tx_burst()
)在有/没有rte_eth_link_get()
/sleep(2)
存在的情况下成功完成。尤其是读取的 MAC 地址,MTU 具有预期值(MTU -> 1500)并rte_eth_tx_burst()
返回1
一个 UDP 数据包的突发。
返回的链接状态为:Link up at 1 Gbps FDX Autoneg
rte_eth_link_get()
可以用可能替换的事实可以rte_eth_timesync_enable()
通过后一个调用来解释,后者调用ixgbe_start_timecounters()
也rte_eth_linkstatus_get()
被调用rte_eth_link_get()
。
我检查了 DPDK 示例,其中大多数rte_eth_link_get()
在发送内容之前都不会调用。设备初始化后也没有睡眠。
我正在使用 DPDK 20.11.2。
更多信息- 回答评论:
我在 Fedora 33 ( 5.13.12-100.fc33.x86_64
) 上运行它。
Ethtool 报告:firmware-version: 0x80000877
我打电话rte_eth_timesync_enable()
是为了处理传输时间戳。但是,在调试过程中,我将其删除以达到最小的复制器。那时我注意到删除它实际上会使情况变得更糟(即没有数据包通过镜像端口传输)。因此,我调查了该功能的哪一部分可能会产生影响,并发现rte_eth_link_get()
哪一部分具有相似的副作用。
当切换到AF_PACKET
我使用股票 ixgbe 内核驱动程序时,即ixgbe
在由 networkd 初始化的设备上使用默认设置(启用 dhcp)。
我的期望是,当rte_eth_dev_start()
终止时链接已启动并且设备已准备好传输。
但是,我想,如果可以避免在程序重新启动后重置设备,那就太好了。我不知道 DPDK 是否支持这个。
关于延迟:我刚刚测试了以下内容:rte_eth_link_get()
如果我将睡眠时间增加到 6 秒,则可以省略。而调用rte_eth_link_get()
需要 3.3 秒。所以,是的,由于额外的延迟,它可能只是有帮助。
解决方案
两种尝试方法之间的区别
为了使用af_packet
PMD,您首先将相关设备绑定到内核驱动程序。此时,将为该设备生成一个内核网络接口。默认情况下,此接口通常具有活动链接。如果没有,您通常运行ip link set dev <interface> up
. 当您启动 DPDK 应用程序时,af_packet
驱动程序不会(重新)配置链接。它只是无条件地报告链接在设备启动时启动(请参阅https://github.com/DPDK/dpdk/blob/main/drivers/net/af_packet/rte_eth_af_packet.c#L266),反之亦然。此驱动程序中的链接更新操作也是无操作的(请参阅https://github.com/DPDK/dpdk/blob/main/drivers/net/af_packet/rte_eth_af_packet.c#L416)。
事实上,通过af_packet
方法,该链接在您启动应用程序时已经处于活动状态。因此无需等待链接。
使用 VFIO 方法时,相关设备的链路断开,相应的 PMD 负责激活它。因此需要在应用程序中测试链接状态。
是否可以避免等待应用程序重新启动?
长话短说,是的。等待链接状态并不是应用程序重启的唯一问题。当您重新启动时,您有效地重新初始化了整个 EAL,而且该过程也非常耗时。为了解决这个问题,您可能应该查看DPDK 中提供的多进程支持(请参阅https://doc.dpdk.org/guides/prog_guide/multi_proc_support.html)。
这要求您重新实现您的应用程序,使其控制逻辑在一个进程(也是主要进程)中,而 Rx/Tx 数据路径逻辑在另一个进程(次要进程)中。这样,您可以一直保持第一个运行,并在需要更改 Rx/Tx 逻辑/重新编译时重新启动第二个。重新启动辅助进程将始终重新附加到现有的 EAL 实例。因此不涉及 PMD 重启,也无需等待。
推荐阅读
- javascript - process.env 变量未定义 React App - 不使用 create-react-app
- c# - 在xamarin中通过陀螺仪移动缩放图像
- systemc - 如何修复 Access Noxim 安装错误
- c# - 使用 C# 播放音乐?
- css - Material UI-makeStyles 我的样式不起作用
- javascript - Jasmine 测试错误:预期 Spy XYZ 已被调用
- opengl - OpenGL中glBindBufferBase()中的索引和几何着色器中的流号有什么关系?
- python - 如何在python中实现#ifdef,专门用于检查testrunner
- ios - 无效的可执行文件 - 可执行的 ProjectName WatchKit Extension' 不包含位码
- javascript - 每当我在反应中运行“npm start”时我得到错误:找不到模块'autoprefixer'