/* close on /dev/logring: destroy state for this client */ static int logring_close(struct fusd_file_info *file) { struct logring_client *c; if ((c = (struct logring_client *) file->private_data) != NULL) { /* take this client off our client list */ client_list_remove(c); /* if there is a read outstanding, free the state */ if (c->read != NULL) { fusd_destroy(c->read); c->read = NULL; } /* destroy any outstanding polldiffs */ if (c->polldiff != NULL) { fusd_destroy(c->polldiff); c->polldiff = NULL; } /* get rid of the struct */ free(c); file->private_data = NULL; } return 0; }
/** * @brief Logout a client and report to auth server. * * This function assumes it is being called with the client lock held! This * function remove the client from the client list and free its memory, so * client is no langer valid when this method returns. * * @param client Points to the client to be logged out */ void logout_client(t_client * client) { t_authresponse authresponse; const s_config *config = config_get_config(); fw_deny(client); client_list_remove(client); /* Advertise the logout if we have an auth server */ if (config->auth_servers != NULL) { UNLOCK_CLIENT_LIST(); auth_server_request(&authresponse, REQUEST_TYPE_LOGOUT, client->ip, client->mac, client->token, client->counters.incoming, client->counters.outgoing); if (authresponse.authcode == AUTH_ERROR) debug(LOG_WARNING, "Auth server error when reporting logout"); LOCK_CLIENT_LIST(); } client_free_node(client); }
/** * Handle the received message containing a ‘Client closed’-header * * @return Zero on success -1 on error or interruption, * `errno` will be set accordingly */ static int handle_close_message(void) { /* Servers do not close too often, there is no need to optimise this with another hash table. Doing so would also require some caution because the keys are 32-bit on 32-bit computers, and the client ID:s are 64-bit. */ size_t i, j, ptr = 0, size = 1; size_t *keys = NULL; size_t *old_keys; uint64_t client; hash_entry_t *entry; client_list_t *list; char *command; /* Remove server for all protocols. */ for (i = 0; i < received.header_count; i++) { if (startswith(received.headers[i], "Client closed: ")) { client = parse_client_id(received.headers[i] + strlen("Client closed: ")); foreach_hash_table_entry (reg_table, j, entry) { /* Remove server from list of servers that support the protocol, once, if it is in the list. */ list = (void *)(entry->value); client_list_remove(list, client); if (list->size) continue; /* If no servers support the protocol, list the protocol for removal. */ fail_if (!keys && xmalloc(keys, size, size_t)); fail_if (ptr == size ? growalloc(old_keys, keys, size, size_t) : 0); keys[ptr++] = entry->key; } /* Mark client as closed. */ close_slaves(client); }
void client_close(struct client *client) { client_list_remove(client); client_set_expired(client); g_timer_destroy(client->last_activity); if (client->cmd_list) { free_cmd_list(client->cmd_list); client->cmd_list = NULL; } g_queue_foreach(client->deferred_send, deferred_buffer_free, NULL); g_queue_free(client->deferred_send); fifo_buffer_free(client->input); g_log(G_LOG_DOMAIN, LOG_LEVEL_SECURE, "[%u] closed", client->num); g_free(client); }