介紹
TCP網(wǎng)絡(luò)傳輸層協(xié)議积糯,當(dāng)經(jīng)過三次握手以后掂墓,TCP點(diǎn)到點(diǎn)建立一條套節(jié)字通道,由于網(wǎng)絡(luò)的復(fù)雜性看成,導(dǎo)致數(shù)據(jù)可能會(huì)分N個(gè)報(bào)文進(jìn)行傳送君编。在服務(wù)端可能一次或多次才能接收完成,系統(tǒng)本身也是緩存一定大小數(shù)據(jù)進(jìn)行傳送川慌,保證傳輸?shù)男阅茏畲蠡院佟6瑯邮莻鬏攲訁f(xié)議UDP則不會(huì)有這樣的問題偿荷,UDP是基于報(bào)文發(fā)送的,從UDP的幀結(jié)構(gòu)可以看出唠椭,在UDP首部采用了16bit來指示UDP數(shù)據(jù)報(bào)文的長度跳纳,因此在應(yīng)用層能很好的將不同的數(shù)據(jù)報(bào)文區(qū)分開,從而避免粘包和拆包的問題贪嫂。而TCP基于字節(jié)流傳輸寺庄,雖然應(yīng)用層和TCP傳輸層之間的數(shù)據(jù)交互是大小不等的數(shù)據(jù)塊,但TCP把這些數(shù)據(jù)塊僅僅看成一連串的無結(jié)構(gòu)的字節(jié)流力崇,無邊界斗塘。從TCP幀結(jié)構(gòu)看出,TCP報(bào)文頭部沒有表示數(shù)據(jù)長度的字段亮靴。
現(xiàn)象的描述
- 拆包 接收端收到了兩個(gè)數(shù)據(jù)包馍盟,但是這兩個(gè)數(shù)據(jù)包要么是不完整的,要么就是多出來一塊茧吊,這種情況即發(fā)生了拆包和粘包贞岭。
- 粘包 同樣在接收的時(shí)候有多個(gè)數(shù)據(jù)包。
發(fā)生的原因
- 發(fā)送數(shù)據(jù)報(bào)文大于TCP緩沖區(qū)的大小搓侄。
- 發(fā)送數(shù)據(jù)小于TCP緩沖區(qū)的大小瞄桨。
- 接收方?jīng)]有及時(shí)讀取緩沖區(qū)的數(shù)據(jù)。
問題的解決方案
- 報(bào)文首部采用16bit指定長度讶踪。
- 數(shù)據(jù)包定長(不足0補(bǔ)充)芯侥。
- 分隔符。
現(xiàn)有框架
- netty封裝tcp拆包乳讥、粘包問題柱查,具體可參考netty相關(guān)實(shí)現(xiàn)。