#include <socket.h>
Definition at line 77 of file socket.h.
Public Member Functions | |
| void | accept () throw ( SocketException ) |
| Wait for a incoming connection to port_. | |
| void | close () |
| void | connect () throw ( SocketException ) |
| Connects to host_:port_. | |
| bool | has_client_connection () const |
| bool | is_blocking () throw () |
| int | port () |
| std::vector< unsigned char > | receive (int bufSize=2048) throw ( SocketException ) |
| bool | receiveExact (Storage &) throw ( SocketException ) |
| void | send (const std::vector< unsigned char >) throw ( SocketException ) |
| void | sendExact (const Storage &) throw ( SocketException ) |
| void | set_blocking (bool) throw ( SocketException ) |
| void | set_verbose (bool newVerbose) |
| Socket (int port) | |
| Constructor that prepare for accepting a connection on given port. | |
| Socket (std::string host, int port) | |
| Constructor that prepare to connect to host:port. | |
| bool | verbose () |
| ~Socket () | |
| Destructor. | |
Private Member Functions | |
| bool | atoaddr (std::string, struct in_addr &addr) |
| void | BailOnSocketError (std::string) const throw ( SocketException ) |
| bool | datawaiting (int sock) const throw () |
| void | init () |
Private Attributes | |
| bool | blocking_ |
| std::string | host_ |
| int | port_ |
| int | server_socket_ |
| int | socket_ |
| bool | verbose_ |
Friends | |
| class | Response |
| tcpip::Socket::Socket | ( | std::string | host, | |
| int | port | |||
| ) |
| tcpip::Socket::Socket | ( | int | port | ) |
Constructor that prepare for accepting a connection on given port.
Definition at line 83 of file socket.cpp.
References init(), and verbose_.
00084 : host_(""), 00085 port_( port ), 00086 socket_(-1), 00087 server_socket_(-1), 00088 blocking_(true) 00089 { 00090 verbose_ = false; 00091 init(); 00092 }
| tcpip::Socket::~Socket | ( | ) |
Destructor.
Definition at line 114 of file socket.cpp.
References close(), server_socket_, and socket_.
00115 { 00116 // Close first an existing client connection ... 00117 close(); 00118 #ifdef WIN32 00119 instance_count_--; 00120 #endif 00121 00122 // ... then the server socket 00123 if( server_socket_ >= 0 ) 00124 { 00125 #ifdef WIN32 00126 ::closesocket( server_socket_ ); 00127 #else 00128 ::close( server_socket_ ); 00129 #endif 00130 server_socket_ = -1; 00131 } 00132 00133 #ifdef WIN32 00134 if( server_socket_ == -1 && socket_ == -1 00135 && init_windows_sockets_ && instance_count_ == 0 ) 00136 WSACleanup(); 00137 windows_sockets_initialized_ = false; 00138 #endif 00139 }
| void tcpip::Socket::accept | ( | ) | throw ( SocketException ) |
Wait for a incoming connection to port_.
Definition at line 219 of file socket.cpp.
References BailOnSocketError(), blocking_, port_, server_socket_, set_blocking(), and socket_.
00221 { 00222 if( socket_ >= 0 ) 00223 return; 00224 00225 struct sockaddr_in client_addr; 00226 #ifdef WIN32 00227 int addrlen = sizeof(client_addr); 00228 #else 00229 socklen_t addrlen = sizeof(client_addr); 00230 #endif 00231 00232 if( server_socket_ < 0 ) 00233 { 00234 struct sockaddr_in self; 00235 00236 //Create the server socket 00237 server_socket_ = static_cast<int>(socket( AF_INET, SOCK_STREAM, 0 )); 00238 if( server_socket_ < 0 ) 00239 BailOnSocketError("tcpip::Socket::accept() @ socket"); 00240 00241 //"Address already in use" error protection 00242 { 00243 int reuseaddr = 1; 00244 00245 #ifdef WIN32 00246 //setsockopt(server_socket_, SOL_SOCKET, SO_REUSEADDR, (const char*)&reuseaddr, sizeof(reuseaddr)); 00247 // No address reuse in Windows!!! 00248 #else 00249 setsockopt(server_socket_, SOL_SOCKET, SO_REUSEADDR, &reuseaddr, sizeof(reuseaddr)); 00250 #endif 00251 } 00252 00253 // Initialize address/port structure 00254 memset(&self, 0, sizeof(self)); 00255 self.sin_family = AF_INET; 00256 self.sin_port = htons(port_); 00257 self.sin_addr.s_addr = htonl(INADDR_ANY); 00258 00259 // Assign a port number to the socket 00260 if ( bind(server_socket_, (struct sockaddr*)&self, sizeof(self)) != 0 ) 00261 BailOnSocketError("tcpip::Socket::accept() Unable to create listening socket"); 00262 00263 00264 // Make it a "listening socket" 00265 if ( listen(server_socket_, 10) == -1 ) 00266 BailOnSocketError("tcpip::Socket::accept() Unable to listen on server socket"); 00267 00268 // Make the newly created socket blocking or not 00269 set_blocking(blocking_); 00270 } 00271 00272 socket_ = static_cast<int>(::accept(server_socket_, (struct sockaddr*)&client_addr, &addrlen)); 00273 00274 if( socket_ >= 0 ) 00275 { 00276 int x = 1; 00277 setsockopt(socket_, IPPROTO_TCP, TCP_NODELAY, (const char*)&x, sizeof(x)); 00278 } 00279 }
| bool tcpip::Socket::atoaddr | ( | std::string | address, | |
| struct in_addr & | addr | |||
| ) | [private] |
Definition at line 193 of file socket.cpp.
Referenced by connect().
00194 { 00195 struct hostent* host; 00196 struct in_addr saddr; 00197 00198 // First try nnn.nnn.nnn.nnn form 00199 saddr.s_addr = inet_addr(address.c_str()); 00200 if (saddr.s_addr != static_cast<unsigned int>(-1)) 00201 { 00202 addr = saddr; 00203 return true; 00204 } 00205 00206 host = gethostbyname(address.c_str()); 00207 if( host ) { 00208 addr = *((struct in_addr*)host->h_addr_list[0]); 00209 return true; 00210 } 00211 00212 return false; 00213 }
| void tcpip::Socket::BailOnSocketError | ( | std::string | context | ) | const throw ( SocketException ) [private] |
Definition at line 144 of file socket.cpp.
Referenced by accept(), connect(), datawaiting(), init(), receive(), receiveExact(), send(), and set_blocking().
00146 { 00147 #ifdef WIN32 00148 int e = WSAGetLastError(); 00149 std::string msg = GetWinsockErrorString( e ); 00150 #else 00151 std::string msg = strerror( errno ); 00152 #endif 00153 throw SocketException( context + ": " + msg ); 00154 }
| void tcpip::Socket::close | ( | ) |
Definition at line 343 of file socket.cpp.
References socket_.
Referenced by testclient::TraCITestClient::close(), OutputDevice_Network::~OutputDevice_Network(), and ~Socket().
00344 { 00345 // Close client-connection 00346 if( socket_ >= 0 ) 00347 { 00348 #ifdef WIN32 00349 ::closesocket( socket_ ); 00350 #else 00351 ::close( socket_ ); 00352 #endif 00353 00354 socket_ = -1; 00355 } 00356 }
| void tcpip::Socket::connect | ( | ) | throw ( SocketException ) |
Connects to host_:port_.
Definition at line 312 of file socket.cpp.
References atoaddr(), BailOnSocketError(), host_, port_, and socket_.
Referenced by testclient::TraCITestClient::connect(), and receive().
00314 { 00315 in_addr addr; 00316 if( !atoaddr( host_.c_str(), addr) ) 00317 BailOnSocketError("tcpip::Socket::connect() @ Invalid network address"); 00318 00319 sockaddr_in address; 00320 memset( (char*)&address, 0, sizeof(address) ); 00321 address.sin_family = AF_INET; 00322 address.sin_port = htons( port_ ); 00323 address.sin_addr.s_addr = addr.s_addr; 00324 00325 socket_ = static_cast<int>(socket( PF_INET, SOCK_STREAM, 0 )); 00326 if( socket_ < 0 ) 00327 BailOnSocketError("tcpip::Socket::connect() @ socket"); 00328 00329 if( ::connect( socket_, (sockaddr const*)&address, sizeof(address) ) < 0 ) 00330 BailOnSocketError("tcpip::Socket::connect() @ connect"); 00331 00332 if( socket_ >= 0 ) 00333 { 00334 int x = 1; 00335 setsockopt(socket_, IPPROTO_TCP, TCP_NODELAY, (const char*)&x, sizeof(x)); 00336 } 00337 00338 }
| bool tcpip::Socket::datawaiting | ( | int | sock | ) | const throw () [private] |
Definition at line 168 of file socket.cpp.
References BailOnSocketError().
Referenced by receive().
00170 { 00171 fd_set fds; 00172 FD_ZERO( &fds ); 00173 FD_SET( sock, &fds ); 00174 00175 struct timeval tv; 00176 tv.tv_sec = 0; 00177 tv.tv_usec = 0; 00178 00179 int r = select( sock+1, &fds, NULL, NULL, &tv); 00180 00181 if (r < 0) 00182 BailOnSocketError("tcpip::Socket::datawaiting @ select"); 00183 00184 if( FD_ISSET( sock, &fds ) ) 00185 return true; 00186 else 00187 return false; 00188 }
| bool tcpip::Socket::has_client_connection | ( | ) | const |
Definition at line 545 of file socket.cpp.
References socket_.
00547 { 00548 return socket_ >= 0; 00549 }
| void tcpip::Socket::init | ( | ) | [private] |
Definition at line 97 of file socket.cpp.
References BailOnSocketError().
Referenced by Socket().
00098 { 00099 #ifdef WIN32 00100 instance_count_++; 00101 00102 if( init_windows_sockets_ && !windows_sockets_initialized_ ) 00103 { 00104 WSAData wsaData; 00105 if( WSAStartup(MAKEWORD(1, 1), &wsaData) != 0 ) 00106 BailOnSocketError("Unable to init WSA Sockets"); 00107 windows_sockets_initialized_ = true; 00108 } 00109 #endif 00110 }
| bool tcpip::Socket::is_blocking | ( | ) | throw () |
Definition at line 554 of file socket.cpp.
References blocking_.
00556 { 00557 return blocking_; 00558 }
| int tcpip::Socket::port | ( | ) |
| vector< unsigned char > tcpip::Socket::receive | ( | int | bufSize = 2048 |
) | throw ( SocketException ) |
Definition at line 430 of file socket.cpp.
References BailOnSocketError(), connect(), datawaiting(), socket_, and verbose_.
00432 { 00433 vector<unsigned char> b; 00434 00435 if( socket_ < 0 ) 00436 connect(); 00437 00438 if( !datawaiting( socket_) ) 00439 return b; 00440 00441 unsigned char const * const buf = new unsigned char[bufSize]; 00442 int a = recv( socket_, (char*)buf, bufSize, 0 ); 00443 00444 if( a <= 0 ) 00445 { 00446 // BailOnSocketError definitely throws an exception so clear up heap 00447 delete[] buf; 00448 BailOnSocketError( "tcpip::Socket::receive() @ recv" ); 00449 } 00450 00451 b.resize(a); 00452 for(int i = 0; i < a; ++i) 00453 { 00454 b[i] = buf[i]; 00455 } 00456 00457 if (verbose_) 00458 { 00459 cerr << "Rcvd " << a << " bytes via tcpip::Socket: ["; 00460 for(int i = 0; i < a; ++i) 00461 { 00462 cerr << " " << (int)b[i] << " "; 00463 } 00464 cerr << "]" << endl; 00465 } 00466 00467 delete[] buf; 00468 return b; 00469 }
| bool tcpip::Socket::receiveExact | ( | Storage & | msg | ) | throw ( SocketException ) |
Definition at line 476 of file socket.cpp.
References BailOnSocketError(), tcpip::Storage::readInt(), socket_, and verbose_.
Referenced by testclient::TraCITestClient::commandChangeLane(), testclient::TraCITestClient::commandChangeRoute(), testclient::TraCITestClient::commandChangeTarget(), testclient::TraCITestClient::commandClose(), testclient::TraCITestClient::commandDistanceRequest(), testclient::TraCITestClient::commandGetTLStatus(), testclient::TraCITestClient::commandGetVariable(), testclient::TraCITestClient::commandGetVariablePlus(), testclient::TraCITestClient::commandPositionConversion(), testclient::TraCITestClient::commandScenario(), testclient::TraCITestClient::commandSetMaximumSpeed(), testclient::TraCITestClient::commandSetValue(), testclient::TraCITestClient::commandSimulationStep(), testclient::TraCITestClient::commandSimulationStep2(), testclient::TraCITestClient::commandSlowDown(), testclient::TraCITestClient::commandStopNode(), and testclient::TraCITestClient::commandSubscribeVariable().
00478 { 00479 /* receive length of vector */ 00480 unsigned char * const bufLength = new unsigned char[4]; 00481 int bytesRead = 0; 00482 int readThisTime = 0; 00483 00484 while (bytesRead<4) 00485 { 00486 readThisTime = recv( socket_, (char*)(bufLength + bytesRead), 4-bytesRead, 0 ); 00487 00488 if( readThisTime <= 0 ) 00489 { 00490 // BailOnSocketError definitely throws an exception so clear up heap 00491 delete[] bufLength; 00492 BailOnSocketError( "tcpip::Socket::receive() @ recv" ); 00493 } 00494 00495 bytesRead += readThisTime; 00496 } 00497 Storage length_storage(bufLength,4); 00498 int NN = length_storage.readInt() - 4; 00499 00500 /* receive vector */ 00501 unsigned char * const buf = new unsigned char[NN]; 00502 bytesRead = 0; 00503 readThisTime = 0; 00504 00505 while (bytesRead<NN) 00506 { 00507 readThisTime = recv( socket_, (char*)(buf + bytesRead), NN-bytesRead, 0 ); 00508 00509 if( readThisTime <= 0 ) 00510 { 00511 // BailOnSocketError definitely throws an exception so clear up heap 00512 delete[] bufLength; 00513 delete[] buf; 00514 BailOnSocketError( "tcpip::Socket::receive() @ recv" ); 00515 } 00516 00517 bytesRead += readThisTime; 00518 } 00519 msg.reset(); 00520 msg.writePacket(buf, NN); 00521 00522 if (verbose_) 00523 { 00524 cerr << "Rcvd Storage with " << 4 + NN << " bytes via tcpip::Socket: ["; 00525 for (int i=0; i < 4; ++i) 00526 { 00527 cerr << " " << (int)bufLength[i] << " "; 00528 } 00529 for (int i=0; i < NN; ++i) 00530 { 00531 cerr << " " << (int)buf[i] << " "; 00532 } 00533 cerr << "]" << endl; 00534 } 00535 00536 delete[] buf; 00537 delete[] bufLength; 00538 return true; 00539 }
| void tcpip::Socket::send | ( | const std::vector< unsigned char > | b | ) | throw ( SocketException ) |
Definition at line 361 of file socket.cpp.
References BailOnSocketError(), socket_, and verbose_.
Referenced by OutputDevice_Network::postWriteHook(), and sendExact().
00363 { 00364 if( socket_ < 0 ) return; 00365 00366 size_t numbytes = b.size(); 00367 unsigned char *const buf = new unsigned char[numbytes]; 00368 00369 for(size_t i = 0; i < numbytes; ++i) 00370 { 00371 buf[i] = b[i]; 00372 } 00373 00374 if (verbose_) 00375 { 00376 cerr << "Send " << numbytes << " bytes via tcpip::Socket: ["; 00377 for(size_t i = 0; i < numbytes; ++i) 00378 { 00379 buf[i] = b[i]; 00380 cerr << " " << (int)b[i] << " "; 00381 } 00382 cerr << "]" << endl; 00383 } 00384 00385 unsigned char const *buf_ptr = buf; 00386 while( numbytes > 0 ) 00387 { 00388 #ifdef WIN32 00389 int n = ::send( socket_, (const char*)buf_ptr, static_cast<int>(numbytes), 0 ); 00390 #else 00391 int n = ::send( socket_, buf_ptr, numbytes, 0 ); 00392 #endif 00393 if( n<0 ) 00394 { 00395 // BailOnSocketError definitely throws an exception so clear up heap 00396 delete[] buf; 00397 BailOnSocketError( "send failed" ); 00398 } 00399 00400 numbytes -= n; 00401 buf_ptr += n; 00402 } 00403 00404 delete[] buf; 00405 }
| void tcpip::Socket::sendExact | ( | const Storage & | b | ) | throw ( SocketException ) |
Definition at line 413 of file socket.cpp.
References tcpip::Storage::begin(), tcpip::Storage::end(), send(), and tcpip::Storage::writeInt().
Referenced by testclient::TraCITestClient::commandChangeLane(), testclient::TraCITestClient::commandChangeRoute(), testclient::TraCITestClient::commandChangeTarget(), testclient::TraCITestClient::commandClose(), testclient::TraCITestClient::commandDistanceRequest(), testclient::TraCITestClient::commandGetTLStatus(), testclient::TraCITestClient::commandGetVariable(), testclient::TraCITestClient::commandGetVariablePlus(), testclient::TraCITestClient::commandPositionConversion(), testclient::TraCITestClient::commandScenario(), testclient::TraCITestClient::commandSetMaximumSpeed(), testclient::TraCITestClient::commandSetValue(), testclient::TraCITestClient::commandSimulationStep(), testclient::TraCITestClient::commandSimulationStep2(), testclient::TraCITestClient::commandSlowDown(), testclient::TraCITestClient::commandStopNode(), and testclient::TraCITestClient::commandSubscribeVariable().
00415 { 00416 int length = static_cast<int>(b.size()); 00417 Storage length_storage; 00418 length_storage.writeInt(length + 4); 00419 vector<unsigned char> msg; 00420 msg.insert(msg.end(), length_storage.begin(), length_storage.end()); 00421 msg.insert(msg.end(), b.begin(), b.end()); 00422 send(msg); 00423 }
| void tcpip::Socket::set_blocking | ( | bool | blocking | ) | throw ( SocketException ) |
Definition at line 284 of file socket.cpp.
References BailOnSocketError(), blocking_, and server_socket_.
Referenced by accept().
00286 { 00287 blocking_ = blocking; 00288 00289 if( server_socket_ > 0 ) 00290 { 00291 #ifdef WIN32 00292 ULONG NonBlock = blocking_ ? 0 : 1; 00293 if (ioctlsocket(server_socket_, FIONBIO, &NonBlock) == SOCKET_ERROR) 00294 BailOnSocketError("tcpip::Socket::set_blocking() Unable to initialize non blocking I/O"); 00295 #else 00296 long arg = fcntl(server_socket_, F_GETFL, NULL); 00297 if (blocking_) 00298 { 00299 arg &= ~O_NONBLOCK; 00300 } else { 00301 arg |= O_NONBLOCK; 00302 } 00303 fcntl(server_socket_, F_SETFL, arg); 00304 #endif 00305 } 00306 00307 }
| void tcpip::Socket::set_verbose | ( | bool | newVerbose | ) | [inline] |
| bool tcpip::Socket::verbose | ( | ) | [inline] |
bool tcpip::Socket::blocking_ [private] |
std::string tcpip::Socket::host_ [private] |
int tcpip::Socket::port_ [private] |
int tcpip::Socket::server_socket_ [private] |
int tcpip::Socket::socket_ [private] |
Definition at line 121 of file socket.h.
Referenced by accept(), close(), connect(), has_client_connection(), receive(), receiveExact(), send(), and ~Socket().
bool tcpip::Socket::verbose_ [private] |
Definition at line 125 of file socket.h.
Referenced by receive(), receiveExact(), send(), set_verbose(), Socket(), and verbose().
1.5.6