int CInConnection::_receiveSimplePacket(std::vector<char>& packet) { _socketTimeOut.tv_sec=10; // 1 second max between successive receive for the same packet _socketTimeOut.tv_usec=0; FD_ZERO(&_socketTheSet); FD_SET(_socketClient,&_socketTheSet); #ifdef _WIN32 int selectResult=select(0,&_socketTheSet,NULL,NULL,&_socketTimeOut); #endif /* _WIN32 */ #if defined (__linux) || defined (__APPLE__) int selectResult=select(_socketClient+1, &_socketTheSet,NULL,NULL,&_socketTimeOut); #endif /* __linux || __APPLE__ */ if (selectResult==1) { //1. Read the header and packet size: char headerAndSize[HEADER_LENGTH]; int totalReceived=0; DWORD startT=getTimeInMs(); while(totalReceived!=HEADER_LENGTH) { int nb=recv(_socketClient,headerAndSize+totalReceived,HEADER_LENGTH-totalReceived,0); if (nb<1) break; totalReceived+=nb; if (getTimeDiffInMs(startT)>SOCKET_TIMEOUT_READ) break; } // 2. Check if the header is consistent: if (totalReceived!=HEADER_LENGTH) return(-2); // Error reading _otherSideIsBigEndian=(((WORD*)headerAndSize)[0]!=1); WORD dataLength=littleEndianShortConversion(((WORD*)headerAndSize)[1],_otherSideIsBigEndian); // 3. Read the data with correct length: packet.clear(); packet.resize(dataLength,0); totalReceived=0; startT=getTimeInMs(); while(totalReceived!=dataLength) { int nb=recv(_socketClient,&packet[0]+totalReceived,dataLength-totalReceived,0); if (nb<1) break; totalReceived+=nb; if (getTimeDiffInMs(startT)>SOCKET_TIMEOUT_READ) break; } if (totalReceived!=dataLength) return(-2); // wrong size or nothing received return(int(littleEndianShortConversion(((WORD*)headerAndSize)[2],_otherSideIsBigEndian))); } if (selectResult==0) return(-1); return(-2); }
int CSimpleInConnection::_receiveSimplePacket(std::vector<char>& packet) { // Returns the number of packets left to read if >=0, -2=error, -1=select time out _socketTimeOut.tv_sec=10; // 1 second max between successive receive for the same packet _socketTimeOut.tv_usec=0; FD_ZERO(&_socketTheSet); FD_SET(_socketClient,&_socketTheSet); #ifdef _WIN32 int selectResult=select(0,&_socketTheSet,NULL,NULL,&_socketTimeOut); #endif /* _WIN32 */ #if defined (__linux) || defined (__APPLE__) int selectResult=select(_socketClient+1, &_socketTheSet,NULL,NULL,&_socketTimeOut); #endif /* __linux || __APPLE__ */ if (selectResult==1) { //1. Read the header and packet size: char headerAndSize[HEADER_LENGTH]; int totalReceived=0; DWORD startT=getTimeInMs(); while(totalReceived!=HEADER_LENGTH) { int nb=recv(_socketClient,headerAndSize+totalReceived,HEADER_LENGTH-totalReceived,0); if (nb<1) break; totalReceived+=nb; if (getTimeDiffInMs(startT)>3000) break; } // 2. Check if the header is consistent: if (totalReceived!=HEADER_LENGTH) return(-2); // Error reading if ( (headerAndSize[0]!=_headerByte1)||(headerAndSize[1]!=_headerByte2) ) return(-2); // Error, wrong header WORD dataLength=((WORD*)(headerAndSize+2))[0]; // 3. Read the data with correct length: packet.clear(); packet.resize(dataLength,0); totalReceived=0; startT=getTimeInMs(); while(totalReceived!=dataLength) { int nb=recv(_socketClient,&packet[0]+totalReceived,dataLength-totalReceived,0); if (nb<1) break; totalReceived+=nb; if (getTimeDiffInMs(startT)>3000) break; } if (totalReceived!=dataLength) return(-2); // wrong size or nothing received return(int(((WORD*)(headerAndSize+2))[1])); } if (selectResult==0) return(-1); return(-2); }
void CSimxSocket::_stop() { // Terminate the communication thread if needed: if (_commThreadLaunched) { connection->stopWaitingForConnection(); _commThreadLaunched=false; // signal the thread we wanna end // First try if we can bring the communication thread to an end: DWORD startT=getTimeInMs(); while (getTimeDiffInMs(startT)<20) { Sleep(1); if (_commThreadEnded) break; // this usually happens when a client was connected and the communication was running } if (!_commThreadEnded) { // no, the communication thread is probably waiting for a connection (blocked while accepting) // Make a fake connection to this socket, to unblock it (the thread might be trapped in the "accept" function) if (_portNb>=0) { // sockets struct hostent *hp; unsigned int addr; struct sockaddr_in _socketServer; #ifdef _WIN32 WSADATA _socketWsaData; if (WSAStartup(0x101,&_socketWsaData)==0) #endif // _WIN32 { _SOCKET _socketConn=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP); if(_socketConn!=INVALID_SOCKET) { addr=inet_addr("127.0.0.1"); hp=gethostbyaddr((char*)&addr,sizeof(addr),AF_INET); if(hp!=NULL) { _socketServer.sin_addr.s_addr=*((unsigned long*)hp->h_addr); _socketServer.sin_family=AF_INET; _socketServer.sin_port=htons(_portNb); connect(_socketConn,(struct sockaddr*)&_socketServer,sizeof(_socketServer)); } #ifdef _WIN32 closesocket(_socketConn); #elif defined (__linux) || defined (__APPLE__) close(_socketConn); #endif // _WIN32 } #ifdef _WIN32 WSACleanup(); #endif // _WIN32 } } // Now wait until the thread signals that it ended (or we reached a timeout: that probably happens when a firewall forbids self-connections) startT=getTimeInMs(); while (getTimeDiffInMs(startT)<1000) { Sleep(1); if (_commThreadEnded) break; // ok, the thread ended } } } // Do some other clean-up: _receivedCommands->clearAll(); _dataToSend->clearAll(); }