FreeBSD设置网络轮询以提高性能

时间:2020-01-09 10:38:30  来源:igfitidea点击:

如何在FreeBSD操作系统下设置网卡(NIC)轮询并禁用中断以提高100M和1000M网络链接的网络性能?

设备轮询是一种技术,它允许操作系统定期轮询设备,而不是在需要注意时依靠设备来生成中断。
这样可以提高服务器网络的响应速度和性能。
特别是,轮询减少了服务中断时所发生的上下文切换的开销,并在各种任务(用户进程,软件中断,设备处理)之间提供了对CPU调度的更多控制权,从而最终减少了系统中发生活锁的机会。

"警告!"这些示例需要高速的LAN/WAN网络链接。
在繁重的工作量和大量的传入请求下,您肯定会注意到改进的地方。
当您的服务器受到DoS攻击时,这也有帮助。

确保您的卡支持网络轮询

设备轮询需要设备驱动程序中的支持。
在撰写本文时,FreeBSD 7.2仅支持以下NIC设备驱动程序:

驱动程序名称描述
bgeBroadcom BCM570x/5714/5721/5722/5750/5751/5752/5789 PCI千兆以太网适配器驱动程序
dcDEC/Intel 21143和克隆10/100以太网驱动程序
emIntel(R)PRO/1000千兆位以太网适配器驱动程序
fweFireWire的以太网仿真驱动程序
fwip基于FireWire的IP驱动程序
fxp英特尔EtherExpress PRO/100以太网设备驱动程序
ixgb用于FreeBSD操作系统的英特尔®PRO/10GbE以太网驱动程序
nfeNVIDIA nForce MCP以太网驱动程序
nge美国国家半导体PCI千兆以太网适配器驱动程序
reRealTek 8139C +/8169/816xS/811xS/8101E PCI/PCIe以太网适配器驱动程序
rlRealTek 8129/8139快速以太网设备驱动程序
sfAdaptec AIC-6915 Starfire PCI快速以太网适配器驱动程序
sisSiS 900,SiS 7016和NS DP83815/DP83816快速以太网设备驱动程序
steSundance Technologies ST201快速以太网设备驱动程序
stgeSundance/Tamarack TC9021千兆以太网适配器驱动程序
vgeVIA Networking Technologies VT6122 PCI千兆以太网适配器驱动程序
vrVIA Technologies莱茵I/II/III以太网设备驱动程序
xl3Com Etherlink XL和Fast Etherlink XL以太网设备驱动程序

请参考上面的手册页,以获取有关轮询和驱动程序加载设置设置的信息。

编译FreeBSD内核

要在驱动程序中启用轮询,请在内核配置中添加以下选项,然后重新编译内核。
缺省内核文件名是GENERIC,位于以下位置:

  • AMD 64(64位)内核位于/usr/src/sys/amd64/conf /
  • i386(32位)内核位于/usr/src/sys/i386/conf /

打开内核配置文件:

# cd /usr/src/sys/`uname -p`/conf
# vi GENERIC

为em驱动程序添加以下内容(有关设备特定的轮询设置,请参见上面的手册页)

options DEVICE_POLLING
        options HZ=1000

强烈建议将HZ = 1000或2000与DEVICE_POLLING一起使用,以实现更平滑的行为。
保存并关闭文件。
重新编译FreeBSD内核,执行:

# make buildkernel KERNCONF=GENERIC
# make installkernel KERNCONF=GENERIC

重新启动该框并启动到新内核:

# reboot

如何启用轮询?

在运行时,使用ifconfig命令打开轮询:

# ifconfig device polling
# ifconfig em0 polling

如何禁用轮询?

在运行时,使用ifconfig命令关闭轮询:

# ifconfig device -polling
# ifconfig em0 -polling

使配置持久化

如下更新/etc/rc.conf:

ifconfig_em0="inet 10.21.111.100 netmask 255.255.255.192 media 10baseT/UTP mediaopt full-duplex polling"

保存并关闭文件。

如何验证轮询设置?

要验证设置,请执行:

# ifconfig device
# ifconfig em0

要查看与轮询相关的MIB,请执行:

# sysctl -a kern.polling

输出示例:

kern.polling.idlepoll_sleeping: 1
kern.polling.stalled: 0
kern.polling.suspect: 0
kern.polling.phase: 4
kern.polling.enable: 0
kern.polling.handlers: 2
kern.polling.residual_burst: 0
kern.polling.pending_polls: 0
kern.polling.lost_polls: 0
kern.polling.short_ticks: 0
kern.polling.reg_frac: 20
kern.polling.user_frac: 50
kern.polling.idle_poll: 0
kern.polling.each_burst: 5
kern.polling.burst_max: 150
kern.polling.burst: 150

了解MIB变量

从手册页引用:

kern.polling.user_frac
	     When polling is enabled, and provided that there is some work to
	     do, up to this percent of the CPU cycles is reserved to userland
	     tasks, the remaining fraction being available for polling pro
	     cessing.  Default is 50.

     kern.polling.burst
	     Maximum number of packets grabbed from each network interface in
	     each timer tick.  This number is dynamically adjusted by the ker
	     nel, according to the programmed user_frac, burst_max, CPU speed,
	     and system load.

     kern.polling.each_burst
	     The burst above is split into smaller chunks of this number of
	     packets, going round-robin among all interfaces registered for
	     polling.  This prevents the case that a large burst from a single
	     interface can saturate the IP interrupt queue
	     (net.inet.ip.intr_queue_maxlen).  Default is 5.

     kern.polling.burst_max
	     Upper bound for kern.polling.burst.  Note that when polling is
	     enabled, each interface can receive at most (HZ * burst_max)
	     packets per second unless there are spare CPU cycles available
	     for polling in the idle loop.  This number should be tuned to
	     match the expected load (which can be quite high with GigE
	     cards).  Default is 150 which is adequate for 100Mbit network and
	     HZ=1000.

     kern.polling.idle_poll
	     Controls if polling is enabled in the idle loop.  There are no
	     reasons (other than power saving or bugs in the scheduler's han
	     dling of idle priority kernel threads) to disable this.

     kern.polling.reg_frac
	     Controls how often (every reg_frac / HZ seconds) the status reg
	     isters of the device are checked for error conditions and the
	     like.  Increasing this value reduces the load on the bus, but
	     also delays the error detection.  Default is 20.

     kern.polling.handlers
	     How many active devices have registered for polling.

     kern.polling.enable
	     Legacy MIB, that was used to enable or disable polling globally.
	     Currently if set to 1, polling is enabled on all capable inter
	     faces.  If set to 0, polling is disabled on all interfaces.

如何验证中断使用率是否下降?

在两个服务器上运行top命令,并在输出中查找中断行:

# top

如何测试网络吞吐量?

安装iperf,执行:

# portsnap fetch update
# cd /usr/ports/benchmarks/iperf
# make install clean && rehash

启用轮询后,请使用iperf工具测量通信链接或网络访问的最大数据吞吐率。
在服务器上启动iperf,如下所示:

# iperf -s -B 10.21.111.100

在客户端上,执行相同的命令,如下所示:

# iperf -c 10.21.111.100 -d -t 60 -i 10

其中:

  • -s:以服务器模式运行
  • -B:IP绑定到IP
  • -c IP:以客户端模式运行,连接到IP
  • -d:同时进行双向测试
  • -t 60:以60秒为单位的传输时间。
  • -i 10:在定期带宽报告之间暂停10秒。

测试结果

启用轮询后,当大量客户端在高负载下连接到服务器时,应该会看到良好的性能提升。
我通过10Mbits/sec城域以太网连接的两个WAN链接之间的测试结果:

测试轮询中断
数据传输8.87 Mbits /秒6.28 Mbits /秒
CPU负载34%73%

使用网络轮询时,当RX CPU负载下降时,您可以清楚地看到网络吞吐量的增加。