searchusermenu
  • 发布文章
  • 消息中心
点赞
收藏
评论
分享
原创

【问题定位过程】mlnx网卡同步link状态导致ovs转发延迟

2023-10-13 08:12:13
386
0

分享一次mlnx网卡因同步link状态,导致openvswitch 转发延迟问题的定位过程

问题现象

海光cpu,Mellanox网卡环境,宿主机内虚机ping包(每秒1000个),偶现100ms以上延迟抖动。大约数分钟出现一次或连续数个。
 

ovs为dpdk模式,此环境正常转发延迟应该在1ms以下。

排查过程

ovs通过pmd-perf-log记录,看到ovs pmd线程上出现一次收包处理周期耗时长达100ms以上的记录。且出现时机与ping包发生大延迟重合。且ping包的延迟和ovs记录的周期时长也能匹配。

pmd一轮处理周期正常情况下只有几千个时钟周期。占用几十毫秒明显不合理。此轮周期时间消耗过长,会导致长时间不收取网卡或虚机队列中的报文,造成下一轮待处理报文产生延迟。符合问题现象。
根据抓取日志,我们定位到造成大延迟的流程均在ovs查找dp流表失败,通过upcall上送慢路径查询ofp流表之后。构造新dp流表完成前的代码区间。

范围在



之间,包括这两个函数。

然后我们通过systemtap跟踪此区间内函数执行时间并抓取异常长pmd周期发生时的函数执行时间,逐步缩小长耗时流程的范围。

通过反复缩小范围,最终定位到长耗时函数为bond_check_arp_copy_ability,此函数本身处理任务不耗时,但是为了获取锁等待了上百毫秒。

检查此锁的持有者,并通过systemtap记录起锁内和锁外的耗时,发现为bond_run占用该锁且锁内处理耗时异常长。进一步分析,发现为bond_run为刷新bond口状态而获取网卡link状态的netdev_get_carrier耗时长。继续向下调用为dpdk提供的mlx5网卡驱动。
rte_eth_link_get_nowait -> mlx5_link_update

通过分析代码,mlx5驱动获取网卡link状态的方法为向其内核态驱动发送ioctl请求,且使用了忙等方式反复尝试,并设置了10s的超时时间。由于此种通信方式本身耗时较长且ovs可能频繁调用,导致了bond_run在持有锁的区间产生较大耗时,从而造成pmd线程等锁形成长pmd处理周期。其他厂商的用户态网卡驱动是在用户态直接读寄存器获取link状态,所以没有这么大的时间开销)

回推复盘,发现每次触发upcall导致长pmd吹周期的报文都是dns请求,这种报文发送不频繁,所以通常dp流表都被老化了,所以会触发upcall。而如果其在upcall处理过程中恰好遇到mlx5_link_update出现长耗时,就会由于等锁的原因阻塞当前pmd处理。而恰好此pmd线程下一轮会处理ping包时,就引起了ping包的大延迟。

解决方法

分析代码,发现网卡可以通过配置为lsc模式(中断模式更新网卡状态,即其网卡内核驱动主动推送网卡状态变更,并存放在用户态内存中,用户态驱动获取网卡状态时直接读取该内存),极大的减少时间开销。 

ovs修改mlnx网卡为lsc模式

ovs-vsctl set interface $dpdkif options:dpdk-lsc-interrupt=true

修改后查看,问题宿主机内部ping包没有再频繁出现100ms以上的不定期时延抖动。

 

0条评论
0 / 1000
леон
2文章数
0粉丝数
леон
2 文章 | 0 粉丝
леон
2文章数
0粉丝数
леон
2 文章 | 0 粉丝
原创

【问题定位过程】mlnx网卡同步link状态导致ovs转发延迟

2023-10-13 08:12:13
386
0

分享一次mlnx网卡因同步link状态,导致openvswitch 转发延迟问题的定位过程

问题现象

海光cpu,Mellanox网卡环境,宿主机内虚机ping包(每秒1000个),偶现100ms以上延迟抖动。大约数分钟出现一次或连续数个。
 

ovs为dpdk模式,此环境正常转发延迟应该在1ms以下。

排查过程

ovs通过pmd-perf-log记录,看到ovs pmd线程上出现一次收包处理周期耗时长达100ms以上的记录。且出现时机与ping包发生大延迟重合。且ping包的延迟和ovs记录的周期时长也能匹配。

pmd一轮处理周期正常情况下只有几千个时钟周期。占用几十毫秒明显不合理。此轮周期时间消耗过长,会导致长时间不收取网卡或虚机队列中的报文,造成下一轮待处理报文产生延迟。符合问题现象。
根据抓取日志,我们定位到造成大延迟的流程均在ovs查找dp流表失败,通过upcall上送慢路径查询ofp流表之后。构造新dp流表完成前的代码区间。

范围在



之间,包括这两个函数。

然后我们通过systemtap跟踪此区间内函数执行时间并抓取异常长pmd周期发生时的函数执行时间,逐步缩小长耗时流程的范围。

通过反复缩小范围,最终定位到长耗时函数为bond_check_arp_copy_ability,此函数本身处理任务不耗时,但是为了获取锁等待了上百毫秒。

检查此锁的持有者,并通过systemtap记录起锁内和锁外的耗时,发现为bond_run占用该锁且锁内处理耗时异常长。进一步分析,发现为bond_run为刷新bond口状态而获取网卡link状态的netdev_get_carrier耗时长。继续向下调用为dpdk提供的mlx5网卡驱动。
rte_eth_link_get_nowait -> mlx5_link_update

通过分析代码,mlx5驱动获取网卡link状态的方法为向其内核态驱动发送ioctl请求,且使用了忙等方式反复尝试,并设置了10s的超时时间。由于此种通信方式本身耗时较长且ovs可能频繁调用,导致了bond_run在持有锁的区间产生较大耗时,从而造成pmd线程等锁形成长pmd处理周期。其他厂商的用户态网卡驱动是在用户态直接读寄存器获取link状态,所以没有这么大的时间开销)

回推复盘,发现每次触发upcall导致长pmd吹周期的报文都是dns请求,这种报文发送不频繁,所以通常dp流表都被老化了,所以会触发upcall。而如果其在upcall处理过程中恰好遇到mlx5_link_update出现长耗时,就会由于等锁的原因阻塞当前pmd处理。而恰好此pmd线程下一轮会处理ping包时,就引起了ping包的大延迟。

解决方法

分析代码,发现网卡可以通过配置为lsc模式(中断模式更新网卡状态,即其网卡内核驱动主动推送网卡状态变更,并存放在用户态内存中,用户态驱动获取网卡状态时直接读取该内存),极大的减少时间开销。 

ovs修改mlnx网卡为lsc模式

ovs-vsctl set interface $dpdkif options:dpdk-lsc-interrupt=true

修改后查看,问题宿主机内部ping包没有再频繁出现100ms以上的不定期时延抖动。

 

文章来自个人专栏
文章 | 订阅
0条评论
0 / 1000
请输入你的评论
0
0