+/* Completion for WHOIS */
+
+SILC_CLIENT_CMD_FUNC(get_client_callback_wc)
+{
+ GetClientInternal i = (GetClientInternal)context;
+ SilcClientCommandReplyContext cmd = context2;
+ SilcClientID *client_id = NULL;
+ SilcClientEntry client_entry = NULL;
+ unsigned char *id_data;
+ SilcUInt32 len;
+
+ /* Get the client entry just returned from server */
+ id_data = silc_argument_get_arg_type(cmd->args, 2, &len);
+ if (id_data)
+ client_id = silc_id_payload_parse_id(id_data, len, NULL);
+ if (client_id)
+ client_entry = silc_client_get_client_by_id(i->client,
+ i->conn, client_id);
+ if (!client_entry) {
+ if (!SILC_STATUS_IS_ERROR(cmd->status) &&
+ cmd->status != SILC_STATUS_OK &&
+ cmd->status != SILC_STATUS_LIST_END) {
+ silc_free(client_id);
+ return;
+ }
+
+ i->completion(i->client, i->conn, i->clients, i->clients_count,
+ i->context);
+ silc_free(client_id);
+ silc_free(i->clients);
+ silc_free(i->nickname);
+ silc_free(i);
+ return;
+ }
+
+ /* Save the client */
+ i->clients = silc_realloc(i->clients,
+ (sizeof(*i->clients) * (i->clients_count + 1)));
+ i->clients[i->clients_count] = client_entry;
+ i->clients_count++;
+
+ /* Return if more data is expected */
+ if (cmd->status != SILC_STATUS_OK &&
+ cmd->status != SILC_STATUS_LIST_END) {
+ silc_free(client_id);
+ return;
+ }
+
+ i->completion(i->client, i->conn, i->clients, i->clients_count,
+ i->context);
+
+ silc_free(client_id);
+ silc_free(i->clients);
+ silc_free(i->nickname);
+ silc_free(i);
+}
+
+/* Our own WHOIS reply processor. */
+
+SILC_CLIENT_CMD_FUNC(get_client_callback_w)
+{
+ SilcClientCommandReplyContext cmd = (SilcClientCommandReplyContext)context;
+ SilcClientConnection conn = (SilcClientConnection)cmd->sock->user_data;
+
+ SILC_LOG_DEBUG(("Start"));
+
+ if (!silc_command_get_status(cmd->payload, NULL, NULL)) {
+ if (SILC_STATUS_IS_ERROR(cmd->status))
+ goto out;
+ if (cmd->status == SILC_STATUS_LIST_END)
+ goto out;
+ goto err;
+ }
+
+ /* Save WHOIS info */
+ silc_client_command_reply_whois_save(cmd, cmd->status, FALSE);
+
+ /* Call pending completion for each reply */
+ if (cmd->status != SILC_STATUS_OK &&
+ cmd->status != SILC_STATUS_LIST_END) {
+ if (cmd->callbacks[0].callback)
+ (*cmd->callbacks[0].callback)(cmd->callbacks[0].context, cmd);
+ silc_client_command_reply_free(cmd);
+ return;
+ }
+
+ out:
+ SILC_CLIENT_PENDING_EXEC(cmd, SILC_COMMAND_WHOIS);
+
+ err:
+ /* If we received notify for invalid ID we'll remove the ID if we
+ have it cached. */
+ if (cmd->error == SILC_STATUS_ERR_NO_SUCH_CLIENT_ID) {
+ SilcClientEntry client_entry;
+ SilcUInt32 tmp_len;
+ unsigned char *tmp =
+ silc_argument_get_arg_type(silc_command_get_args(cmd->payload),
+ 2, &tmp_len);
+ if (tmp) {
+ SilcClientID *client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
+ if (client_id) {
+ client_entry = silc_client_get_client_by_id(cmd->client, conn,
+ client_id);
+ if (client_entry)
+ silc_client_del_client(cmd->client, conn, client_entry);
+ silc_free(client_id);
+ }
+ }
+ }
+
+ /* Unregister this command reply */
+ silc_client_command_unregister(cmd->client, SILC_COMMAND_WHOIS,
+ NULL, silc_client_command_reply_whois_i,
+ cmd->ident);
+ silc_client_command_reply_free(cmd);
+}
+