我近来碰到这样的问题:
   一个客户端连接发起大约30几万次连接成功后,再连接时出现连接不上服务器的问题,但我在服务器所在机子上 敲入“netstat /a”命令后,发现服务器监听的端口号正常,且只有几个time_wait。当我将服务器进程重启一下(不是重启机子),服务器又工作正常了,并且可以接收新的客户端连接请求了。
   客户端工作方式:每完成连接服务器3千次后,就睡眠4分钟,同时,每次断开连接都是客户端发起的,一次连接交互通信的时间大约为100毫秒
   服务器工作方式:主线程始终监听端口号7000,当有一个连接时,就为此链接创建一个新线程与客户端交互通信。
   客户端测试方式:客户端向服务器端请求连接,完成与服务器通信后,就断开此连接。重新开始,连接进行300万次,每次间隔50毫秒。服务器端监听线程代码:

        int z=0;
WSADATA wsaData; 
int iRet=WSAStartup(MAKEWORD(2,2),&wsaData); 
if(iRet!=NO_ERROR)
{
WSACleanup(); 
return ERROR; 
}
//create a socket 
SOCKET m_ClientSocket; 
m_ClientSocket=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);
if(m_ClientSocket==INVALID_SOCKET) 

WSACleanup(); 
return ERROR;  

int sndbuf=1024*30;        /* Send buffer size */
        int rcvbuf=1024*30;        /* Receive buffer size */
        setsockopt(m_ClientSocket,SOL_SOCKET,SO_SNDBUF,(const char*)&sndbuf,sizeof(sndbuf));
        setsockopt(m_ClientSocket,SOL_SOCKET,SO_RCVBUF,(const char*)&rcvbuf,sizeof(rcvbuf));
//bind a socket 
sockaddr_in service; 
service.sin_family=AF_INET; 
service.sin_addr.s_addr=INADDR_ANY; service.sin_port=htons(7000);
if(bind(m_ClientSocket,(SOCKADDR*)&service,sizeof(service))==SOCKET_ERROR) 

closesocket(m_ClientSocket); 
WSACleanup(); 
return ERROR; 

//listen on a socket 
if(listen(m_ClientSocket,1000)==SOCKET_ERROR)
{
closesocket(m_ClientSocket); 
WSACleanup(); 
return ERROR; 
}
else
{
str.Format("Client socket begin listening and the listen port is %d ",LISTEN_CLIENT_PORT);
FhtLogEx(info2, str);
}
//accept a connection  while(1) //listen and creat a ClientFileThread 
{
SOCKET AcceptSocket; 
struct sockaddr_in local_addr;//record client info
int   remote_addr_len =   sizeof(local_addr);
AcceptSocket=SOCKET_ERROR; 
while(AcceptSocket==SOCKET_ERROR) 
{
AcceptSocket=accept(m_ClientSocket,(SOCKADDR*)&local_addr,&remote_addr_len); 
}
if (INVALID_SOCKET==AcceptSocket)
{
GetSocketErrorCode();
}
else
{
LPCTSTR   lpClientIp   =   inet_ntoa(local_addr.sin_addr);
DWORD dwThreadId;
HANDLE hThread;
hThread=CreateThread(NULL,NULL,ClientFileThread,  
(LPVOID)AcceptSocket,0,&dwThreadId); 
if(hThread==NULL) 
{
}
else 

}
}
}
closesocket(m_ClientSocket); 
WSACleanup(); 
return OK; 
客户端每次连接服务器的代码:

         WSADATA wsaData; 
int iRet=WSAStartup(MAKEWORD(2,2),&wsaData); 
if(iRet!=NO_ERROR)
{
return SOCKET_INIT_ERROR; 
}

        if ((Socket =  socket (AF_INET, SOCK_STREAM, IPPROTO_IP)) == INVALID_SOCKET) 
{
                return SOCKET_INIT_ERROR;
        }
BOOL bReuseaddr=TRUE;
setsockopt(Socket,SOL_SOCKET ,SO_REUSEADDR,(const char*)&bReuseaddr,sizeof(BOOL)); 
return OK;
SOCKADDR_IN inetAddr;
        inetAddr.sin_family=AF_INET;
inetAddr.sin_addr.s_addr= inet_addr(strServerIP);
inetAddr.sin_port=htons(uServerPort);
        while (connect(SendFileSocket, (struct sockaddr *)&inetAddr, sizeof (inetAddr)) == SOCKET_ERROR) 
{
closesocket(SendFileSocket);
WSACleanup();
                return CONNECT_ERROR;
       }

if (send(SendFileSocket,(char *)&(fileinfo),sizeof(fileinfo),0)!=sizeof(fileinfo))
{
file.Close();
closesocket(SendFileSocket);
WSACleanup();
return SEND_FAILED;
}        closesocket(SendFileSocket);
        return OK;

解决方案 »

  1.   

    把ClientFileThread的代码发来看看.
      

  2.   

    服务端CreateThread后,CloseHandle(hThread);
      

  3.   

    嗯, 很可能是资源泄露, 3楼的建议不错, 还可以用于调试, 把一些主要资源, socket,线程, 打开的文件数, 内存消耗等计数, 就好分析了.
      

  4.   

    hThread=CreateThread(NULL,NULL,ClientFileThread,  
                    (LPVOID)AcceptSocket,0,&dwThreadId);  换成_beginthread吧,此外线程函数要善后。
      

  5.   

    CreateThread返回的句柄关了吗?看一下进程的句柄数。