diff options
| author | Wilmer van der Gaast <wilmer@gaast.net> | 2006-01-18 19:25:31 +0100 | 
|---|---|---|
| committer | Wilmer van der Gaast <wilmer@gaast.net> | 2006-01-18 19:25:31 +0100 | 
| commit | c1826c6f72d1fe85e1c5decf5207601dac2c23e7 (patch) | |
| tree | 9189d6f012a7d77f8029a44a7ef8e7a7a49a6d10 | |
| parent | ac9f0e965b5002c9eb022f77eb7c6f16cba662b1 (diff) | |
BitlBee now tries to empty sendbuffer before closing the connection.
| -rw-r--r-- | bitlbee.c | 26 | ||||
| -rw-r--r-- | irc.c | 18 | ||||
| -rw-r--r-- | irc.h | 4 | 
3 files changed, 32 insertions, 16 deletions
| @@ -199,7 +199,7 @@ gboolean bitlbee_io_current_client_read( GIOChannel *source, GIOCondition condit  	if( !irc_process( irc ) )  	{  		log_message( LOGLVL_INFO, "Destroying connection with fd %d.", irc->fd ); -		irc_free( irc ); +		irc_abort( irc );  		return FALSE;  	}  @@ -207,7 +207,7 @@ gboolean bitlbee_io_current_client_read( GIOChannel *source, GIOCondition condit  	if( irc->readbuffer && ( strlen( irc->readbuffer ) > 1024 ) )  	{  		log_message( LOGLVL_ERROR, "Maximum line length exceeded." ); -		irc_free( irc ); +		irc_abort( irc );  		return FALSE;  	} @@ -226,25 +226,25 @@ gboolean bitlbee_io_current_client_write( GIOChannel *source, GIOCondition condi  	size = strlen( irc->sendbuffer );  	st = write( irc->fd, irc->sendbuffer, size ); -	if( st <= 0 ) +	if( st == 0 || ( st < 0 && !sockerr_again() ) )  	{ -		if( sockerr_again() ) -		{ -			return TRUE; -		} -		else -		{ -			irc_free( irc ); -			return FALSE; -		} +		irc_free( irc ); +		return FALSE; +	} +	else if( st < 0 ) /* && sockerr_again() */ +	{ +		return TRUE;  	}  	if( st == size )  	{  		g_free( irc->sendbuffer );  		irc->sendbuffer = NULL; -		  		irc->w_watch_source_id = 0; +		 +		if( irc->status == USTATUS_SHUTDOWN ) +			irc_free( irc ); +		  		return( FALSE );  	}  	else @@ -150,6 +150,20 @@ irc_t *irc_new( int fd )  	return( irc );  } +void irc_abort( irc_t *irc ) +{ +	irc->status = USTATUS_SHUTDOWN; +	if( irc->sendbuffer ) +	{ +		g_source_remove( irc->r_watch_source_id ); +		irc->r_watch_source_id = g_timeout_add_full( G_PRIORITY_HIGH, 1000, (GSourceFunc) irc_free, irc, NULL ); +	} +	else +	{ +		irc_free( irc ); +	} +} +  static gboolean irc_free_userhash( gpointer key, gpointer value, gpointer data )  {  	g_free( key ); @@ -158,7 +172,7 @@ static gboolean irc_free_userhash( gpointer key, gpointer value, gpointer data )  }  /* Because we have no garbage collection, this is quite annoying */ -void irc_free(irc_t * irc) +void irc_free( irc_t * irc )  {  	account_t *account, *accounttmp;  	user_t *user, *usertmp; @@ -495,7 +509,7 @@ int irc_exec( irc_t *irc, char **cmd )  	else if( g_strcasecmp( cmd[0], "QUIT" ) == 0 )  	{  		irc_write( irc, "ERROR :%s%s", cmd[1]?"Quit: ":"", cmd[1]?cmd[1]:"Client Quit" ); -		g_io_channel_close( irc->io_channel ); +		/* g_io_channel_close( irc->io_channel ); */  		return( 0 );  	} @@ -43,7 +43,8 @@ typedef enum  	USTATUS_OFFLINE,  	USTATUS_AUTHORIZED,  	USTATUS_LOGGED_IN, -	USTATUS_IDENTIFIED +	USTATUS_IDENTIFIED, +	USTATUS_SHUTDOWN  } irc_status_t;  typedef struct channel @@ -103,6 +104,7 @@ typedef struct irc  extern GSList *irc_connection_list;  irc_t *irc_new( int fd ); +void irc_abort( irc_t *irc );  void irc_free( irc_t *irc );  int irc_exec( irc_t *irc, char **cmd ); | 
