解决FreeNAS under KVM使用Virtio网卡导致宿主机网卡Hang的问题

前言

没错,最近也在折腾,不过太晚了前言不写了,改天有时间补上(→_→)

环境

先说一下硬件以及软件环境

宿主机的网卡 Intel 82579LM

系统 Proxmox VE 5.4

症状

FreeNAS运行在KVM虚拟化创建的VM下面,Proxmox VE内设置的操作系统类型为Other,网卡设置为Virtio。

在使用FreeNAS的SMB服务时,通过任意一台局域网中的Windows 10系统复制共享文件夹中的文件时,宿主机会立即断网,并在message/dmesg提示类似以下的错误消息。

[ 5789.827518] e1000e 0000:00:19.0 eno1: Detected Hardware Unit Hang:
                 TDH                  <5d>
                 TDT                  <90>
                 next_to_use          <90>
                 next_to_clean        <5c>
               buffer_info[next_to_clean]:
                 time_stamp           <10014eaa6>
                 next_to_watch        <5d>
                 jiffies              <10014f100>
                 next_to_watch.status <0>
               MAC Status             <80083>
               PHY Status             <796d>
               PHY 1000BASE-T Status  <3800>
               PHY Extended Status    <3000>
               PCI Status             <10>
[ 5790.850700] e1000e 0000:00:19.0 eno1: Reset adapter unexpectedly
[ 5790.856800] vmbr0: port 1(eno1) entered disabled state
[ 5794.468588] e1000e: eno1 NIC Link is Up 1000 Mbps Full Duplex, Flow Control: Rx/Tx
[ 5794.468629] vmbr0: port 1(eno1) entered blocking state
[ 5794.468632] vmbr0: port 1(eno1) entered forwarding state
[ 5796.994932] e1000e 0000:00:19.0 eno1: Detected Hardware Unit Hang:
                 TDH                  <bc>
                 TDT                  <f1>
                 next_to_use          <f1>
                 next_to_clean        <bb>
               buffer_info[next_to_clean]:
                 time_stamp           <10014f683>
                 next_to_watch        <bc>
                 jiffies              <10014f800>
                 next_to_watch.status <0>
               MAC Status             <80083>
               PHY Status             <7ba8>
               PHY 1000BASE-T Status  <b6fc>
               PHY Extended Status    <ffff>
               PCI Status             <10>
[ 5798.883561] e1000e 0000:00:19.0 eno1: Detected Hardware Unit Hang:
                 TDH                  <bc>
                 TDT                  <f1>
                 next_to_use          <f1>
                 next_to_clean        <bb>
               buffer_info[next_to_clean]:
                 time_stamp           <10014f683>
                 next_to_watch        <bc>
                 jiffies              <10014f9d8>
                 next_to_watch.status <0>
               MAC Status             <80083>
               PHY Status             <796d>
               PHY 1000BASE-T Status  <3800>
               PHY Extended Status    <3000>
               PCI Status             <10>
[ 5800.867598] e1000e 0000:00:19.0 eno1: Detected Hardware Unit Hang:
                 TDH                  <bc>
                 TDT                  <f1>
                 next_to_use          <f1>
                 next_to_clean        <bb>
               buffer_info[next_to_clean]:
                 time_stamp           <10014f683>
                 next_to_watch        <bc>
                 jiffies              <10014fbc8>
                 next_to_watch.status <0>
               MAC Status             <80083>
               PHY Status             <796d>
               PHY 1000BASE-T Status  <3800>
               PHY Extended Status    <3000>
               PCI Status             <10>
[ 5802.883622] e1000e 0000:00:19.0 eno1: Detected Hardware Unit Hang:
                 TDH                  <bc>
                 TDT                  <f1>
                 next_to_use          <f1>
                 next_to_clean        <bb>
               buffer_info[next_to_clean]:
                 time_stamp           <10014f683>
                 next_to_watch        <bc>
                 jiffies              <10014fdc0>
                 next_to_watch.status <0>
               MAC Status             <80083>
               PHY Status             <796d>
               PHY 1000BASE-T Status  <3800>
               PHY Extended Status    <3000>
               PCI Status             <10>
[ 5804.867717] e1000e 0000:00:19.0 eno1: Detected Hardware Unit Hang:
                 TDH                  <bc>
                 TDT                  <f1>
                 next_to_use          <f1>
                 next_to_clean        <bb>
               buffer_info[next_to_clean]:
                 time_stamp           <10014f683>
                 next_to_watch        <bc>
                 jiffies              <10014ffb0>
                 next_to_watch.status <0>
               MAC Status             <80083>
               PHY Status             <796d>
               PHY 1000BASE-T Status  <3800>
               PHY Extended Status    <3000>
               PCI Status             <10>
[ 5804.930723] e1000e 0000:00:19.0 eno1: Reset adapter unexpectedly
[ 5804.944478] vmbr0: port 1(eno1) entered disabled state
[ 5812.216776] e1000e: eno1 NIC Link is Up 1000 Mbps Full Duplex, Flow Control: Rx/Tx
[ 5812.216829] vmbr0: port 1(eno1) entered blocking state
[ 5812.216835] vmbr0: port 1(eno1) entered forwarding state

其中最重要的就是eno1: Detected Hardware Unit Hang这一句,网卡Hang住了。

解决方案

在Google一番搜寻后,发现一般这种情况大家不是说要在BIOS中关闭C1E,就是要在内核中关闭pcie_aspm,或者是关闭宿主机网卡的checksum(offloading),还有要修改ringbuff(不知道是啥,命令是附在下面了)。

ethtool -G eth0 rx 256 tx 256

但是问题是好像之前也没出现过这种问题,Google到的都是不定时出现这种问题,但是Ovear这遇到的是只有在从FreeNAS这台VM的SMB中下载文件的时候才会出现,而且是100%出现,上传文件的时候也完全没问题。

方法一

想了想这个是网卡的问题,这台FreeBSD用的Virtio,会不会是这个问题,于是把FreeNAS的网卡改成e1000(vmxnet也行),然后一重启,果然没有问题了。但是接下来的问题来了,使用这个e1000网卡的时候,FreeBSD的CPU使用率异常的高(主要是interrupt和system),可以达到20%左右(8个核心,也就是160%)。

这就算了,速度还非常不稳定,最高只有800多Mbps,后续更是掉到了700Mbps左右,偶尔甚至会掉到400-500Mbps,VM延时也大增。这要是其他作用的VM还好,问题这可是NAS呀,这种性能怎么够看。

方法二

Ovear思前想后都觉得这个性能接受不了,但是Virtio又有这种问题,然后突然想到之前大家不是说要关闭宿主机网卡的checksum吗?但是这很明显宿主机没有问题,是虚拟机FreeBSD的驱动出现了问题,由于又是Virtio半虚拟化,进而影响到了宿主机,如果把VM的网卡offloading关闭,不是也许可以解决这个问题。

root@Ovear-Z420:~# ifconfig vtnet0 -rxcsum -txcsum -tso -lro

通过上面这个命令就可以临时禁用对应网卡的offloading,具体是关闭了什么offloading可以参考下FreeBSD的Manual。

rxcsum - RX Checksum Offloading
txcsum - TX Checksum Offloading
tso - TCP Segment Offloading
lso - Large Segment Offloading

在关闭Offloading之后,宿主机在SMB下载的时候网卡Hang的问题也就消失了,速度也恢复了之前的水平,(不过不知道是不是属于正常的Virtio水平了),稳定在900Mbps左右,此时服务器CPU占用率也才10%左右(interrupt 4-5% system 5%),比之前性能消耗少了一倍,吞吐率也稳定了很多。

同时在上下行同时进行测试的情况下,上下行都可以稳定在900Mbps,可以说是全双工1Gbps网卡的正常水准了,此时的服务器CPU占用率在20%左右(interrupt 6-7% system 10%)。

在这种情况下服务器要从硬盘中读取数据本身就需要CPU,其中system的10%应该大部分就是读取硬盘占用的了,而interrupt的6%应该就是网卡所占用的了。

暂时不清楚关闭offloading之后VM的网路性能到底有没有下降,今天懒得再改回去做对比了(:з」∠)

如果想要让FreeNAS自动禁止offloading的话,则需要在FreeNAS的Control Panel – Network -Interface中选择对应网卡,然后在Options中填入如下内容:

-rxcsum -txcsum -tso -lro

保存之后就可以让FreeNAS自动设置了。

疑问

不过目前的疑问还有很多,希望以后自己,或者路过的大佬们能够解答下

  • 当关闭offloading之后,SMB的下载功能恢复正常,但是此时如果在一台机器A中测试SMB下载后,再启动offloading,那么这台机器A下载SMB就会一直正常。但是如果换另外一台机器B来下载SMB的文件,则又会出现宿主机网卡Hang的问题。但是在这个时候如果再关闭offloading,则之前测试不行的机器B,SMB下载会恢复正常,然后再开启offloading,就会发现第一次正常的机器A又出现之前的让宿主机网卡Hang的问题了(但是也有AB两台机器同时正常的情况,具体忘了,可能是在关闭offloading的时候都下载过)。这里Ovear猜测是FreeBSD的某种缓存机制?
  • 必须要同时关闭rxcsum txcsum tso lro这四个,少一个都不行,但是问题只出现在下载,按理来说不应该关掉txcsum就可以了吗?
  • 为啥SMB下载的时候会触发这个问题,上传的时候却不会,是有什么Magic Packet吗?
  • 同样是Virtio网卡,同样是SMB的情况下,用Windows虚拟机做服务器,不管是上传还是下载都不会触发这个问题,而且性能也非常好,Windows默认不是启用了这些offloading的吗?但是Windows为什么会没问题,是FreeBSD对Virtio支持的驱动问题,还是Linux内核的KVM中Virtio驱动的问题,又或者是Linux的Intel e1000驱动模块的问题。
  • 宿主机断网的时候为什么会进入AMT的控制模式(TTL变成255),同时就算VM关闭了offloading,宿主机也会SMB下载(本来会断网和Hang)的时候,进入AMT模式(持续时间不定),但是只是ICMP的TTL变成255了,但是不管是VM还是宿主机的TCP功能都还是正常的。难道是Intel AMT的问题?
  • 宿主机网卡的状态中RX出现了errors和dropped,是网络问题吗?

尾巴

其实Ovear应该早点想到是FreeBSD对KVM Virtio兼容性的问题,看了Proxmox官方论坛的讨论才想起来,之前折腾pfSense(同样是BSD内核)的时候,pfSense特意强调了在vm下要关闭所有hardware offloading的事情,不然可能会导致性能非常差或者断网(没想到连宿主机都会一起断,而且关了之后性能也。。很感人)。对啦,Google到的一些可能有帮助,Ovear用到的网址就放在下面啦。

2019-07-02

PS:根据国外IDC Hetzner的提示,在宿主机上关闭tso和gso也可以解决这个问题,命令如下

ethtool -K <interface> tso off gso off

[1] https://pve.proxmox.com/wiki/PfSense_Guest_Notes

[2] https://forum.proxmox.com/threads/poor-virtio-network-performance-on-freebsd-guests.26289/

[3] https://www.freebsd.org/cgi/man.cgi?ifconfig

[4] https://superuser.com/questions/1270723/how-to-fix-eth0-detected-hardware-unit-hang-in-debian-9/1270796

[5] https://serverfault.com/questions/616485/e1000e-reset-adapter-unexpectedly-detected-hardware-unit-hang

[6] https://serverfault.com/questions/193114/linux-e1000e-intel-networking-driver-problems-galore-where-do-i-start

[7] https://blog.teatime.com.tw/1/post/414

[8] https://www.mail-archive.com/e1000-devel@lists.sourceforge.net/msg04618.html

[9] https://superuser.com/questions/959222/freebsd-turning-off-offloading

[10] https://wiki.hetzner.de/index.php/Low_performance_with_Intel_i218/i219_NIC/en

解决FreeNAS under KVM使用Virtio网卡导致宿主机网卡Hang的问题 没有评论

发表评论

电子邮件地址不会被公开。 必填项已用*标注