Здравствуйте! По задумке, после соединения с сервером создаётся поток, в котором происходит ожидание данных от сервера.
Соединение происходит нормально, но после начала цикла ожидания данных мой комп начинает глючить (100% CPU).
Что делать?
я полагаю, что ошибка в функции OnReceive:
| Код | virtual void OnReceive( void ) { /* Получение данных */ fd_set set;
while (1) { FD_ZERO(&set); FD_SET(m_sBase, &set);
if ( select(0, &set, NULL, NULL, 0) > 0 ) { if ( FD_ISSET(m_sBase, &set) ) { int c = recv(m_sBase, (char*)pRecvBuf, Pack, 0);
if ( c > 0 ) { pRecvBuf[c] = NULL; MessageBox(0, (LPSTR)pRecvBuf, 0, 0); } } } else OnException(E_FUNC_SELECT_); } }
|
но на всякий случай полный код клиента:
| Код | #ifndef _CLIENT_H_ #define _CLIENT_H_
#if defined (_MSC_VER) && (_MSC_VER >= 1020) #pragma once #endif
#define CLIENT_VER 1.0
#include <winsock.h> #include <memory.h>
// возможные исключения: #define E_FUNC_SOCKET_ 0 #define E_FUNC_ASYNC_ 1 #define E_FUNC_THREAD_ 2 #define E_FUNC_SELECT_ 3 #define E_FUNC_ADDRESS_ 4
////////////////////////////////////////////////// // // // Асинхронный TCP/IP Клиент (v1.0) // // // //////////////////////////////////////////////////
DWORD WINAPI ReceiveThread_TCP( LPVOID pTCPClient );
class CTCPClient { friend DWORD WINAPI ReceiveThread_TCP( LPVOID pTCPClient ); private: SOCKET m_sBase; // сокет клиента BOOL m_bActive; // true: запущен | false: остановлен HANDLE m_hThrd; // главный поток protected: virtual void OnException( u_long Ecode ) { /* [event] Исключение */ char *Emap[] = { "Неудаётся создать сокет", "Неудаётся перейти в асинхронный режим", "Ошибка создания потока", "Ошибка функции select", "Неверный адрес сервера" }; // сообщение об ошибке: MessageBox(0, Emap[Ecode], "TCP/IP Client Exception", MB_ICONERROR);
if ( m_bActive ) Disconnect(); } virtual void OnReceive( void ) { /* [event] Получение данных */ fd_set set;
while (1) { FD_ZERO(&set); FD_SET(m_sBase, &set);
if ( select(0, &set, NULL, NULL, 0) > 0 ) { if ( FD_ISSET(m_sBase, &set) ) { int c = recv(m_sBase, (char*)pRecvBuf, Pack, 0);
if ( c > 0 ) { pRecvBuf[c] = NULL; MessageBox(0, (LPSTR)pRecvBuf, 0, 0); } } } else OnException(E_FUNC_SELECT_); } } public: u_short Pack; timeval TimeOut; // максимальное время ожидания
byte *pRecvBuf; // буффер получаемых данных byte *pSendBuf; // буффер отправляемый данных // -------------------------------------------- bool Connect( LPCSTR Address, u_short Port ) { /* Соединение */ // создание асинхронного сокета: m_sBase = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); if ( m_sBase == SOCKET_ERROR ) { OnException(E_FUNC_SOCKET_); return FALSE; }
u_long state = true;
if ( ioctlsocket(m_sBase, FIONBIO, &state) != 0 ) { OnException(E_FUNC_ASYNC_); return FALSE; }
// адрес: sockaddr_in server_address; server_address.sin_family = AF_INET; server_address.sin_addr.s_addr = inet_addr(Address); server_address.sin_port = htons(Port); memset(server_address.sin_zero, 0, 8); if ( server_address.sin_addr.s_addr == INADDR_NONE ) { hostent *pHost = NULL; pHost = gethostbyname(Address);
if ( pHost == NULL ) { OnException(E_FUNC_ADDRESS_); return FALSE; } else memcpy(&server_address.sin_addr, pHost->h_addr_list[0], pHost->h_length); }
// соединение: fd_set set;
FD_ZERO(&set); FD_SET(m_sBase, &set); connect(m_sBase, (sockaddr*)&server_address, sizeof(server_address));
if ( select(0, &set, NULL, NULL, &TimeOut) != SOCKET_ERROR ) { if ( FD_ISSET(m_sBase, &set) ) { // создание главного потока: DWORD dwThreadID;
m_hThrd = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)&ReceiveThread_TCP, this, 0, &dwThreadID);
if ( m_hThrd == NULL ) OnException(E_FUNC_THREAD_); else m_bActive = TRUE; } else Disconnect(); } else OnException(E_FUNC_SELECT_);
return m_bActive; } void Disconnect( void ) { /* Разрыв соединения */ if ( m_sBase != INVALID_SOCKET ) { if ( m_hThrd != NULL ) { TerminateThread(m_hThrd, 0); CloseHandle(m_hThrd); m_hThrd = NULL; } u_long state = false; ioctlsocket(m_sBase, FIONBIO, &state); closesocket(m_sBase); m_sBase = INVALID_SOCKET; m_bActive = FALSE; } } bool IsConnected( void ) { return m_bActive; } // -------------------------------------------- CTCPClient( void ) { m_bActive = FALSE; m_sBase = INVALID_SOCKET; TimeOut.tv_sec = 1; TimeOut.tv_usec = 0; m_hThrd = NULL; Pack = 32;
pRecvBuf = new BYTE[Pack]; pSendBuf = new BYTE[Pack]; } ~CTCPClient( void ) { Disconnect();
delete [] pRecvBuf; delete [] pSendBuf; } };
DWORD WINAPI ReceiveThread_TCP( LPVOID pTCPClient ) { ((CTCPClient*)pTCPClient)->OnReceive();
return 0; }
#endif
|
Зараннее спасибо.... |