static gboolean bee_irc_user_free(bee_t *bee, bee_user_t *bu) { return irc_user_free(bee->ui_data, (irc_user_t *) bu->ui_data); }
void irc_free(irc_t * irc) { GSList *l; irc->status |= USTATUS_SHUTDOWN; log_message(LOGLVL_INFO, "Destroying connection with fd %d", irc->fd); if (irc->status & USTATUS_IDENTIFIED && set_getbool(&irc->b->set, "save_on_quit")) { if (storage_save(irc, NULL, TRUE) != STORAGE_OK) { log_message(LOGLVL_WARNING, "Error while saving settings for user %s", irc->user->nick); } } for (l = irc_plugins; l; l = l->next) { irc_plugin_t *p = l->data; if (p->irc_free) { p->irc_free(irc); } } irc_connection_list = g_slist_remove(irc_connection_list, irc); while (irc->queries != NULL) { query_del(irc, irc->queries); } /* This is a little bit messy: bee_free() frees all b->users which calls us back to free the corresponding irc->users. So do this before we clear the remaining ones ourselves. */ bee_free(irc->b); while (irc->users) { irc_user_free(irc, (irc_user_t *) irc->users->data); } while (irc->channels) { irc_channel_free(irc->channels->data); } if (irc->ping_source_id > 0) { b_event_remove(irc->ping_source_id); } if (irc->r_watch_source_id > 0) { b_event_remove(irc->r_watch_source_id); } if (irc->w_watch_source_id > 0) { b_event_remove(irc->w_watch_source_id); } closesocket(irc->fd); irc->fd = -1; g_hash_table_foreach_remove(irc->nick_user_hash, irc_free_hashkey, NULL); g_hash_table_destroy(irc->nick_user_hash); g_hash_table_foreach_remove(irc->watches, irc_free_hashkey, NULL); g_hash_table_destroy(irc->watches); if (irc->iconv != (GIConv) - 1) { g_iconv_close(irc->iconv); } if (irc->oconv != (GIConv) - 1) { g_iconv_close(irc->oconv); } g_free(irc->sendbuffer); g_free(irc->readbuffer); g_free(irc->password); g_free(irc); if (global.conf->runmode == RUNMODE_INETD || global.conf->runmode == RUNMODE_FORKDAEMON || (global.conf->runmode == RUNMODE_DAEMON && global.listen_socket == -1 && irc_connection_list == NULL)) { b_main_quit(); } }