关于TCP收到数据粘包问题——Nagle算法

  • 在一个项目中,要在TCP连接的客户端和服务器之间发送json形式的数据。遇到了一个问题,有时候数据发送端连续多次调用send()函数发送多条json字符串时,接收端用recv()函数接收一条数据是一个组合多条json的大字符串,并不是期望的收到多条分割开的json字符串。这就是TCP的粘包问题。
  • 这就导致在使用cJSON_Parse()函数对json字符串进行解析时,只能解析出第一条完整的json,而后面的就丢弃了。这种情况对于每条json是一条命令来说,是很糟糕的。
  • 其实这种每条json是一个命令的业务需求,使用UDP来发送数据,就不会发生粘包问题。UDP是数据报传输协议,顾名思义其就是每次发送一个数据报,不会进行多条的封装拼凑再集体发送。

在socket网络程序中,TCP和UDP分别是面向连接和非面向连接的。因此TCP的socket编程,收发两端(客户端和服务器端)都要有成对的socket,因此,发送端为了将多个发往接收端的包,更有效的发到对方,使用了优化方法(Nagle算法),将多次间隔较小、数据量小的数据,合并成一个大的数据块,然后进行封包。这样,接收端,就难于分辨出来了,必须自己提供科学的拆包机制。

对于UDP,不会使用块的合并优化算法,这样,实际上目前认为,是由于UDP支持的是一对多的模式,所以接收端的skbuff(套接字缓冲区)采用了链式结构来记录每一个到达的UDP包,在每个UDP包中就有了消息头(消息来源地址,端口等信息),这样,对于接收端来说,就容易进行区分处理了。所以UDP不会出现粘包问题。
https://www.cnblogs.com/kex1n/p/6502002.html
TCP通信粘包问题分析和解决(全)
====================================================================

TCP的Nagle算法和延迟ACK

  • Nagle算法的操作过程请参看Wiki,它减少了大量小包的发送,实际上就是基于小包的停-等协议。在等待已经发出的包被确认之前,发送端利用这段时间可以积累应用下来的数据,使其大小趋向于增加。这是避免糊涂窗口综合症的一种有效方法,请注意,糊涂窗口指的是接收端的糊涂,而不是发送端的糊涂,接收端不管三七二十一得通告自己的接收窗口大小,丝毫不管这会在发送端产生大量小包。然而发送端可以不糊涂,你通告你的,我就是不发,你糊涂我不糊涂,你不断通告很小的数值,我不予理睬,我有自己的方法,直到收到已经发出包的ACK才会继续发送,这就是Nagle算法的糊涂抵制方案。
  • 治疗糊涂窗口综合症有两种方式,一种是“你糊涂我不糊涂”的方式,即上述的Nagle算法的方式,另外一种是“治疗接收端的糊涂”的方式,其中一种机制是延迟ACK(还有其它机制,比如不发送小窗口通告等)。可以看出,这两种方式中都在试图减少包的发送量,二者殊途同归的解决了同一问题,对于发送方而言,不理会接收端的小窗口通告等于说不马上发送小包,小包得以有时间积累成大包,对于接收方而言,延迟ACK可以拖延ACK发送时间,进而延迟窗口通告,在这段时间内,接收窗口有机会进一步(由于应用程序处理)放大。单独理解这两种方式都是简单的,但是一旦它们混在一起使用,情况就会非常不幸!因为...
  • Nagle算法和延迟ACK作用在方向相反的数据包和针对该数据包的确认包上,因此它们的作用力会相悖,结果就是谁也不能发包。就像一根绳子上拴两只青蛙一样,被对方牵制谁也跑不了!关键点在于,小包的发送依赖于ACK,然而延迟ACK阻止了ACK的即时发送,形成了僵持状态。本来只是为了减少网络上小包的数量(再次强调Nagle算法以及延迟ACK的目的,注意,糊涂窗口综合症只是网络上小包泛滥的原因之一!),却人为引入了大量的延迟!
  • 此处有一个通用的解释,Nagle算法的小包发送依赖于接收端对小包得快速确认,因此接收端对待ACK而言,应该朝着延迟ACK相反俄方向用力,即快速ACK;相对的,如果在接收端启用了延迟ACK,发送端就应该不断发送数据包,不管是大包还是小包(不考虑稍带ACK的影响),因为发送端已经不能指望接收端正常ACK数据包了,即发送端应该禁掉Nagle算法。以上解释背后的思想就是数据包和ACK包是相关的,力应该往一个方向使,一边拉另一边就要推,如果两边都拉,力就会抵消掉,陷入僵持。不幸点或者说悲哀的地方在于,Nagle算法和延迟ACK机制都是“拉方案”!划船的人都知道,划桨手有两种座位布局,要么超同一个方向,要么面朝不同的方向,后者和TCP数据包和ACK很类似,要想船往前走,必须朝一个方向划,虽然他们面朝相反的方向。

https://blog.csdn.net/dog250/article/details/21303679
再次谈谈TCP的Nagle算法与TCP_CORK选项

https://blog.csdn.net/wdscq1234/article/details/52432095
TCP-IP详解:Nagle算法

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 216,001评论 6 498
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,210评论 3 392
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 161,874评论 0 351
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,001评论 1 291
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,022评论 6 388
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,005评论 1 295
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,929评论 3 416
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,742评论 0 271
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,193评论 1 309
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,427评论 2 331
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,583评论 1 346
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,305评论 5 342
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,911评论 3 325
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,564评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,731评论 1 268
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,581评论 2 368
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,478评论 2 352

推荐阅读更多精彩内容

  • 1.这篇文章不是本人原创的,只是个人为了对这部分知识做一个整理和系统的输出而编辑成的,在此郑重地向本文所引用文章的...
    SOMCENT阅读 13,062评论 6 174
  • 个人认为,Goodboy1881先生的TCP /IP 协议详解学习博客系列博客是一部非常精彩的学习笔记,这虽然只是...
    贰零壹柒_fc10阅读 5,053评论 0 8
  • TCP/IP详解系列,关于tcp拥塞控制和数据流的地方讲的不细致,或许是涉及概念/算法太多,作者略去了一些对初学者...
    半岛夏天阅读 1,112评论 0 1
  • 套接字选项SO_RESUEADDR 即使端口处于2MSL状态,使用该选项,仍然能够在该端口建立连接。服务器常会设置...
    Myth52125阅读 1,407评论 0 0
  • 转自原文:TCP、UDP以及TCP滑窗,它们的区别注:文中提到TCP传输过程的特点,以及“粘包”的原因和解决方案,...
    半岛夏天阅读 3,482评论 2 31