34 #include <sys/types.h>
35 #include <sys/socket.h>
36 #include <netinet/in.h>
37 #include <arpa/inet.h>
40 #include <netinet/tcp.h>
55 #include <arpa/inet.h>
59 using std::istringstream ;
73 string err(
"Socket is already listening" ) ;
79 string err(
"Socket is already connected" ) ;
86 struct protoent *pProtoEnt ;
87 struct sockaddr_in sin ;
90 if( isdigit( _host[0] ) )
92 if( ( address = inet_addr( _host.c_str() ) ) == -1 )
94 string err(
"Invalid host ip address " ) ;
98 sin.sin_addr.s_addr = address ;
99 sin.sin_family = AF_INET ;
103 if( ( ph = gethostbyname( _host.c_str() ) ) == NULL )
109 string err(
"No such host " ) ;
115 string err(
"Host " ) ;
116 err += _host +
" is busy, try again later" ;
121 string err(
"DNS error for host " ) ;
127 string err(
"No IP address for host " ) ;
139 sin.sin_family = ph->h_addrtype ;
140 for(
char **p =ph->h_addr_list; *p != NULL; p++ )
143 (void)memcpy( &in.s_addr, *p,
sizeof( in.s_addr ) ) ;
144 memcpy( (
char*)&sin.sin_addr, (
char*)&in,
sizeof( in ) ) ;
149 sin.sin_port = htons( _portVal ) ;
150 pProtoEnt = getprotobyname(
"tcp" ) ;
153 string err(
"Error retreiving tcp protocol information" ) ;
158 int descript = socket( AF_INET, SOCK_STREAM, pProtoEnt->p_proto ) ;
170 string err(
"getting socket descriptor: ");
171 const char* error_info = strerror(errno);
173 err += (string)error_info;
180 holder = fcntl(
_socket, F_GETFL, NULL);
181 holder = holder | O_NONBLOCK;
182 fcntl(
_socket, F_SETFL, holder);
185 setTcpRecvBufferSize( ) ;
186 setTcpSendBufferSize( ) ;
188 int res =
::connect( descript, (
struct sockaddr*)&sin,
sizeof( sin ) );
193 if(errno == EINPROGRESS) {
196 struct timeval timeout ;
205 if( select( maxfd+1, NULL, &write_fd, NULL, &timeout) < 0 ) {
208 holder = fcntl(
_socket, F_GETFL, NULL);
209 holder = holder & (~O_NONBLOCK);
210 fcntl(
_socket, F_SETFL, holder);
213 string err(
"selecting sockets: " ) ;
214 const char *error_info = strerror( errno ) ;
216 err += (string)error_info ;
227 getsockopt(
_socket, SOL_SOCKET, SO_ERROR, (
void*) &valopt, &lon);
233 holder = fcntl(
_socket, F_GETFL, NULL);
234 holder = holder & (~O_NONBLOCK);
235 fcntl(
_socket, F_SETFL, holder);
238 string err(
"Did not successfully connect to server\n");
239 err +=
"Server may be down or you may be trying on the wrong port";
246 holder = fcntl(
_socket, F_GETFL, NULL);
247 holder = holder & (~O_NONBLOCK);
248 fcntl(
_socket, F_SETFL, holder);
259 holder = fcntl(
_socket, F_GETFL, NULL);
260 holder = holder & (~O_NONBLOCK);
261 fcntl(
_socket, F_SETFL, holder);
264 string err(
"socket connect: ");
265 const char* error_info = strerror(errno);
267 err += (string)error_info;
277 holder = fcntl(
_socket, F_GETFL, NULL);
278 holder = holder & (~O_NONBLOCK);
279 fcntl(
_socket, F_SETFL, holder);
290 string err(
"Socket is already connected" ) ;
296 string err(
"Socket is already listening" ) ;
301 struct sockaddr_in server ;
302 server.sin_family = AF_INET ;
303 server.sin_addr.s_addr = INADDR_ANY ;
304 struct servent *sir = 0 ;
305 BESDEBUG(
"ppt",
"Checking /etc/services for port "
306 << _portVal << endl ) ;
308 sir = getservbyport(htons(_portVal), 0);
311 std::ostringstream error_oss;
312 error_oss << endl <<
"CONFIGURATION ERROR: The requested port (" << _portVal <<
") appears in the system services list. ";
313 error_oss <<
"Port " << _portVal <<
" is assigned to the service '" << sir->s_name << (string)
"'" ;
315 if(sir->s_aliases[0]!=0){
316 error_oss <<
" which may also be known as: ";
317 for(
int i=0; sir->s_aliases[i]!=0 ;i++) {
321 error_oss << sir->s_aliases[i] ;
330 server.sin_port = htons( _portVal ) ;
331 _socket = socket( AF_INET, SOCK_STREAM, 0 ) ;
335 if( setsockopt(
_socket, SOL_SOCKET, SO_REUSEADDR,
336 (
char*)&on,
sizeof( on ) ) )
338 std::ostringstream errMsg;
339 errMsg << endl <<
"ERROR: Failed to set SO_REUSEADDR on TCP socket";
340 const char* error_info = strerror( errno ) ;
342 errMsg <<
". Msg:: " <<error_info ;
347 BESDEBUG(
"besdaemon",
"About to bind to port: " << _portVal <<
" in process: " << getpid() << endl);
349 if( bind(
_socket, (
struct sockaddr*)&server,
sizeof server) != -1 )
351 int length =
sizeof( server ) ;
352 #ifdef _GETSOCKNAME_USES_SOCKLEN_T
353 if( getsockname(
_socket, (
struct sockaddr *)&server,
354 (socklen_t *)&length ) == -1 )
356 if( getsockname(
_socket, (
struct sockaddr *)&server,
360 string error(
"getting socket name" ) ;
361 const char* error_info = strerror( errno ) ;
363 error +=
" " + (string)error_info ;
369 setTcpRecvBufferSize( ) ;
370 setTcpSendBufferSize( ) ;
378 string error(
"could not listen TCP socket" ) ;
379 const char* error_info = strerror( errno ) ;
381 error +=
" " + (string)error_info ;
387 std::ostringstream error_msg;
388 error_msg << endl <<
"ERROR: Failed to bind TCP socket: "<< _portVal ;
389 const char* error_info = strerror( errno ) ;
391 error_msg <<
": " << error_info ;
398 std::ostringstream error_oss;
399 error_oss << endl <<
"ERROR: Failed to create socket for port "<< _portVal << endl;
400 const char *error_info = strerror( errno ) ;
402 error_oss <<
" " << (string)error_info ;
426 TcpSocket::setTcpRecvBufferSize()
428 if( !_haveRecvBufferSize )
443 if( setit ==
"Yes" || setit ==
"yes" || setit ==
"Yes" )
449 istringstream sizestrm( sizestr ) ;
450 unsigned int sizenum = 0 ;
451 sizestrm >> sizenum ;
454 string err =
"Socket Recv Size malformed: " + sizestr ;
459 int err = setsockopt(
_socket, SOL_SOCKET, SO_RCVBUF,
460 (
char *)&sizenum, (socklen_t)
sizeof(sizenum) ) ;
461 int myerrno = errno ;
464 char *serr = strerror( myerrno ) ;
465 string err =
"Failed to set the socket receive buffer size: " ;
469 err +=
"unknow error occurred" ;
473 BESDEBUG(
"ppt",
"Tcp receive buffer size set to "
474 << (
unsigned long)sizenum << endl ) ;
498 TcpSocket::setTcpSendBufferSize()
501 vector<string> vals ;
513 if( setit ==
"Yes" || setit ==
"yes" || setit ==
"Yes" )
526 istringstream sizestrm( sizestr ) ;
527 unsigned int sizenum = 0 ;
528 sizestrm >> sizenum ;
531 string err =
"Socket Send Size malformed: " + sizestr ;
536 int err = setsockopt(
_socket, SOL_SOCKET, SO_SNDBUF,
537 (
char *)&sizenum, (socklen_t)
sizeof(sizenum) ) ;
538 int myerrno = errno ;
541 char *serr = strerror( myerrno ) ;
542 string err =
"Failed to set the socket send buffer size: " ;
546 err +=
"unknow error occurred" ;
550 BESDEBUG(
"ppt",
"Tcp send buffer size set to "
551 << (
unsigned long)sizenum << endl ) ;
566 if( !_haveRecvBufferSize )
569 unsigned int sizenum = 0 ;
570 socklen_t sizelen =
sizeof(sizenum) ;
571 int err = getsockopt(
_socket, SOL_SOCKET, SO_RCVBUF,
572 (
char *)&sizenum, (socklen_t *)&sizelen ) ;
573 int myerrno = errno ;
576 char *serr = strerror( myerrno ) ;
577 string err =
"Failed to get the socket receive buffer size: " ;
581 err +=
"unknow error occurred" ;
585 BESDEBUG(
"ppt",
"Tcp receive buffer size is "
586 << (
unsigned long)sizenum << endl ) ;
588 _haveRecvBufferSize = true ;
589 _recvBufferSize = sizenum ;
591 return _recvBufferSize ;
605 if( !_haveSendBufferSize )
608 unsigned int sizenum = 0 ;
609 socklen_t sizelen =
sizeof(sizenum) ;
610 int err = getsockopt(
_socket, SOL_SOCKET, SO_SNDBUF,
611 (
char *)&sizenum, (socklen_t *)&sizelen ) ;
612 int myerrno = errno ;
615 char *serr = strerror( myerrno ) ;
616 string err =
"Failed to get the socket send buffer size: " ;
620 err +=
"unknow error occurred" ;
624 BESDEBUG(
"ppt",
"Tcp send buffer size is "
625 << (
unsigned long)sizenum << endl ) ;
627 _haveSendBufferSize = true ;
628 _sendBufferSize = sizenum ;
630 return _sendBufferSize ;
642 struct request_info req ;
643 request_init( &req, RQ_DAEMON,
"besdaemon", RQ_FILE,
647 if( STR_EQ( eval_hostname(), paranoid ) && hosts_access() )
666 << (
void *)
this <<
")" << endl ;
670 strm <<
BESIndent::LMarg <<
"have recv buffer size: " << _haveRecvBufferSize
674 strm <<
BESIndent::LMarg <<
"have send buffer size: " << _haveSendBufferSize
virtual unsigned int getRecvBufferSize()
get the tcp receive buffer size using getsockopt
exception thrown if an internal error is found and is fatal to the BES
exception thrown if inernal error encountered
virtual void dump(ostream &strm) const
dumps information about this object
virtual string get_file()
get the file name where the exception was thrown
virtual string get_message()
get the error message for this exception
Abstract exception class for the BES with basic string message.
virtual unsigned int getSendBufferSize()
get the tcp send buffer size using getsockopt
static ostream & LMarg(ostream &strm)
virtual int getSocketDescriptor()
void get_value(const string &s, string &val, bool &found)
Retrieve the value of a given key, if set.
#define BESDEBUG(x, y)
macro used to send debug information to the debug stream
static BESKeys * TheKeys()
virtual void dump(ostream &strm) const
dumps information about this object
virtual bool allowConnection()
is there any wrapper code for unix sockets
virtual int get_line()
get the line number where the exception was thrown