这两天看csdn有一些关于socket粘包,socket缓冲区设置的问题。发现自己不是非常清楚,所以查资料了解记录一下:

一两个简单概念长连接与短连接:
1.长连接

Client方与Server方先建立通讯连接。连接建立后不断开。 然后再进行报文发送和接收。

2.短连接

Client方与Server每进行一次报文收发交易时才进行通讯连接,交易完成后马上断开连接。此种方式经常使用于一点对多点
通讯。比方多个Client连接一个Server.

二 什么时候须要考虑粘包问题?

1:假设利用tcp每次发送数据,就与对方建立连接,然后两方发送完一段数据后,就关闭连接,这样就不会出现粘包问题(由于仅仅有一种包结构,类似于http协议)。

关闭连接主要要两方都发送close连接(參考tcp关闭协议)。如:A须要发送一段字符串给B。那么A与B建立连接,然后发送两方都默认好的协议字符如"hello give me sth abour yourself",然后B收到报文后,就将缓冲区数据接收,然后关闭连接,这样粘包问题不用考虑到,由于大家都知道是发送一段字符。
2:假设发送数据无结构,如文件传输,这样发送方仅仅管发送,接收方仅仅管接收存储就ok。也不用考虑粘包
3:假设两方建立连接,须要在连接后一段时间内发送不同结构数据,如连接后,有好几种结构:
 1)"hello give me sth abour yourself"
 2)"Don't give me sth abour yourself"
   那这种话,假设发送方连续发送这个两个包出去,接收方一次接收可能会是"hello give me sth abour yourselfDon't give me sth abour yourself" 这样接收方就傻了,究竟是要干嘛?不知道,由于协议没有规定这么诡异的字符串,所以要处理把它分包,怎么分也须要两方组织一个比較好的包结构,所以一般可能会在头加一个数据长度之类的包,以确保接收。

三 粘包出现原因:在流传输中出现。UDP不会出现粘包。由于它有消息边界(參考Windows 网络编程)
1 发送端须要等缓冲区满才发送出去,造成粘包
2 接收方不及时接收缓冲区的包。造成多个包接收

解决的方法:
为了避免粘包现象,可採取下面几种措施。

一是对于发送方引起的粘包现象。用户可通过编程设置来避免,TCP提供了强制数据马上传送的操作指令push,TCP软件收到该操作指令后。就马上将本段数据发送出去,而不必等待发送缓冲区满;二是对于接收方引起的粘包,则可通过优化程序设计、精简接收进程工作量、提高接收进程优先级等措施,使其及时接收数据,从而尽量避免出现粘包现象。三是由接收方控制,将一包数据按结构字段,人为控制分多次接收,然后合并,通过这样的手段来避免粘包。

以上提到的三种措施。都有其不足之处。第一种编程设置方法尽管能够避免发送方引起的粘包,但它关闭了优化算法,降低了网络发送效率,影响应用程序的性能,一般不建议使用。另外一种方法仅仅能降低出现粘包的可能性,但并不能全然避免粘包,当发送频率较高时,或因为网络突发可能使某个时间段数据包到达接收方较快,接收方还是有可能来不及接收。从而导致粘包。

第三种方法尽管避免了粘包,但应用程序的效率较低,对实时应用的场合不适合。

相关文章截取:

一个包没有固定长度,以太网限制在46-1500字节,1500就是以太网的MTU,超过这个量,TCP会为IP数据报设置偏移量进行分片传输,如今一般可同意应用层设置8k(NTFS系)的缓冲区,8k的数据由底层分片,而应用看来仅仅是一次发送。windows的缓冲区经验值是4k,Socket本身分为两种。流(TCP)和数据报(UDP),你的问题针对这两种不同使用而结论不一

样。甚至还和你是用堵塞、还是非堵塞Socket来编程有关。

1、通信长度,这个是你自己决定的,没有系统强迫你要发多大的包,实际应该依据需求和网络状况来决定。对于TCP,这个长度能够大点。但要知道,Socket内部默认的收发缓冲区大小大概是8K,你能够用SetSockOpt来改变。但对于UDP,就不要太大。一般在1024至10K。注意一点。你不管发多大的包,IP层和链路层都会把你的包进行分片发送。一般局域网就是1500左右,广域网就仅仅有几十字节。分片后的包将经过不同的路由到达接收方。对于UDP而言。要是当中一个分片丢失,那么接收方的IP层将把整个发送包丢弃,这就形成丢包。显然,要是一个UDP发包佷大。它被分片后,链路层丢失分片的几率就佷大。你这个UDP包。就佷easy丢失,可是太小又影响效率。最好能够配置这个值,以依据不同的环境来调整到最佳状态。

send()函数返回了实际发送的长度,在网络不断的情况下,它绝不会返回(发送失败的)错误,最多就是返回0。

对于TCP你能够字节写一个循环发送。

当send函数返回SOCKET_ERROR时,才标志着有错误。但对于UDP,你不要写循环发送。否则将给你的接收带来极大的麻烦。所以UDP须要用SetSockOpt来改变Socket内部Buffer的大小,以能容纳你的发包。

明白一点,TCP作为流,发包是不会整包到达的,而是源源不断的到。那接收方就必须组包。而UDP作为消息或数据报,它一定是整包到达接收方。

2、关于接收,一般的发包都有包边界,首要的就是你这个包的长度要让接收方知道,于是就有个包头信息,对于TCP,接收方先收这个包头信息。然后再收包数据。

一次收齐整个包也能够,可要对结果是否收齐进行验证。这也就完毕了组包过程。UDP,那你仅仅能整包接收了。要是你提供的接收Buffer过小。TCP将返回实际接收的长度,余下的还能够收,而UDP不同的是。余下的数据被丢弃并返回WSAEMSGSIZE错误。注意TCP。要是你提供的Buffer佷大,那么可能收到的就是多个发包。你必须分离它们。还有就是当Buffer太小,而一次收不完Socket内部的数据,那么Socket接收事件(OnReceive),可能不会再触发,使用事件方式进行接收时,密切注意这点。

这些特性就是体现了流和数据包的差别。

相关參考文章:
http://www.cnblogs.com/alon/archive/2009/04/16/1437600.html

TCP Socket 粘包相关推荐

  1. golang中tcp socket粘包问题和处理

    http://www.01happy.com/golang-tcp-socket-adhere/ 在用golang开发人工客服系统的时候碰到了粘包问题,那么什么是粘包呢?例如我们和客户端约定数据交互格 ...

  2. Go语言中Tcp协议粘包问题处理

    在用golang开发人工客服系统的时候碰到了粘包问题,那么什么是粘包呢?例如我们和客户端约定数据交互格式是一个json格式的字符串: {"Id":1,"Name" ...

  3. socket Php 粘包,python3 tcp的粘包现象和解决办法解析

    这篇文章主要介绍了python3 tcp的粘包现象和解决办法解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下 服务器端 import socket ...

  4. Socket粘包问题

    这两天看csdn有一些关于socket粘包,socket缓冲区设置的问题,发现自己不是很清楚,所以查资料了解记录一下: 一两个简单概念长连接与短连接: 1.长连接 Client方与Server方先建立 ...

  5. TCP通信粘包问题分析和解决

    在socket网络程序中,TCP和UDP分别是面向连接和非面向连接的.因此TCP的socket编程,收发两端(客户端和服务器端)都要有成对的socket,因此,发送端为了将多个发往接收端的包,更有效的 ...

  6. TCp传输粘包问题

    解决TCP网络传输"粘包"问题   当前在网络传输应用中,广泛采用的是TCP/IP通信协议及其标准的socket应用开发编程接口(API).TCP/IP传输层有两个并列的协 议:T ...

  7. Socket粘包问题终极解决方案—Netty版(2W字)!

    作者 | 王磊 来源 | Java中文社群(ID:javacn666) 转载请联系授权(微信ID:GG_Stone) 上一篇我们写了<Socket粘包问题的3种解决方案>,但没想到评论区竟 ...

  8. Netty解决TCP的粘包和分包(二)

    2019独角兽企业重金招聘Python工程师标准>>> Netty解决TCP的粘包和分包(二) 使用LengthFieldBasedFrameDecoder解码器分包 先看一下这个类 ...

  9. (Java)socket网络编程及处理socket粘包拆包问题

    目录 1.socket简介 2.TCP/IP协议 3.tcp三次握手 4.socket的一些接口函数原理 5.java socket 长连接粘包拆包问题 6.socket模拟服务端客户端发消息 7.U ...

最新文章

  1. 新版微信小程序即将上线 新增微信支付功能
  2. 数据库读写分离 - MyBatis
  3. mysql“Access denied for user 'root'@'localhost'”问题的解决
  4. python密码传参有特殊字符如何解决_Python为什么我在RSA加密中有特殊字符
  5. oracle 创建用户
  6. 吴恩达教授机器学习课程笔记【七】- Part 7 最优模型选择
  7. 循序渐进的手动安装k8s笔记-1
  8. 颜色的原理,三基色原理以及HLS(色相、亮度、饱和度)原理
  9. 运用人类「从众心理」!掌握简单心理学成为说服高手
  10. amd r7 2700u linux,锐龙r72700u相当于 r72700u相当于什么水平?
  11. ReadyState的五种状态详解
  12. 快递100接口使用整理
  13. 怎么卸载光速头条_教你怎么卸载光速浏览器
  14. html长图转换成pdf,iOS将HTML页面转换成PDF文件保存到本地并分享传输文件
  15. 树莓派WEB服务器(Boa)CGI编程入门
  16. namenode元数据多目录配置及测试
  17. 5 Hibernate:Java Persistence API (JPA) 入门
  18. 三个维度看全球半导体格局变迁
  19. Linux yum命令
  20. 细细品味Flex——BlazeDS开发指南

热门文章

  1. linux为什么要禁止内核抢占,为什么linux在内核代码持有自旋锁后禁用内核抢占?...
  2. python中的event_Python event
  3. 对外经贸大学计算机应用基础,对外经贸大学计算机应用基础试题.doc
  4. 安全策略_Spring Security 实战干货:如何实现不同的接口不同的安全策略
  5. java 线程由浅入深_由浅入深,Java 并发编程中的 Synchronized(一)
  6. doxygen生成html文件,doxygen 的安装、配置、编译及使用(从源代码到文档)
  7. arduino tft 方向_ESP32在Arduino环境下玩转 LVGL,ESP32移植LVGL详细教程
  8. 如何和后台接触的_后台产品,不只是做支持
  9. android从服务检查,android开发分享Android:你如何检查是否启用了特定的AccessibilityService...
  10. aj6 stamps storm_亲友限定的 AJ 6 要发了?3 月好鞋发售清单 for girls