TCP/IP (三) TCP消息的接收

上一篇文章提到:

先发送数据包data1,再发送数据包data2

data1的数据是有可能比data2先达到对端的接收缓冲区,

但是对端调用接收函数时,是不可能先读取到data2再读取到data1,

下面说明为什么会出现这种情形。

 

这里先借用陶大师的一张图,

情景:socket为阻塞模式,调用recv等方法时flag标志位为0,未对SO_RCVLOWAT做设置



1.  应用程序开始收取TCP消息,与程序所在的机器网卡上接收到网络里发来的TCP消息,这是两个独立的流程,所以第一篇文章中提到的通过127.0.0.1发送数据,只经过内核,不经过网卡,也就可以理解了。

 

2.接收TCP消息最终会调用tcp_recvmsg方法,而tcp_recvmsg会首先锁住socket,因此socket是可以被多进程同时使用的。

 

3.内核在处理接收到的TCP报文时使用了4个队列容器,分别为receive、out_of_order、prequeue、backlog队列


receive:receive队列是允许用户进程直接读取的,它是将已经接收到的TCP报文,去除了TCP头部、排好序放入的、用户进程可以直接按序读取的队列

out_of_order:失序的数据包,暂时存放

prequeue:未被处理的数据包,暂时存放

backlog:未被处理的数据包,暂时存放


这里的数据流是比较复杂的,有兴趣研究清楚的可以点击文章末尾推荐的链接进去学习,这里就不搬陶大师的劳动成果了。 


4.flags参数MSG_PEEK标志位会导致receive队列不会删除报文,MSG_PEEK主要用于多进程读取同一套接字的情形

5.阻塞socket模式下,flags参数中若携带MSG_WAITALL标志位,则意味着必须等到读取到len长度的消息才能返回,否则按SO_RCVLOWAT属性处理


参考资料:《tcp/ip详解卷1》

参考文章:http://blog.csdn.net/russell_tao/article/details/9950615 强烈推荐!






评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值