本人要做一个模拟发包程序,在压力测试中,每个线程代表一个“客户端”。现在的问题是:
1 在1500个线程时运行很稳定,但是线程数超过1600以后机器就会重新启动,请问是内存溢出问题还是别的地方出问题了?
2 我的每个线程都建了2个阻塞的socket连接,是不是socket连接数限制了可创建的线程数量?
3 WSAGetLastError()=10048,正常情况下每一个套接字地址(协议/IP地址/端口号)只允许使用一次。如果要重复使用一个套接字怎么解决?
4 线程公用的一个类中有static unsigned long SocketsNum;在使用SocketsNum++;的时候是否需要加锁?

解决方案 »

  1.   

    1、如果线程很多,建议用线程池,或完成端口
    2、socket可以有很多,但线程是有限的
    3、端口重用
    4、加锁
      

  2.   

    1 在1500个线程时运行很稳定,但是线程数超过1600以后机器就会重新启动,请问是内存溢出问题还是别的地方出问题了?
    >>一个是检查所有函数(Function)的返回值,并加以处理,做好多线程访问的内存空间的写保护 
    2 我的每个线程都建了2个阻塞的socket连接,是不是socket连接数限制了可创建的线程数量? 
    >>对于外连连接数的限制,可以通过修改注册表解决,建议不要使用WinXP,特别是WinXP SP2
    3 WSAGetLastError()=10048,正常情况下每一个套接字地址(协议/IP地址/端口号)只允许使用一次。如果要重复使用一个套接字怎么解决? 
    >>使用Winsock2的Overlapped机制,需要重复使用的Socket用DiconnectEx替代closesocket
    4 线程公用的一个类中有static unsigned long SocketsNum;在使用SocketsNum++;的时候是否需要加锁?
    >>可以使用InterlockedIncrement(原子操作)来替代CriticalSection等,如果机器支持的话
      

  3.   

    端口重用设置过了        int   optval = 1;  
    if ( setsockopt ( Socket,SOL_SOCKET, SO_REUSEADDR, ( char * ) &optval, sizeof(optval)) == SOCKET_ERROR ) 
    {
    closesocket(Socket);
    g_LogFile.PrintLog("设置socket 重用错误!WSAGetLastError()=%d\n",WSAGetLastError());
    return false;
    }
      

  4.   

    这个只是对于多个socket绑定(bind)到同一个Protocol+IP+Port,为的是防止服务类的应用程序由于异步重启之后无法再次监听在同一端口从而无法及时服务而使用的。对于客户端,特别是在同一个进程当中的多个socket,如果bind到同协议同地址同端口,可能会导致数据包错乱,非同一个进程,那就只有前面启动的程序生效。