From 6c1ff14e669c4d5dea5f73ce4de6d501e6634af9 Mon Sep 17 00:00:00 2001 From: sc Date: Fri, 5 Feb 1999 19:03:14 +0000 Subject: Corrected bug when broadcast socket can't be opened. --- src/ivy.c | 110 +++++++++++++++--------------- src/ivysocket.c | 206 ++++++++++++++++++++++++++++++++------------------------ 2 files changed, 171 insertions(+), 145 deletions(-) (limited to 'src') diff --git a/src/ivy.c b/src/ivy.c index 710c7b5..6aab573 100644 --- a/src/ivy.c +++ b/src/ivy.c @@ -136,7 +136,7 @@ static void IvyCleanup() { IvyClientPtr clnt,next; - /* destruction des connexion clients */ + /* destruction des connexions clients */ LIST_EACH_SAFE( clients, clnt, next ) { /* on dit au revoir */ @@ -145,13 +145,15 @@ static void IvyCleanup() LIST_EMPTY( clnt->msg_send ); } LIST_EMPTY( clients ); - /* destruction des socket serveur et supervision */ + + /* destruction des sockets serveur et supervision */ SocketServerClose( server ); SocketClose( broadcast ); } -static int MsgCall( const char *message, MsgSndPtr msg, Client client ) +static int +MsgCall (const char *message, MsgSndPtr msg, Client client) { regmatch_t match[MAX_MATCHING_ARGS+1]; #ifdef GNU_REGEXP @@ -160,60 +162,56 @@ static int MsgCall( const char *message, MsgSndPtr msg, Client client ) unsigned int i; #endif memset( match, -1, sizeof(match )); /* work around bug !!!*/ - if (regexec(&msg->regexp, message, MAX_MATCHING_ARGS, match, 0)==0) { + if (regexec (&msg->regexp, message, MAX_MATCHING_ARGS, match, 0) != 0) + return 0; + #ifdef DEBUG - printf( "Sending message id=%d '%s'\n",msg->id,message); + printf( "Sending message id=%d '%s'\n",msg->id,message); #endif SocketSend( client, "%d %d" ARG_START ,Msg, msg->id); #ifdef DEBUG - printf( "Send matching args count %d\n",msg->regexp.re_nsub); + printf( "Send matching args count %d\n",msg->regexp.re_nsub); #endif //DEBUG #ifdef GNU_REGEXP p = &match[1]; - while ( p->rm_so != -1 ) { + while ( p->rm_so != -1 ) { SocketSend( client, "%.*s" ARG_END , p->rm_eo - p->rm_so, - message + p->rm_so); + message + p->rm_so); ++p; } #else - for ( i = 1; i < msg->regexp.re_nsub+1; i ++ ) - { - if ( match[i].rm_so != -1 ) - { + for ( i = 1; i < msg->regexp.re_nsub+1; i ++ ) { + if ( match[i].rm_so != -1 ) { #ifdef DEBUG - printf( "Send matching arg%d %d %d\n",i,match[i].rm_so , match[i].rm_eo); - printf( "Send matching arg%d %.*s\n",i,match[i].rm_eo - match[i].rm_so, + printf ("Send matching arg%d %d %d\n",i,match[i].rm_so , match[i].rm_eo); + printf ("Send matching arg%d %.*s\n",i,match[i].rm_eo - match[i].rm_so, message + match[i].rm_so); #endif - SocketSend( client, "%.*s" ARG_END ,match[i].rm_eo - match[i].rm_so, + SocketSend (client, "%.*s" ARG_END ,match[i].rm_eo - match[i].rm_so, message + match[i].rm_so); - } - else - { - SocketSend( client, ARG_END ); + } else { + SocketSend (client, ARG_END); #ifdef DEBUG - printf( "Send matching arg%d VIDE\n",i); + printf( "Send matching arg%d VIDE\n",i); #endif //DEBUG - } } + } #endif - SocketSend( client, "\n"); + SocketSend (client, "\n"); return 1; - } - return 0; } -static int ClientCall( IvyClientPtr clnt, const char *message ) +static int +ClientCall (IvyClientPtr clnt, const char *message) { MsgSndPtr msg; int match_count = 0; /* recherche dans la liste des requetes recues de ce client */ - LIST_EACH( clnt->msg_send, msg ) - { - match_count+= MsgCall( message, msg, clnt->client ); + LIST_EACH (clnt->msg_send, msg) { + match_count+= MsgCall (message, msg, clnt->client); } return match_count; } @@ -296,7 +294,7 @@ static void Receive( Client client, void *data, char *line ) SocketClose( client ); break; case Error: - printf("Receive error %d %s\n", id, arg); + printf ("Received error %d %s\n", id, arg); break; case AddRegexp: @@ -306,7 +304,7 @@ static void Receive( Client client, void *data, char *line ) if ( !CheckRegexp( arg ) ) { #ifdef DEBUG - printf("Warning exp='%s' can't match removing from %s\n",arg,ApplicationName); + printf("Warning: regexp '%s' illegal, removing from %s\n",arg,ApplicationName); #endif //DEBUG return; } @@ -325,7 +323,7 @@ static void Receive( Client client, void *data, char *line ) { char errbuf[4096]; regerror (reg, ®exp, errbuf, 4096); - printf("Error compiling '%s', %s\n",arg,errbuf); + printf("Error compiling '%s', %s\n", arg, errbuf); MsgSendTo( client, Error, reg, errbuf ); } break; @@ -354,7 +352,7 @@ static void Receive( Client client, void *data, char *line ) #ifdef DEBUG printf("Quitting already connected %s\n", line); #endif //DEBUG - IvySendError( clnt, 0, "Applicationlication already connected" ); + IvySendError( clnt, 0, "Application already connected" ); SocketClose( client ); } break; @@ -544,7 +542,7 @@ static void BroadcastReceive( Client client, void *data, char *line ) } -void IvyInit(const char *appname, unsigned short port, const char *ready, +void IvyInit (const char *appname, unsigned short port, const char *ready, IvyApplicationCallback callback, void *data, IvyDieCallback die_callback, void *die_data ) @@ -582,8 +580,8 @@ void IvyStart (const char* bus) /* * Initialize TCP port */ - server = SocketServer(ANYPORT, ClientCreate, ClientDelete, Receive ); - ApplicationPort = SocketServerGetPort(server); + server = SocketServer (ANYPORT, ClientCreate, ClientDelete, Receive); + ApplicationPort = SocketServerGetPort (server); /* * Find network list as well as broadcast port @@ -677,60 +675,60 @@ void IvyStart (const char* bus) } /* desabonnements */ -void UnbindMsg( MsgRcvPtr msg ) +void +UnbindMsg (MsgRcvPtr msg) { -IvyClientPtr clnt; + IvyClientPtr clnt; /* Send to already connected clients */ - LIST_EACH( clients, clnt ) - { - MsgSendTo( clnt->client, DelRegexp,msg->id, ""); + LIST_EACH (clients, clnt ) { + MsgSendTo( clnt->client, DelRegexp,msg->id, ""); } } /* demande de reception d'un message */ -static MsgRcvPtr _BindMsg( MsgCallback callback, void *user_data, const char *regexp ) +static MsgRcvPtr +_BindMsg (MsgCallback callback, void *user_data, const char *regexp ) { static int recv_id = 0; IvyClientPtr clnt; MsgRcvPtr msg; /* add Msg to the query list */ LIST_ADD( msg_recv, msg ); - if ( msg ) - { + if (msg) { msg->id = recv_id++; msg->regexp = strdup(regexp); msg->callback = callback; msg->user_data = user_data; - } + } /* Send to already connected clients */ /* recherche dans la liste des requetes recues de mes clients */ - LIST_EACH( clients, clnt ) - { - MsgSendTo( clnt->client, AddRegexp,msg->id,msg->regexp); + LIST_EACH( clients, clnt ) { + MsgSendTo( clnt->client, AddRegexp,msg->id,msg->regexp); } return msg; } -MsgRcvPtr IvyBindMsg( MsgCallback callback, void *user_data, const char *fmt_regex, ... ) +MsgRcvPtr +IvyBindMsg (MsgCallback callback, void *user_data, const char *fmt_regex, ... ) { char buffer[4096]; va_list ap; - va_start( ap, fmt_regex ); - vsprintf( buffer, fmt_regex, ap ); - va_end ( ap ); - return _BindMsg( callback, user_data, buffer ); + va_start (ap, fmt_regex ); + vsprintf (buffer, fmt_regex, ap ); + va_end (ap ); + return _BindMsg (callback, user_data, buffer ); } -static int _SendMsg( const char *message ) +static int +_SendMsg (const char *message) { IvyClientPtr clnt; int match_count = 0; /* recherche dans la liste des requetes recues de mes clients */ - LIST_EACH( clients, clnt ) - { - match_count+= ClientCall( clnt, message ); + LIST_EACH (clients, clnt) { + match_count += ClientCall (clnt, message); } #ifdef DEBUG if ( match_count == 0 ) printf( "Warning no recipient for %s\n",message); diff --git a/src/ivysocket.c b/src/ivysocket.c index 3a86fcc..7fa30f7 100644 --- a/src/ivysocket.c +++ b/src/ivysocket.c @@ -251,12 +251,18 @@ Server SocketServer(unsigned short port, server->port = ntohs(local.sin_port); return server; } + + unsigned short SocketServerGetPort( Server server ) { - return server->port; + return server ? server->port : 0; } + + void SocketServerClose( Server server ) { + if (!server) + return; (*channel_close)( server->channel ); shutdown( server->fd, 2 ); close( server->fd ); @@ -269,6 +275,10 @@ char *SocketGetPeerHost( Client client ) struct sockaddr_in name; struct hostent *host; int len = sizeof(name); + + if (!client) + return "undefined"; + err = getpeername( client->fd, (struct sockaddr *)&name, &len ); if ( err < 0 ) return "can't get peer"; host = gethostbyaddr( (char *)&name.sin_addr.s_addr,sizeof(name.sin_addr.s_addr),name.sin_family); @@ -278,12 +288,16 @@ char *SocketGetPeerHost( Client client ) struct in_addr * SocketGetRemoteAddr( Client client ) { - return &client->from.sin_addr; + return client ? &client->from.sin_addr : 0; } void SocketGetRemoteHost (Client client, char **host, unsigned short *port ) { struct hostent *hostp; + + if (!client) + return; + /* extract hostname and port from last message received */ hostp = gethostbyaddr( (char *)&client->from.sin_addr.s_addr, sizeof(client->from.sin_addr.s_addr),client->from.sin_family); @@ -294,12 +308,17 @@ void SocketGetRemoteHost (Client client, char **host, unsigned short *port ) void SocketClose( Client client ) { - (*channel_close)( client->channel ); + if (client) + (*channel_close)( client->channel ); } void SocketSendRaw( Client client, char *buffer, int len ) { int err; + + if (!client) + return; + err = send( client->fd, buffer, len, 0 ); if ( err != len ) perror( "*** send ***"); @@ -307,7 +326,8 @@ void SocketSendRaw( Client client, char *buffer, int len ) void SocketSetData( Client client, void *data ) { - client->data = data; + if (client) + client->data = data; } void SocketSend( Client client, char *fmt, ... ) @@ -315,6 +335,9 @@ void SocketSend( Client client, char *fmt, ... ) char buffer[4096]; va_list ap; int len; + + if (!client) + return; va_start( ap, fmt ); len = vsprintf( buffer, fmt, ap ); SocketSendRaw( client, buffer, len ); @@ -323,8 +346,9 @@ void SocketSend( Client client, char *fmt, ... ) void *SocketGetData( Client client ) { - return client->data; + return client ? client->data : 0; } + void SocketBroadcast( char *fmt, ... ) { Client client; @@ -340,6 +364,8 @@ void SocketBroadcast( char *fmt, ... ) SocketSendRaw( client, buffer, len ); } } + + /* Ouverture d'un canal TCP/IP en mode client */ @@ -361,49 +387,50 @@ Client SocketConnect( char * host, unsigned short port, Client SocketConnectAddr( struct in_addr * addr, unsigned short port, - void *data, - SocketInterpretation interpretation, - void (*handle_delete)(Client client, void *data) - ) + void *data, + SocketInterpretation interpretation, + void (*handle_delete)(Client client, void *data) + ) { -HANDLE handle; -Client client; -struct sockaddr_in remote; + HANDLE handle; + Client client; + struct sockaddr_in remote; -remote.sin_family = AF_INET; -remote.sin_addr = *addr; -remote.sin_port = htons (port); + remote.sin_family = AF_INET; + remote.sin_addr = *addr; + remote.sin_port = htons (port); -if ((handle = socket( AF_INET, SOCK_STREAM, 0)) < 0){ - perror( "*** client socket ***"); - return NULL; + if ((handle = socket( AF_INET, SOCK_STREAM, 0)) < 0){ + perror( "*** client socket ***"); + return NULL; }; -if ( connect( handle, (struct sockaddr *)&remote, sizeof(remote) ) < 0){ - perror( "*** client connect ***"); - return NULL; + if ( connect( handle, (struct sockaddr *)&remote, sizeof(remote) ) < 0){ + perror( "*** client connect ***"); + return NULL; }; -LIST_ADD( clients_list, client ); -if ( !client ) - { - fprintf(stderr,"NOK Memory Alloc Error\n"); - close( handle ); - exit(0); + LIST_ADD( clients_list, client ); + if ( !client ) { + fprintf(stderr,"NOK Memory Alloc Error\n"); + close( handle ); + exit(0); } -client->fd = handle; -client->channel = (*channel_setup)( handle, client, DeleteSocket, HandleSocket ); -client->interpretation = interpretation; -client->ptr = client->buffer; -client->data = data; -client->handle_delete = handle_delete; -client->from.sin_family = AF_INET; -client->from.sin_addr = *addr; -client->from.sin_port = htons (port); - -return client; + client->fd = handle; + client->channel = (*channel_setup)( handle, client, DeleteSocket, HandleSocket ); + client->interpretation = interpretation; + client->ptr = client->buffer; + client->data = data; + client->handle_delete = handle_delete; + client->from.sin_family = AF_INET; + client->from.sin_addr = *addr; + client->from.sin_port = htons (port); + + return client; } + + int SocketWaitForReply( Client client, char *buffer, int size, int delai) { fd_set rdset; @@ -461,87 +488,88 @@ int SocketWaitForReply( Client client, char *buffer, int size, int delai) /* Socket UDP */ Client SocketBroadcastCreate( unsigned short port, - void *data, - SocketInterpretation interpretation + void *data, + SocketInterpretation interpretation ) { -HANDLE handle; -Client client; -struct sockaddr_in local; -int on = 1; - -local.sin_family = AF_INET; -local.sin_addr.s_addr = INADDR_ANY; -local.sin_port = htons (port); - -if ((handle = socket( AF_INET, SOCK_DGRAM, 0)) < 0){ - perror( "*** dgram socket ***"); - return NULL; + HANDLE handle; + Client client; + struct sockaddr_in local; + int on = 1; + + local.sin_family = AF_INET; + local.sin_addr.s_addr = INADDR_ANY; + local.sin_port = htons (port); + + if ((handle = socket( AF_INET, SOCK_DGRAM, 0)) < 0){ + perror( "*** dgram socket ***"); + return NULL; }; -/* wee need to used multiple client on the same host */ -if (setsockopt( handle, SOL_SOCKET, SO_REUSEADDR, (char *)&on, sizeof( on)) < 0) + /* wee need to used multiple client on the same host */ + if (setsockopt( handle, SOL_SOCKET, SO_REUSEADDR, (char *)&on, sizeof( on)) < 0) { - perror( "*** set socket option REUSEADDR ***"); - return NULL; + perror( "*** set socket option REUSEADDR ***"); + return NULL; }; #ifdef SO_REUSEPORT -if (setsockopt( fd, SOL_SOCKET, SO_REUSEPORT, (char *)&on, sizeof( on)) < 0) + if (setsockopt( fd, SOL_SOCKET, SO_REUSEPORT, (char *)&on, sizeof( on)) < 0) { - perror( "*** set socket option REUSEPORT ***"); - return NULL; + perror( "*** set socket option REUSEPORT ***"); + return NULL; } #endif -/* wee need to broadcast */ -if (setsockopt( handle, SOL_SOCKET, SO_BROADCAST, (char *)&on, sizeof( on)) < 0) - { + /* wee need to broadcast */ + if (setsockopt( handle, SOL_SOCKET, SO_BROADCAST, (char *)&on, sizeof( on)) < 0) + { perror( "*** BROADCAST ***"); return NULL; - }; + }; -if (bind(handle, (struct sockaddr *)&local, sizeof(local)) < 0) - { - perror( "*** test BIND ***"); - return NULL; - }; + if (bind(handle, (struct sockaddr *)&local, sizeof(local)) < 0) + { + perror( "*** test BIND ***"); + return NULL; + }; -LIST_ADD( clients_list, client ); -if ( !client ) - { - fprintf(stderr,"NOK Memory Alloc Error\n"); - close( handle ); - exit(0); - } + LIST_ADD(clients_list, client ); + if ( !client ) + { + fprintf(stderr,"NOK Memory Alloc Error\n"); + close( handle ); + exit(0); + } -client->fd = handle; -client->channel = (*channel_setup)( handle, client, DeleteSocket, HandleSocket ); -client->interpretation = interpretation; -client->ptr = client->buffer; -client->data = data; + client->fd = handle; + client->channel = (*channel_setup)( handle, client, DeleteSocket, HandleSocket ); + client->interpretation = interpretation; + client->ptr = client->buffer; + client->data = data; -return client; + return client; } -void SocketSendBroadcast( Client client, unsigned long host, unsigned short port, char *fmt, ... ) +void SocketSendBroadcast (Client client, unsigned long host, unsigned short port, char *fmt, ... ) { struct sockaddr_in remote; char buffer[4096]; va_list ap; int err,len; - - va_start( ap, fmt ); + + if (!client) + return; + + va_start (ap, fmt ); len = vsprintf( buffer, fmt, ap ); /* Send UDP packet to the dest */ remote.sin_family = AF_INET; remote.sin_addr.s_addr = htonl( host ); remote.sin_port = htons(port); - err = sendto( client->fd, + err = sendto (client->fd, buffer, len,0, (struct sockaddr *)&remote,sizeof(remote)); - if ( err != len ) - { + if (err != len) { perror( "*** send ***"); - } va_end ( ap ); + } va_end ( ap ); } - -- cgit v1.1