socket中send函数的研究
send函数的具体细节这篇文章写得很好,
http://blog.csdn.net/locape/archive/2011/03/31/6292659.aspx
。
现在的问题是: 发送方如何知道接收方确实正确无误地收到数据了?
以下是我理解的,还没有仔细的把(tcp/ip详解三卷给研读完,所以。。。),自知对tcp了解暂时还不够,故不知道对不对,请大家共同探讨。
1. 如果是阻塞的,send会把数据拷贝到内核的tcp缓冲区中,然后等待内核把数据全部发送出去(不一定收到)才返回; 如果非阻塞,则把发送内容尽量拷贝到内核tcp的缓冲区,没拷贝完全部数据也会直接返回。
2.如果内核的tcp协议第一次发送失败(一定时间内没有收到接收方的确认),则会过一定时间后再进行第二次发送。。。 循环直到超时时间到。 如果超时了,发送方下次调用send会返回错误。
现在我想尽快知道接收方是否收到数据了。 先分析一下QQ。a) 我在实验时,发送方发一条消息后,对方会立即收到。b) 如果先把网络断开,那么QQ检测到网络不通,则不让发送,提示未联网。 c) 如果网络断开后,在QQ头像还未变灰,也就是QQ还没来得及检查网络是否连通时,发送一条消息出去,这时大约过了5秒左右会提示发送失败。 d)如果在未反馈发送失败之前再把网络连上那么依然能发送成功。
在上面的c情况下,我觉得QQ是在等待对方回复一个确认消息,如果大约5秒内没有收到则让tcp/udp停止尝试并向用户提示发送失败。
类似的,如果我们也这么设计通信双方, 发送方send之后要等接收方反馈一个确认。 现在我的问题是,如何保证这个确认能正确无误地被传到发送方?
假设这样一个场景:
A向B发了(send)条消息,A在大约6秒内想知道B是否收到(这段时间里内核可能已经通过复杂的超时算法和重传机制尝试过若干次了,但还没有超时), B在A发出后2秒内就收到了消息于是发送确认,但是中途某某些原因(如路由器重启了)导致没有过成功发到A,于是B的内核在等待重传这个确认或者直接超时或者主机不可达等错误。
但是此时A不知道B已经成功收到了数据,于是又重传。。。
而此时B不知道这个确认是否正确发送到A手中,也有可能B知道这个确认发送失败,于是不断的重发。
这个问题处理起来就复杂了。。。
-----------------------
[解决办法]
有意思.帮顶
[解决办法]
这篇文章貌似错了吧。 阻塞 模式下也是把 buff 拷贝到tcp buff去, 然后返回, 返回时数据并不保证已经被发送出去, 不然那个nagle 算法就没用了
[解决办法]