tcp接受窗口会不会带来死锁?

bsnry 2016-03-10 03:44:42
我看过一个人写的书, 接收方连续发送win=0的包给发方,连续发了好几次。

当然,这几个连续的包之间里,并没有出现发方的包!! 因为发方知道收方的win=0, 所以不会发送数据。

问题来了:

1. 什么原因导致接收方会连续发送win=0的包

recv/read系统调用有两部分功能: (1)发送ack和win (2)从内核中取出数据到应用缓冲区中。

难道是说,接收方的代码 连续调用这些api, 但api的返回值为0, 体现出: 接受窗口爆满,而且应答ack+win。


2. 由于 接收方 的接受窗口为0,那么会不会导致发方的重传定时器触发,要发数据给接收方,结果接收方的应答报文里的win=0,从而死锁。




...全文
278 11 打赏 收藏 转发到动态 举报
写回复
用AI写文章
11 条回复
切换为时间正序
请发表友善的回复…
发表回复
oniisama 2016-03-14
  • 打赏
  • 举报
回复
1.快速重传是连续收到dup ack后重传,超时重传是没收到ack导致超时后重传。 2.有包丢失的话,收到后续包时接收方会返回它期望的下一个数据包的seq作为ack,也就是后面不管收到3号包4号包,都会返回2号包的seq,这才会产生dup ack,也是实现快速重传的前提条件。当收到重传的第2个包之后,假如之前3、4、5号包都已经接收到了,就会直接返回5号包的ack。
oniisama 2016-03-11
  • 打赏
  • 举报
回复
引用 6 楼 oniisama 的回复:
看潘爱民翻译的《计算机网络》,每台主机会定时在每个连接上发送确认和缓冲大小的控制段,所以 1.接收方长时间没有可用缓冲区的时候,可能就会连续发送win=0的包。 2.接收方win=0时发送方不会重传,因为这样只会加剧拥塞。有可能发生死锁的情况是,接收方有可用缓冲时,发送给发送方的控制段丢失,发送方无法得知该变化,为了解决这种情况才会定时发送包含缓冲大小的控制段。
更正一下,刚翻了一下书,这个是数据报网络的情况,tcp不一定是这样
pengzhixi 2016-03-11
  • 打赏
  • 举报
回复
引用 5 楼 bsnry 的回复:
[quote=引用 4 楼 pengzhixi 的回复:] 1.只能确定接收方的数据包没有被消费就会发送win=0的数据包 2.为什么会死锁呢?如果接收方很久没回数据包,那么发送方会发送数据询问接收方是否有窗口可以接收。
.为什么会死锁呢?如果接收方很久没回数据包,那么发送方会发送数据询问接收方是否有窗口可以接收。 这条理论似乎我没见过? 这个循环算是重传机制还是什么? [/quote] 不是重传机制,只是说发送方很久没接到接收方的ack包(ack包里面包含了数据窗口大小,可能这个ack包丢失了),这个时候发送方就发送这种窗口探测的数据包。这个情况一般很少。
oniisama 2016-03-11
  • 打赏
  • 举报
回复
看潘爱民翻译的《计算机网络》,每台主机会定时在每个连接上发送确认和缓冲大小的控制段,所以 1.接收方长时间没有可用缓冲区的时候,可能就会连续发送win=0的包。 2.接收方win=0时发送方不会重传,因为这样只会加剧拥塞。有可能发生死锁的情况是,接收方有可用缓冲时,发送给发送方的控制段丢失,发送方无法得知该变化,为了解决这种情况才会定时发送包含缓冲大小的控制段。
bsnry 2016-03-11
  • 打赏
  • 举报
回复
引用 4 楼 pengzhixi 的回复:
1.只能确定接收方的数据包没有被消费就会发送win=0的数据包 2.为什么会死锁呢?如果接收方很久没回数据包,那么发送方会发送数据询问接收方是否有窗口可以接收。
.为什么会死锁呢?如果接收方很久没回数据包,那么发送方会发送数据询问接收方是否有窗口可以接收。 这条理论似乎我没见过? 这个循环算是重传机制还是什么?
pengzhixi 2016-03-11
  • 打赏
  • 举报
回复
我可能大概知道你说的快速重发和超时重发了。 你说的超时重发可能是针对这种没有窗口机制控制的时候,发送端有一个超时,这个超时就是发送端认为在这个时间内一定会收到接收端的确认包,如果到了这个时间还没收到那么发送端认为之前的数据包丢失然后重发。 快速重发,是发送端直接发送序列号为 1,2,3,4,5个数据包过去,加入序列号为2的数据包丢了,这个时候接收端连续发几个响应包说发送端你要发2号包给我,然后发送端收到这几次响应报之后马上重发2号包,然后在接收端接收到之后,发响应包告诉发送端接下来你该发6号数据包了。
bsnry 2016-03-11
  • 打赏
  • 举报
回复
引用 8 楼 oniisama 的回复:
[quote=引用 6 楼 oniisama 的回复:] 看潘爱民翻译的《计算机网络》,每台主机会定时在每个连接上发送确认和缓冲大小的控制段,所以 1.接收方长时间没有可用缓冲区的时候,可能就会连续发送win=0的包。 2.接收方win=0时发送方不会重传,因为这样只会加剧拥塞。有可能发生死锁的情况是,接收方有可用缓冲时,发送给发送方的控制段丢失,发送方无法得知该变化,为了解决这种情况才会定时发送包含缓冲大小的控制段。
更正一下,刚翻了一下书,这个是数据报网络的情况,tcp不一定是这样[/quote]
引用 7 楼 pengzhixi 的回复:
[quote=引用 5 楼 bsnry 的回复:] [quote=引用 4 楼 pengzhixi 的回复:] 1.只能确定接收方的数据包没有被消费就会发送win=0的数据包 2.为什么会死锁呢?如果接收方很久没回数据包,那么发送方会发送数据询问接收方是否有窗口可以接收。
.为什么会死锁呢?如果接收方很久没回数据包,那么发送方会发送数据询问接收方是否有窗口可以接收。 这条理论似乎我没见过? 这个循环算是重传机制还是什么? [/quote] 不是重传机制,只是说发送方很久没接到接收方的ack包(ack包里面包含了数据窗口大小,可能这个ack包丢失了),这个时候发送方就发送这种窗口探测的数据包。这个情况一般很少。[/quote] 请无视主楼的问题, 主楼的问题本身就是一个错误的,所以回答毫无意义。 主楼犯了一个错误———— ack是内核做的,不是应用层,也就是说,即使应用层故意不接受recv, 那么发方也会回应ack。 ack包中含有接受窗口的大小!!! 请教一个新的问题———— 1. 超时重传和快速重传到底有什么区别? 快速重传是指: 网络丢失少量的包,那么收方会收到的包里的seq,和其期望的大小不一,准确的说,是seq过大!!! 所以收方就发送三次dup ack 给发方!!! 超时重传呢? 2. 对于快速重传后,收方如何继续后续操作,比如发送10个包,结果第2个包丢失,所以就收方告诉发方快速重传!!! 但是重传之前,收方收到了第3个包,这个时候收方怎么办? 如何回应发方? 回应的包里的seq大小是多少? 是回应收方期待收到第4个包呢?还是回应期待要收第2个包。如果是回应收到第2个包,发方收到后,快速重传第2个包,收方收到第2个包后,那么此时回应什么?回应他期待第4个包? 还是什么?
pengzhixi 2016-03-10
  • 打赏
  • 举报
回复
1.只能确定接收方的数据包没有被消费就会发送win=0的数据包 2.为什么会死锁呢?如果接收方很久没回数据包,那么发送方会发送数据询问接收方是否有窗口可以接收。
UDX协议 2016-03-10
  • 打赏
  • 举报
回复
1.当接收方没有调用Recv的时候,一直不调用,但是远程调用Send把buff发过来了,这时,接收方就会发送窗口为0的ACK,通知发送方不用发数据了。 2.不会死锁,当接收方,重新调用Recv的时候,由于接收方接收窗口大于0,从而通知发送方,可以发数据了。
赵4老师 2016-03-10
  • 打赏
  • 举报
回复
建议楼主先学会使用抓包软件比如wireshark
bsnry 2016-03-10
  • 打赏
  • 举报
回复
引用 1 楼 zhao4zhong1 的回复:
建议楼主先学会使用抓包软件比如wireshark
这和我的问题有关?
  大家好,我是录制课程的老师,课程已经上线课堂,欢迎大家试听,感谢同学们的支持。在你们的学习中我全力助你提升MySQL技能,助你冲击更高年薪。支持课程答疑,支持一对一答疑服务,由课程老师直接回答。    MySQL凭借着它不错的性能、不错的稳定性、数据的安全性常年稳居行业老二宝座。    越来越多的DBA和后端同学在工作中少不了和MySQL打交道,也经常产生这样的疑问:    为什么我写的sql语句性能这么低?  为什么明明我建了索引却没有用到索引?  为什么突然我的数据就成了乱码?  为什么我备份的文件在主库恢复,数据无法同步到从库?  为什么我的数据库数据不多,却占了很多的空间?  生产中我应该选择哪种隔离级别?  生产中都在使用innodb存储引擎,我却对它一无所知?  我应该怎么规划缓冲池才能让数据库性能更高?  为什么我做表数据迁移这么慢?  为什么我写的sql造成那么多的锁冲突、死锁?  为什么我不能将数据恢复到任意时间点?  为什么我不能解决公司主从复制架构中的故障?  吧啦吧啦一大堆问题……    在面试中MySQL的一些知识更成为躲不过的问题,比如b+tree索引、MVCC、隔离级别的实现、锁的使用,主从复制,MySQL性能优化、事务两阶段提交等等都成为了面试考题重灾区。    我的课程就是从实际工作来,从问题出发,带着问题来学习MySQL,想解决问题就要学习新的知识,大家跟紧老司机,MySQL的面纱就慢慢摘下。

64,654

社区成员

发帖
与我相关
我的任务
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++ 技术论坛(原bbs)
社区管理员
  • C++ 语言社区
  • encoderlee
  • paschen
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
  1. 请不要发布与C++技术无关的贴子
  2. 请不要发布与技术无关的招聘、广告的帖子
  3. 请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下

试试用AI创作助手写篇文章吧