一个C/S模式的socket应用,服务器端采用c#编写。当客户端调用的时候,服务器端偶尔会获取不到客户端发送的信息,并且是再也收不到该客户端发送的信息,直到这个客户端重新绑定一个新socket来连接。这个问题在一台客户端或者多台客户端同时保持连接时都会出现。关键代码如下:
IPEndPoint localEndPoint = new IPEndPoint(ipAddress,Convert.ToInt32(port_));
Socket listener = new Socket(AddressFamily.InterNetwork,SocketType.Stream,ProtocolType.Tcp);
try
{
listener.SetSocketOption(SocketOptionLevel.Socket,SocketOptionName.ReuseAddress,50);
listener.Bind(localEndPoint);
listener.Listen(400);
Socket s = listener.Accept();
while(s!=null)
{
MsgOperate o=new MsgOperate(this);
o.ClientSocket=s;
Thread clientservice = new Thread(new ThreadStart(o.Poll)); 
clientservice.Start(); 
s=listener.Accept();
}
}
catch(Exception ex)
{
//错误抛出(此处没有抛出过错误)
}public class MsgOperate
{
public void Poll(){
while(true)
{
if(clientsocket.Poll(-1,SelectMode.SelectRead))
{
//如果引发消息监听的socket已关闭,则退出循环
int k = ServiceClient();
if (k == 0)
    break;
}
}
}
public int ServiceClient() 

while(true)
{
try
{
if(socket.Available==0)
 { returnvalue=0;
  break;
}
else
{returnvalue=1;
//做消息处理
}
return returnvalue;
}
catch(Exception e)
{
return 0;
}
}
}

解决方案 »

  1.   

    http://www.cnblogs.com/Pierce/category/22231.html
      

  2.   

    你的文章写的很好,可是不是我要的。谁来救救我,突然接收不倒消息,重启socket又可以正常通讯。用sniffer监视,发现机器是收到消息的,但是程序的listen没有listen到
      

  3.   

    Thread clientservice = new Thread(new ThreadStart(o.Poll));把线程打开的地方放在程序循环外面。试试。
      

  4.   

    to:whChina  为什么要放在循环外面?我试过把while(s!= null)改成while(true),应该和放在循环外面一个效果吧。还是有这个问题。
      

  5.   

    看了下,你的代码里获取的socket连接没有保存过。没有断线重新连接。应该在主程序里还开了一个线程吧。这样的话,可能是多线程的问题。阻塞若没开其他线程的话,你怎么轮询多个client?
      

  6.   

    whChina,有msn吗?能和你直接交流吗?
      

  7.   

    服务端的SOCKET程序一般都不用C#写,效率太低。
      

  8.   

    可能是你的緩沖區的問題,以前我把server和client放到一台主機上運行時,就會遇到偶爾收不到的情況。你可以用tcpListen和tcpClient來試試,他們都是繼承自socket的。
      

  9.   

    to gxy2005.如果几千次出现一次,可以这样解决,如果出现次数多的话,这样解决怕是不行的,尤其有一些消息远远大于8K
      

  10.   

    to tjvictor:如果是这样,不能解释2台客户端连接主机.一台客户端始终没问题,另外一台经常出现问题的情况吧.
    个人认为是if(clientsocket.Poll(-1,SelectMode.SelectRead))这个判断没有通过。可是不知道该如何解决,用单步调试,调试不到这个地方
      

  11.   

    Socket如果长时间没有通讯,可能会造成连接丢失,我做的类似项目是让客户端每隔几秒钟发送一个测试消息,服务器收到消息后给客户端一个回复,如果两端在规定的时间内没有收到消息,则服务端放弃该连接,客户端自动重新建立连接。
      

  12.   

    to baixc 我也猜测是连接断了。不过用netstat查看的时候,一般是连接装他established或者有些时候是close_wait状态。不过这个连接丢失的话不会连上就丢失吧?有些时候就是上一次操作好的,下一次操作就失败了。中间间隔也就是几秒或者几十秒
      

  13.   

    因为我这边每一个连接的socket都用一个线程,线程的优先级不知道怎么设定。如果是这个线程在机器收到消息,程序没收到消息的时候突然delay了,那就真不知道该如何处理了
      

  14.   

    Socket如果长时间没有通讯,可能会造成连接丢失
      

  15.   

    用心跳消息来保证Socket的正常连接。心跳消息:
    由客户端每隔一段时间(如3秒)发送一个简单的特定的消息,如果超过一定的时间(如5秒)没有收到响应消息,则放弃此Socket,重新连接。(因此客户端需要一个timer)
    而服务器只需要在收到心跳消息后回一个心跳响应消息。