2003-08-13 05:53:07 +04:00
/*
Unix SMB / CIFS implementation .
Samba utility functions
Copyright ( C ) Andrew Tridgell 1992 - 1998
Copyright ( C ) Tim Potter 2000 - 2001
This program is free software ; you can redistribute it and / or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation ; either version 2 of the License , or
( at your option ) any later version .
This program is distributed in the hope that it will be useful ,
but WITHOUT ANY WARRANTY ; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
GNU General Public License for more details .
You should have received a copy of the GNU General Public License
along with this program ; if not , write to the Free Software
Foundation , Inc . , 675 Mass Ave , Cambridge , MA 0213 9 , USA .
*/
# include "includes.h"
2004-11-02 01:48:25 +03:00
# include "system/network.h"
2003-08-13 05:53:07 +04:00
enum SOCK_OPT_TYPES { OPT_BOOL , OPT_INT , OPT_ON } ;
2005-09-27 15:10:57 +04:00
static const struct {
2003-08-13 05:53:07 +04:00
const char * name ;
int level ;
int option ;
int value ;
int opttype ;
2005-09-27 15:10:57 +04:00
} socket_options [ ] = {
2003-08-13 05:53:07 +04:00
{ " SO_KEEPALIVE " , SOL_SOCKET , SO_KEEPALIVE , 0 , OPT_BOOL } ,
{ " SO_REUSEADDR " , SOL_SOCKET , SO_REUSEADDR , 0 , OPT_BOOL } ,
{ " SO_BROADCAST " , SOL_SOCKET , SO_BROADCAST , 0 , OPT_BOOL } ,
# ifdef TCP_NODELAY
{ " TCP_NODELAY " , IPPROTO_TCP , TCP_NODELAY , 0 , OPT_BOOL } ,
# endif
# ifdef IPTOS_LOWDELAY
{ " IPTOS_LOWDELAY " , IPPROTO_IP , IP_TOS , IPTOS_LOWDELAY , OPT_ON } ,
# endif
# ifdef IPTOS_THROUGHPUT
{ " IPTOS_THROUGHPUT " , IPPROTO_IP , IP_TOS , IPTOS_THROUGHPUT , OPT_ON } ,
# endif
# ifdef SO_REUSEPORT
{ " SO_REUSEPORT " , SOL_SOCKET , SO_REUSEPORT , 0 , OPT_BOOL } ,
# endif
# ifdef SO_SNDBUF
{ " SO_SNDBUF " , SOL_SOCKET , SO_SNDBUF , 0 , OPT_INT } ,
# endif
# ifdef SO_RCVBUF
{ " SO_RCVBUF " , SOL_SOCKET , SO_RCVBUF , 0 , OPT_INT } ,
# endif
# ifdef SO_SNDLOWAT
{ " SO_SNDLOWAT " , SOL_SOCKET , SO_SNDLOWAT , 0 , OPT_INT } ,
# endif
# ifdef SO_RCVLOWAT
{ " SO_RCVLOWAT " , SOL_SOCKET , SO_RCVLOWAT , 0 , OPT_INT } ,
# endif
# ifdef SO_SNDTIMEO
{ " SO_SNDTIMEO " , SOL_SOCKET , SO_SNDTIMEO , 0 , OPT_INT } ,
# endif
# ifdef SO_RCVTIMEO
{ " SO_RCVTIMEO " , SOL_SOCKET , SO_RCVTIMEO , 0 , OPT_INT } ,
# endif
{ NULL , 0 , 0 , 0 , 0 } } ;
/****************************************************************************
Set user socket options .
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
void set_socket_options ( int fd , const char * options )
{
2005-09-27 15:10:57 +04:00
const char * * options_list = str_list_make ( NULL , options , " \t , " ) ;
int j ;
2003-08-13 05:53:07 +04:00
2005-09-27 15:10:57 +04:00
for ( j = 0 ; options_list [ j ] ; j + + ) {
const char * tok = options_list [ j ] ;
2003-08-13 05:53:07 +04:00
int ret = 0 , i ;
int value = 1 ;
char * p ;
BOOL got_value = False ;
if ( ( p = strchr_m ( tok , ' = ' ) ) ) {
* p = 0 ;
value = atoi ( p + 1 ) ;
got_value = True ;
}
for ( i = 0 ; socket_options [ i ] . name ; i + + )
if ( strequal ( socket_options [ i ] . name , tok ) )
break ;
if ( ! socket_options [ i ] . name ) {
DEBUG ( 0 , ( " Unknown socket option %s \n " , tok ) ) ;
continue ;
}
switch ( socket_options [ i ] . opttype ) {
case OPT_BOOL :
case OPT_INT :
ret = setsockopt ( fd , socket_options [ i ] . level ,
socket_options [ i ] . option , ( char * ) & value , sizeof ( int ) ) ;
break ;
case OPT_ON :
if ( got_value )
DEBUG ( 0 , ( " syntax error - %s does not take a value \n " , tok ) ) ;
{
int on = socket_options [ i ] . value ;
ret = setsockopt ( fd , socket_options [ i ] . level ,
socket_options [ i ] . option , ( char * ) & on , sizeof ( int ) ) ;
}
break ;
}
if ( ret ! = 0 )
DEBUG ( 0 , ( " Failed to set socket option %s (Error %s) \n " , tok , strerror ( errno ) ) ) ;
}
2005-09-27 15:10:57 +04:00
talloc_free ( options_list ) ;
2003-08-13 05:53:07 +04:00
}