启用TCP_NODELAY的Linux环回性能

我最近偶然发现了一个有趣的TCP性能问题,同时运行了一些比较networking性能和环回性能的性能testing。 在我的情况下,networking性能超过了环回性能(1Gignetworking,相同的子网)。 在这种情况下,我处理延迟是至关重要的,所以TCP_NODELAY已启用。 我们提出的最好理论是TCP拥塞控制正在维持数据包。 我们做了一些数据包分析,可以肯定的看到数据包正在被占用,但是原因并不明显。 现在的问题…

1)在什么情况下,以及为什么通过回送进行通信比通过networking慢?

2)尽可能快地发送时,为什么切换TCP_NODELAY对环回的最大吞吐量有比networking更多的影响?

3)如何检测和分析TCP拥塞控制作为对性能差的一个潜在的解释?

4)有没有人有这个现象的理由? 如果是的话,任何方法来certificate这个理论?

这里是一些简单的点到点的c + +应用程序生成的示例数据:

传输消息大小(字节)TCP NoDelay发送缓冲区(字节)发送方主机接收方主机吞吐量(字节/秒)消息速率(msgs / sec)
 TCP 128 On 16777216 HostA HostB 118085994 922546
 TCP 128closures16777216 HostA HostB 118072006 922437
 TCP 128在4096 HostA HostB 11097417 86698
 TCP 128closures4096 HostA主机B 62441935 487827
 TCP 128 On 16777216 HostA HostA 20606417 160987
 TCP 128closures16777216 HostA HostA 239580949 1871726
 TCP 128在4096 HostA HostA 18053364 141041
 TCP 128closures4096 HostA主机A 214148304 1673033
 UnixStream 128  -  16777216 HostA HostA 89215454 696995
 UnixDatagram 128  -  16777216 HostA HostA 41275468 322464
 NamedPipe 128  -   -  HostA HostA 73488749 574130

以下是一些有用的信息:

  • 我只看到这个小问题的消息
  • HostA和HostB都具有相同的硬件套件(Xeon X5550@2.67GHz,总共32个内核/ 128 Gig Mem / 1Gig Nics)
  • OS是RHEL 5.4内核2.6.18-164.2.1.el5)

谢谢

Solutions Collecting From Web of "启用TCP_NODELAY的Linux环回性能"

1) 在什么情况下,为什么通过回送进行通信比通过网络慢?

Loopback将tx + rx的数据包设置+ tcp chksum计算放在同一台计算机上,所以它需要做2倍的处理,而2台计算机则在它们之间分配tx / rx。 这可能会对环回产生负面影响。

2) 尽可能快地发送时,为什么切换 TCP_NODELAY 对环回的最大吞吐量有比网络更多的影响?

不知道你是如何得出这个结论的,但是loopback vs network是非常不同的,如果你试图将它们推到极限,你会遇到不同的问题。 Loopback接口(如答案1中所述)会在同一台机器上导致tx + rx处理开销。 另一方面,网卡在循环缓冲区中可以有多少未完成的数据包有一定的限制,这将导致完全不同的瓶颈(这种情况在不同芯片之间也有很大差别,甚至在两者之间他们)

3) 如何检测和分析TCP拥塞控制作为对性能差的一个潜在的解释?

拥塞控制只有在丢包的情况下才会起作用。 你看到包丢失? 否则,你可能在tcp窗口大小vs网络延迟因素上达到极限。

4) 有没有人有这个现象的理由? 如果是的话,任何方法来证明这个理论?

我不明白你在这里提到的现象。 我在桌面上看到的是,你有一些带有大发送缓冲区的套接字 – 这可能是完全合法的。 在一台快速的机器上,你的应用程序肯定能够产生比网络可以抽出更多的数据,所以我不确定你在这里把什么归类为一个问题。

最后一个注意事项:由于各种原因,小消息会在您的网络上创建更大的性能,例如:

  • 每个数据包的开销都是固定的(对于mac + ip + tcp头文件),有效载荷越小,开销就越大。
  • 许多网卡的限制是相对于未完成数据包的数量而言的,这意味着在使用较小的数据包时,数据量会减少很多。
  • 网络本身就是每个数据包的开销,所以您可以通过网络抽取的最大数据量取决于数据包的大小。

1或2)我不知道为什么你打扰使用环回,我个人不知道它将如何模仿一个真实的接口,它将是多么有效。 我知道微软禁用NAGLE的回环接口(如果你在意)。 看看这个链接 ,这里有一个讨论。

3)我会密切关注在这两种情况下的前几个数据包,看看你是否得到了前五个数据包的严重延迟。 看到这里

这也是我面临的同样的问题。 在同一台RHEL6计算机上运行的两个组件之间传输2 MB数据时,需要7秒钟才能完成。 数据量大的时候是不可接受的。 花了1分钟来传输10 MB的数据。

然后,我尝试禁用TCP_NODELAY 。 它解决了这个问题

这两个组件在两台不同的机器上时不会发生这种情况。