基于TCP的流式套接字(Socket)接收数据不完全

Neil_wzb 2009-07-22 05:42:29
采用TCP的流式Socket接收对方发送的数据,对方发送数据(按帧计算,分帧编号)的速度比较快,而且是接连发送2帧数据后(4096bits),稍停顿下,再发下2帧,我在这边采用基于消息的响应模式接收数据:

case F_READ:
int recvNums = Receive()接收,

每次Receive函数返回的值是4032,可是我把收到的原始数据写到文件后,发现通常对方发送的每2帧,我只能收到1帧。但是通过抓包软件,发现数据都是过来了的。

那么,为什么我收到的数据会不完全呢?

PS:我的缓冲区设的比较大了已经(64K)
...全文
1238 59 打赏 收藏 转发到动态 举报
写回复
用AI写文章
59 条回复
切换为时间正序
请发表友善的回复…
发表回复
sjbingyan 2010-09-25
  • 打赏
  • 举报
回复
TCP 接收数据包的时候,能一次只接收一包吗?
zhhuajian 2010-08-17
  • 打赏
  • 举报
回复
mark回去细看
zhhuajian 2010-07-30
  • 打赏
  • 举报
回复
mark,遇到类似的问题,看有没有帮助
Pro_X 2009-08-21
  • 打赏
  • 举报
回复
换udp试试
lk_cool 2009-08-21
  • 打赏
  • 举报
回复
楼上的,问一下。
使用IP报文发送,怎么使用TCP接收?

问题:
1、和缓冲区大小没有关系。缓冲区再大你send的时候不一定全部发出去。recv的时候不一定全部收过来,你得考虑网络传输的带宽情况。
2、如果是阻塞方式的socket,既然你抓包都能获得,你程序应该能完全收到。如果是非阻塞方式,你需要特殊处理。

建议:
首先弄清楚,对方给你发数据时采用什么方式。有什么注意点。
使用最基本的socket试试。建立个套接字,listen一下,使用阻塞非阻塞都试一下,看看问题出在什么地方。(记着用free_eyes说的方法)
pady_pady 2009-08-14
  • 打赏
  • 举报
回复
TCP协议的send和recv在我们看来很简单,其实他内部实现极其复杂,所以建议你问下他如果丢失报文了,应该怎么发送丢失报文的号给他处理
pady_pady 2009-08-14
  • 打赏
  • 举报
回复
[Quote=引用 45 楼 neil_wzb 的回复:]
引用 44 楼 conry 的回复:
在没有代码的情况下上面各位已经分析的差不多了,
你把上面所述的方案都试一下,总比干等着强吧。而且还可以学习知识

另外说一下,我写网络程序还没用用过那么大的接受缓冲,一般一次接收1024,即recv(buf,1024),为了方便处理粘包,buff大小2048


我没干等着的,上述的方案我都挨个试了一下,今天我用API也重新写了程序,还编了几个测试程序,实在就是接收不完整啊。我就纳闷了,为什么抓包软件都能抓到,可是Socket就是接受不完全呢?有没有可能缓冲区自己丢数据啊?
[/Quote]

如果真是这样,估计是因为你用的是TCP,他用的是IP报文发送机制,而且不会在失败后重发。正常TCP接收速度是变化,用的是滑动窗口机制,如果发送方用的不是TCP机制,只是简单的发送报文而不管,丢包是很有可能的啊。所以问题在于他而不是你,如果是这种情况,你试试发送没有收到的报文编号,看他能不能重新发送给你,如果他没有这种机制就没办法了。
你要清楚,TCP其实不是连续的接收或发送的,一般是按网速自动调整的,就是说发一个包要等一小会的。如果对方发送太快,你就会丢包,办法只有是:
1。对方同样用TCP。
2。对方有报文处理机制,可以实现重发,这样你要问问他有没有。如果有,你要问他怎么发送出错包通知他重发
Zhurikeji 2009-07-31
  • 打赏
  • 举报
回复
有没有相关的书籍?
steven_007 2009-07-31
  • 打赏
  • 举报
回复
mmx2008 2009-07-29
  • 打赏
  • 举报
回复

mark
lijinglailenny3 2009-07-29
  • 打赏
  • 举报
回复
循环接收
songtao_01 2009-07-28
  • 打赏
  • 举报
回复
1.你用什么抓的包(有的工具抓的包,包的大小是包括TCP头的,所以长度大于实际接受的有用数据);
2.还有就是这个跟缓冲区大小没有关系.
3.你抓的包里面的数据是正常的吗(你确定一下)?
4.你是否是用的多线程?如是,同步做好了吗?
5.m_sock是什么类型的,CSocket?如是,那这个m_socket.Receive(dwBuf,sizeof(1)*RECV_BUF_SIZE,0); 可能会在你还没有处理完数据的时候调用两次,从而覆盖了你上次调用的数据.
zhujuncug 2009-07-28
  • 打赏
  • 举报
回复
需要在在应用层定个简单的协议来保证数据接受完全的问题,如包头(包长)+数据,先读包头,在根据包头中数据的内容循环的读取数据的长度。读到一帧数据后再读下一个包头,如此循环...
Neil_wzb 2009-07-27
  • 打赏
  • 举报
回复
自己顶一下吧,这样的问题没有人遇到过吗,有没有帮我分析下……
Neil_wzb 2009-07-25
  • 打赏
  • 举报
回复
不能加分了,郁闷
Neil_wzb 2009-07-25
  • 打赏
  • 举报
回复
谢谢楼上的老兄,这么多人帮顶,真是幸福啊。要加分了这个帖子
Neil_wzb 2009-07-25
  • 打赏
  • 举报
回复
[Quote=引用 44 楼 conry 的回复:]
在没有代码的情况下上面各位已经分析的差不多了,
你把上面所述的方案都试一下,总比干等着强吧。而且还可以学习知识

另外说一下,我写网络程序还没用用过那么大的接受缓冲,一般一次接收1024,即recv(buf,1024),为了方便处理粘包,buff大小2048
[/Quote]

我没干等着的,上述的方案我都挨个试了一下,今天我用API也重新写了程序,还编了几个测试程序,实在就是接收不完整啊。我就纳闷了,为什么抓包软件都能抓到,可是Socket就是接受不完全呢?有没有可能缓冲区自己丢数据啊?
Conry 2009-07-25
  • 打赏
  • 举报
回复
在没有代码的情况下上面各位已经分析的差不多了,
你把上面所述的方案都试一下,总比干等着强吧。而且还可以学习知识

另外说一下,我写网络程序还没用用过那么大的接受缓冲,一般一次接收1024,即recv(buf,1024),为了方便处理粘包,buff大小2048
Neil_wzb 2009-07-25
  • 打赏
  • 举报
回复
自己顶一下…………
Neil_wzb 2009-07-25
  • 打赏
  • 举报
回复
现在把问题进一步明了一下:

我们的工程是这样的。发送方自己实现了TCP/IP协议,他将每288字节数据,加上TCP头和尾做成一包发送给我。288字节数据是我们自己定义的一帧,每帧都是编号的。

但是当发送方给我发过数据来以后,通过抓包软件,我发现每一包数据都含有一帧,而且帧编号是连续的。但是,我这边通过Socket接收以后,不论我将缓冲区设为多大(不论是设为帧大小288的整数倍,还是只设为288),总是会丢掉几帧,一般是隔一帧丢一帧,但是这种情况不是绝对,也有连续的帧出现。

请大家帮忙分析分析,到底是哪里出现了问题呢?
加载更多回复(39)

18,356

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC 网络编程
c++c语言开发语言 技术论坛(原bbs)
社区管理员
  • 网络编程
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

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