LinuxSir.cn,穿越时空的Linuxsir!

 找回密码
 注册
搜索
热搜: shell linux mysql
查看: 2841|回复: 12

linux socket 通信中并发服务器拒绝连接,重置连接,客户端自动关闭问题

[复制链接]
发表于 2007-1-22 11:16:45 | 显示全部楼层 |阅读模式
我写好了一个client 在arm9上跑,同事写了个server在win2000上跑,client往server发数据,服务端程序是阻塞式多线程实现,问题是:通信过程中,client会不明原因地自动结束(不明原因是只没任何提示),有的时候又可以看到如:connection refused和 connection reset by peer.初步原因经查证为:
                                  1,tcp 端口连接数逻辑上为256个,但是因为服务线程处理数据费时,速度比client连接慢,没及时断开连接.
                                  2,服务器套接口维护的连接队列长度不能满足需求

我现在还迷惑的是:
                 1;即使服务器重置连接或拒绝连接,client也不应该会结束,因为我的client在连接传输过程中的每一步失败后都是continue,继续尝试.
                 2;服务端拒绝连接和重置连接这种情况有什么好的解决方法啊,不可能每次都要重启client吧,我增设了服务端tcp端口连接上限效果也一样.
                 3;服务器套接口的连接队列大小该怎么设置,服务器程序是用c++写的,在c中是改变listen()函数的第二个参数设置,c++中同事不清楚怎么改
发表于 2007-1-22 11:31:00 | 显示全部楼层
1. 是不是遇到出错或者被中断后,服务器端采取close了socket导致的?
2. 采用循环,while(1)
3. 不知道, C++中不是调用listen()么, 应该也有BACKLOG这个参数吧.
回复 支持 反对

使用道具 举报

 楼主| 发表于 2007-1-22 11:36:55 | 显示全部楼层
1,服务端应该是生成的新线程处理完数据就close socket.
2,我是采用的循环,while(1),所以有那样的疑问,不管怎么样它都应该跳不出循环
3,c++中的listen()就这样的,不带参数
刚才同事自己用c++写了个客户端,往server上发数据,他说都没问题,郁闷啊!
回复 支持 反对

使用道具 举报

发表于 2007-1-22 12:42:50 | 显示全部楼层
客户端socket初始化和发送部分代码贴出来瞧瞧
回复 支持 反对

使用道具 举报

 楼主| 发表于 2007-1-22 14:28:56 | 显示全部楼层
client socket 核心代码如下代码在虚拟机上,好象不能直接拷贝出来)

  1. 0  int upload(){

  2. 1  int f;//文件标识符

  3. 2 size_t rsize;//读取长度

  4. 3  struct stat buffer;//结构,用来取得文件大小

  5. 4  unsigned char buf[1024+1];//缓冲区

  6. 5  struct sockaddr_in servaddr;

  7.     //初始化套接口,hostname和port是经过参数初始化了的服务器ip和端口

  8. 6  servaddr.sin_family=AF_INET:

  9. 7  servaddr.sin_port=htons(port);

  10. 8   if(inet_pton(AF_INET,hostname,&servaddr.sin_addr)<=0){

  11. 9        perror("inet_pton");

  12. 10  }

  13. 11  while(1){

  14. 12   stat(filename,&buffer);//取得文件属性

  15.     //打开文件

  16. 13    if((f=open("filename",O_RDONLY))<0){

  17. 14        perror("can't open file");

  18. 15       continue;

  19. 16    }
  20.       //生成套接口

  21. 17    if(sockfd=socket(AF_INET,SOCK_STREAM,0)<0){

  22. 18        perror("socket");

  23. 19         close(f);

  24. 20         continue;

  25. 21    }
  26.       //连接服务器

  27. 22     if(connect(sockfd,(struct sockaddr *)&seraddr,sizeof(struct sockaddr))<0){

  28. 23          perror("connect");

  29. 24          close(f);

  30. 25          close(sockfd);

  31. 26         continue;

  32. 27    }

  33. 28    resize=buffer.st_size;//文件大小

  34. 29     while(rsize>0){

  35. 30           resize -=readn(f,buf,1024);//readn()函数是经过封装了read函数能准确读一定字节文件的函数

  36. 31           writen(sockfd,buf,1024);//和readn函数一样封装过write函数

  37. 32     }

  38. 33     close(f);

  39. 34     close(sockfd);

  40. 35  }

  41. 36}
复制代码
回复 支持 反对

使用道具 举报

发表于 2007-1-22 16:19:41 | 显示全部楼层
给代码加上标签吧, 这样看起来清晰
回复 支持 反对

使用道具 举报

 楼主| 发表于 2007-1-22 16:30:09 | 显示全部楼层
客户端会关闭这点最让我头疼,始终弄不明白
回复 支持 反对

使用道具 举报

发表于 2007-1-22 16:53:29 | 显示全部楼层
贴代码用[code] [/code]
回复 支持 反对

使用道具 举报

 楼主| 发表于 2007-1-23 11:11:09 | 显示全部楼层
经抓包分析,服务器发向客户端的ack有一部分有于防火墙的原因,客户端没收到,在抓包软件中的提示中看到 如:tcp slow ack 和tcp connect repeated attempt,然后看到服务器发给客户端的包中 tcp flag字段 reset 是1
但是这样好象也不是能解释 客户端会关闭 的真正原因吧
还有就是我在所抓的包中看不出来有fin包
回复 支持 反对

使用道具 举报

 楼主| 发表于 2007-1-23 17:49:50 | 显示全部楼层
经分析,客户端的关闭有可能是因为 writen函数产生SIG_PIPE信号或者readn函数产生SIG_SEGV信号而终止进程
现在我读信号处理不清楚,哪位兄弟能告诉我在代码什么位置加什么代码吗,我的客户端是要一直运行下去的呀
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

快速回复 返回顶部 返回列表