Nagle 算法尽量减少小分组出现在网络上,而 TCP_CORK 是完全避免小分组出现在网络上。该选项是在 Linux 2.2 才引入的。
cork 这个单词,意为“塞子”,我们把 TCP 发送缓冲区想象成一个水池,而 cork 的作用就是把这个水池的出口堵住,直到下面的事情发生才会拔掉塞子,发送数据:
- 水池满了
 - 达到一定的大小,比如超过 MSS 了
 - 一段时间都没有水进来(比如 200ms)
 - 遇到 FIN 了
 - 会不会还有其它情况?
 
1. 程序路径
如果你已经 clone 过这个代码了,请使用 git pull 更新一下。本节程序所使用的程序路径是 unp/program/options/opt。
2. 实验
实验中我们设置 TCP_CORK 选项,然后发送小分组,观察 tcpdump 的输出。
- flower 上启动服务器
 
$ ./opt -s -h flower --slowread 4096
- sun 上启动客户端,打开 TCP_CORK 选项
 
// 打开 TCP_CORD,一次 write 1 字节
$ ./opt -h flower --cork --writesize 1
 
 

 图1 开启 TCP_CORK 选项,完全避免发送小分组 
 
我们看到 11 字节数据被发送出去,是因为超时,尽管 11 字节的分组仍然是小分组。
为了方便你对照它与 Nagle 的区别,我把上一篇文章的结果拿来进行对比。如图 2.
 
 

 图2 开启 Nagle 算法 
 
3. TCP_CORK 与 TCP_NODELAY
这两个选项完全是相反的作用,所以使用的时候,二者不能同时开启。但是从 Linux 2.5.71 内核开始,却可以同时打开这两个选项……想看结果吗?见图 3.
 
 

 图3 同时打开 TCP_CORK 与 TCP_NODELAY 
 
结果显示的是按照 TCP_CORK 算法来的。。。
man 手册推荐:如果你的代码要求可移植,就不应该使用 TCP_CORK 选项。
4. 总结
- 掌握 TCP_CORK 选项的作用
 - 知道 TCP_NODELAY、TCP_CORK 的区别
 - 知道 cork 与 nagle 的区别
 
                










