监听线程代码如下 void ListenThread::threadProc() { if (getState()!=xThread::THREAD_RUN) { XLOG("[%s]listener is not in running state %u", pServer->serverName, getState()); return; } XLOG("[%s]listener start", pServer->serverName); SOCKADDR_IN clientAddr; int addrLen = sizeof(clientAddr); WSAEVENT acceptEvent = WSACreateEvent(); if (acceptEvent == WSA_INVALID_EVENT ) { XERR("[%s]listener WSACreateEvent failed", pServer->serverName); stop(); } if (getState()==xThread::THREAD_RUN) { int nRet = WSAEventSelect(pServer->sock,acceptEvent,FD_ACCEPT); if (nRet == SOCKET_ERROR) { XERR("[%s]listener WSACreateEvent failed", pServer->serverName); stop(); } } while (getState()==xThread::THREAD_RUN) { WSAResetEvent(acceptEvent); DWORD dwRet = WSAWaitForMultipleEvents(1, &acceptEvent, false, 1, false); if (dwRet == WSA_WAIT_TIMEOUT) continue; WSANETWORKEVENTS events; //查看发生的网络事件 int nRet = WSAEnumNetworkEvents(pServer->sock, acceptEvent, &events); if (nRet == SOCKET_ERROR) { XERR("[%s]listener WSAEnumNetworkEvents failed with ret %d", pServer->serverName, nRet); stop(); break; } if (events.lNetworkEvents & FD_ACCEPT) //发生FD_ACCEPT网络事件 { if ( events.iErrorCode[FD_ACCEPT_BIT] == 0) { int sAccept=WSAAccept(pServer->sock, (SOCKADDR*)&clientAddr, &addrLen,0,0); if (INVALID_SOCKET==sAccept) continue; pServer->accept(sAccept, clientAddr); } } Sleep(30); } setState(xThread::THREAD_STOP); XLOG("[%s]listener stopped", pServer->serverName); WSACloseEvent(acceptEvent); } 启动时运行很好,但是大概几十次以后,就一直TIMEOUT 奇怪的是,客户端::connect是成功的,发送消息也成功 但是服务器收不到 ---------------------------------------------------------------------- 我试过了WSA_INFINITE就没有问题,可以接收到所有连接 while (getState()==xThread::THREAD_RUN) { WSAResetEvent(acceptEvent); DWORD dwRet = WSAWaitForMultipleEvents(1, &acceptEvent, false, 1, false); if (dwRet == WSA_WAIT_TIMEOUT) continue; 在这段代码反复循环过程中会漏掉网络事件? 我觉得不可能, WSA_INFINITE 还是不行 我用4个客户端反复连接,一段时间后,就再也收不到了非常郁闷 ------------------------------------------------ 唉额滴神啊,终于搞定了 原来if (events.lNetworkEvents & FD_ACCEPT) //发生FD_ACCEPT网络事件 触发的时候可能有多个连接在等待,要循环accept多次,直到返回-1 if ( events.iErrorCode[FD_ACCEPT_BIT] == 0) { int sAccept = -1; int count = 0; while ((sAccept = WSAAccept(pServer->sock, (SOCKADDR*)&clientAddr, &addrLen,0,0))!=INVALID_SOCKET) { if (getState()==xThread::THREAD_RUN) pServer->accept(sAccept, clientAddr); else SAFE_CLOSE_SOCKET(sAccept); count++; } if (0==count) { XERR("[listener]WSAAccept failed with error %d", WSAGetLastError()); break; } } else XERR("[listener]iErrorCode[FD_ACCEPT_BIT]"); |
|