5 Author: Pekka Riikonen <priikone@silcnet.org>
7 Copyright (C) 1997 - 2002 Pekka Riikonen
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
21 * Server packet routines to handle received packets.
25 #include "serverincludes.h"
26 #include "server_internal.h"
28 /* Received notify packet. Server can receive notify packets from router.
29 Server then relays the notify messages to clients if needed. */
31 void silc_server_notify(SilcServer server,
32 SilcSocketConnection sock,
33 SilcPacketContext *packet)
35 SilcNotifyPayload payload;
37 SilcArgumentPayload args;
38 SilcChannelID *channel_id = NULL, *channel_id2;
39 SilcClientID *client_id, *client_id2;
40 SilcServerID *server_id;
42 SilcChannelEntry channel = NULL;
43 SilcClientEntry client = NULL, client2 = NULL;
44 SilcServerEntry server_entry = NULL;
45 SilcChannelClientEntry chl;
46 SilcIDCacheEntry cache = NULL;
47 SilcHashTableList htl;
53 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
54 packet->src_id_type != SILC_ID_SERVER || !packet->dst_id) {
55 SILC_LOG_DEBUG(("Bad notify packet received"));
59 /* If the packet is destined directly to a client then relay the packet
60 before processing it. */
61 if (packet->dst_id_type == SILC_ID_CLIENT) {
63 SilcSocketConnection dst_sock;
65 /* Get the route to the client */
66 dst_sock = silc_server_get_client_route(server, packet->dst_id,
67 packet->dst_id_len, NULL,
70 /* Relay the packet */
71 silc_server_relay_packet(server, dst_sock, idata->send_key,
72 idata->hmac_send, idata->psn_send++,
76 /* Parse the Notify Payload */
77 payload = silc_notify_payload_parse(packet->buffer->data,
82 /* If we are router and this packet is not already broadcast packet
83 we will broadcast it. The sending socket really cannot be router or
84 the router is buggy. If this packet is coming from router then it must
85 have the broadcast flag set already and we won't do anything. */
86 if (server->server_type == SILC_ROUTER &&
87 sock->type == SILC_SOCKET_TYPE_SERVER &&
88 !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
89 SILC_LOG_DEBUG(("Broadcasting received Notify packet"));
90 if (packet->dst_id_type == SILC_ID_CHANNEL) {
91 /* Packet is destined to channel */
92 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
97 silc_server_packet_send_dest(server, SILC_PRIMARY_ROUTE(server),
98 packet->type, packet->flags |
99 SILC_PACKET_FLAG_BROADCAST,
100 channel_id, SILC_ID_CHANNEL,
101 packet->buffer->data,
102 packet->buffer->len, FALSE);
103 silc_server_backup_send_dest(server, sock->user_data,
104 packet->type, packet->flags,
105 channel_id, SILC_ID_CHANNEL,
106 packet->buffer->data, packet->buffer->len,
109 /* Packet is destined to client or server */
110 silc_server_packet_send(server, SILC_PRIMARY_ROUTE(server),
112 packet->flags | SILC_PACKET_FLAG_BROADCAST,
113 packet->buffer->data, packet->buffer->len,
115 silc_server_backup_send(server, sock->user_data,
116 packet->type, packet->flags,
117 packet->buffer->data, packet->buffer->len,
122 type = silc_notify_get_type(payload);
123 args = silc_notify_get_args(payload);
128 case SILC_NOTIFY_TYPE_JOIN:
130 * Distribute the notify to local clients on the channel
132 SILC_LOG_DEBUG(("JOIN notify"));
135 silc_free(channel_id);
138 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
141 channel_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
145 /* Get channel entry */
146 channel = silc_idlist_find_channel_by_id(server->global_list,
149 channel = silc_idlist_find_channel_by_id(server->local_list,
152 SILC_LOG_DEBUG(("Notify for unknown channel"));
153 silc_free(channel_id);
157 silc_free(channel_id);
160 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
163 client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
167 /* If the the client is not in local list we check global list (ie. the
168 channel will be global channel) and if it does not exist then create
169 entry for the client. */
170 client = silc_idlist_find_client_by_id(server->global_list,
171 client_id, server->server_type,
174 client = silc_idlist_find_client_by_id(server->local_list,
175 client_id, server->server_type,
178 /* If router did not find the client the it is bogus */
179 if (server->server_type != SILC_SERVER) {
180 silc_free(client_id);
185 silc_idlist_add_client(server->global_list, NULL, NULL, NULL,
186 silc_id_dup(client_id, SILC_ID_CLIENT),
187 sock->user_data, NULL, 0);
189 SILC_LOG_ERROR(("Could not add new client to the ID Cache"));
190 silc_free(client_id);
194 client->data.status |= SILC_IDLIST_STATUS_REGISTERED;
197 silc_free(client_id);
199 /* Do not process the notify if the client is not registered */
200 if (!(client->data.status & SILC_IDLIST_STATUS_REGISTERED))
203 /* Do not add client to channel if it is there already */
204 if (silc_server_client_on_channel(client, channel, NULL)) {
205 SILC_LOG_DEBUG(("Client already on channel %s",
206 channel->channel_name));
210 /* Send to channel */
211 silc_server_packet_send_to_channel(server, sock, channel, packet->type,
212 FALSE, packet->buffer->data,
213 packet->buffer->len, FALSE);
215 if (server->server_type != SILC_ROUTER &&
216 sock->type == SILC_SOCKET_TYPE_ROUTER)
217 /* The channel is global now */
218 channel->global_users = TRUE;
220 SILC_LOG_DEBUG(("Joining to channel %s", channel->channel_name));
222 /* JOIN the global client to the channel (local clients (if router
223 created the channel) is joined in the pending JOIN command). */
224 chl = silc_calloc(1, sizeof(*chl));
225 chl->client = client;
226 chl->channel = channel;
228 if (server->server_type != SILC_ROUTER ||
229 sock->type == SILC_SOCKET_TYPE_ROUTER) {
230 /* If this is the first one on the channel then it is the founder of
231 the channel. This is done on normal server and on router if this
232 notify is coming from router */
233 if (!silc_hash_table_count(channel->user_list)) {
234 SILC_LOG_DEBUG(("Client %s is founder on channel",
235 silc_id_render(chl->client->id, SILC_ID_CLIENT)));
236 chl->mode = (SILC_CHANNEL_UMODE_CHANOP | SILC_CHANNEL_UMODE_CHANFO);
240 silc_hash_table_add(channel->user_list, client, chl);
241 silc_hash_table_add(client->channels, channel, chl);
242 channel->user_count++;
243 channel->disabled = FALSE;
245 /* Make sure we don't expire clients that are on channel */
249 /* Update statistics */
250 if (server->server_type == SILC_ROUTER) {
251 if (sock->type != SILC_SOCKET_TYPE_ROUTER)
252 server->stat.cell_chanclients++;
253 server->stat.chanclients++;
258 case SILC_NOTIFY_TYPE_LEAVE:
260 * Distribute the notify to local clients on the channel
262 SILC_LOG_DEBUG(("LEAVE notify"));
265 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
266 packet->dst_id_type);
271 /* Get channel entry */
272 channel = silc_idlist_find_channel_by_id(server->global_list,
275 channel = silc_idlist_find_channel_by_id(server->local_list,
278 SILC_LOG_DEBUG(("Notify for unknown channel"));
279 silc_free(channel_id);
285 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
287 silc_free(channel_id);
290 client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
292 silc_free(channel_id);
296 /* Get client entry */
297 client = silc_idlist_find_client_by_id(server->global_list,
298 client_id, TRUE, NULL);
300 client = silc_idlist_find_client_by_id(server->local_list,
301 client_id, TRUE, NULL);
303 silc_free(client_id);
304 silc_free(channel_id);
308 silc_free(client_id);
309 silc_free(channel_id);
311 /* Check if on channel */
312 if (!silc_server_client_on_channel(client, channel, NULL))
315 /* Send the leave notify to channel */
316 silc_server_packet_send_to_channel(server, sock, channel, packet->type,
317 FALSE, packet->buffer->data,
318 packet->buffer->len, FALSE);
320 /* Remove the user from channel */
321 silc_server_remove_from_one_channel(server, sock, channel, client, FALSE);
324 case SILC_NOTIFY_TYPE_SIGNOFF:
326 * Distribute the notify to local clients on the channel
328 SILC_LOG_DEBUG(("SIGNOFF notify"));
331 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
334 client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
338 /* Get client entry */
339 client = silc_idlist_find_client_by_id(server->global_list,
340 client_id, TRUE, &cache);
342 client = silc_idlist_find_client_by_id(server->local_list,
343 client_id, TRUE, &cache);
345 silc_free(client_id);
349 silc_free(client_id);
351 /* Get signoff message */
352 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
356 /* Update statistics */
357 server->stat.clients--;
358 if (server->stat.cell_clients)
359 server->stat.cell_clients--;
360 SILC_OPER_STATS_UPDATE(client, server, SILC_UMODE_SERVER_OPERATOR);
361 SILC_OPER_STATS_UPDATE(client, router, SILC_UMODE_ROUTER_OPERATOR);
362 silc_schedule_task_del_by_context(server->schedule, client);
364 /* Remove the client from all channels. */
365 silc_server_remove_from_channels(server, NULL, client, TRUE, tmp, FALSE);
367 /* Check if anyone is watching this nickname */
368 if (server->server_type == SILC_ROUTER)
369 silc_server_check_watcher_list(server, client, NULL,
370 SILC_NOTIFY_TYPE_SIGNOFF);
372 /* Remove this client from watcher list if it is */
373 silc_server_del_from_watcher_list(server, client);
375 client->data.status &= ~SILC_IDLIST_STATUS_REGISTERED;
376 cache->expire = SILC_ID_CACHE_EXPIRE_DEF;
379 case SILC_NOTIFY_TYPE_TOPIC_SET:
381 * Distribute the notify to local clients on the channel
384 SILC_LOG_DEBUG(("TOPIC SET notify"));
387 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
390 client_id = silc_id_payload_parse_id(tmp, tmp_len, &id_type);
394 /* Get client entry */
395 if (id_type == SILC_ID_CLIENT) {
396 client = silc_idlist_find_client_by_id(server->global_list,
397 client_id, TRUE, &cache);
399 client = silc_idlist_find_client_by_id(server->local_list,
400 client_id, TRUE, &cache);
402 silc_free(client_id);
406 silc_free(client_id);
410 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
412 silc_free(channel_id);
417 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
418 packet->dst_id_type);
423 /* Get channel entry */
424 channel = silc_idlist_find_channel_by_id(server->global_list,
427 channel = silc_idlist_find_channel_by_id(server->local_list,
430 SILC_LOG_DEBUG(("Notify for unknown channel"));
431 silc_free(channel_id);
435 silc_free(channel_id);
437 if (channel->topic && !strcmp(channel->topic, tmp)) {
438 SILC_LOG_DEBUG(("Topic is already set and same"));
443 /* Get user's channel entry and check that topic set is allowed. */
444 if (!silc_server_client_on_channel(client, channel, &chl))
446 if (channel->mode & SILC_CHANNEL_MODE_TOPIC &&
447 !(chl->mode & SILC_CHANNEL_UMODE_CHANOP) &&
448 !(chl->mode & SILC_CHANNEL_UMODE_CHANFO)) {
449 SILC_LOG_DEBUG(("Topic change is not allowed"));
454 /* Change the topic */
455 silc_free(channel->topic);
456 channel->topic = strdup(tmp);
458 /* Send the same notify to the channel */
459 silc_server_packet_send_to_channel(server, NULL, channel, packet->type,
460 FALSE, packet->buffer->data,
461 packet->buffer->len, FALSE);
464 case SILC_NOTIFY_TYPE_NICK_CHANGE:
467 * Distribute the notify to local clients on the channel
469 unsigned char *id, *id2;
471 SilcUInt32 nickname_len;
473 SILC_LOG_DEBUG(("NICK CHANGE notify"));
475 /* Get old client ID */
476 id = silc_argument_get_arg_type(args, 1, &tmp_len);
479 client_id = silc_id_payload_parse_id(id, tmp_len, NULL);
483 /* Get new client ID */
484 id2 = silc_argument_get_arg_type(args, 2, &tmp_len);
487 client_id2 = silc_id_payload_parse_id(id2, tmp_len, NULL);
489 silc_free(client_id);
493 SILC_LOG_DEBUG(("Old Client ID id(%s)",
494 silc_id_render(client_id, SILC_ID_CLIENT)));
495 SILC_LOG_DEBUG(("New Client ID id(%s)",
496 silc_id_render(client_id2, SILC_ID_CLIENT)));
498 /* From protocol version 1.1 we also get the new nickname */
499 nickname = silc_argument_get_arg_type(args, 3, &nickname_len);;
501 /* Replace the Client ID */
502 client = silc_idlist_replace_client_id(server,
503 server->global_list, client_id,
504 client_id2, nickname);
506 client = silc_idlist_replace_client_id(server,
507 server->local_list, client_id,
508 client_id2, nickname);
511 /* Send the NICK_CHANGE notify type to local clients on the channels
512 this client is joined to. */
513 silc_server_send_notify_on_channels(server, client, client,
514 SILC_NOTIFY_TYPE_NICK_CHANGE, 3,
515 id, tmp_len, id2, tmp_len,
520 silc_free(client_id);
522 silc_free(client_id2);
526 case SILC_NOTIFY_TYPE_CMODE_CHANGE:
528 * Distribute the notify to local clients on the channel
531 SILC_LOG_DEBUG(("CMODE CHANGE notify"));
534 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
537 client_id = silc_id_payload_parse_id(tmp, tmp_len, &id_type);
541 /* Get client entry */
542 if (id_type == SILC_ID_CLIENT) {
543 client = silc_idlist_find_client_by_id(server->global_list,
544 client_id, TRUE, &cache);
546 client = silc_idlist_find_client_by_id(server->local_list,
547 client_id, TRUE, &cache);
549 silc_free(client_id);
554 silc_free(client_id);
557 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
558 packet->dst_id_type);
563 /* Get channel entry */
564 channel = silc_idlist_find_channel_by_id(server->global_list,
567 channel = silc_idlist_find_channel_by_id(server->local_list,
570 SILC_LOG_DEBUG(("Notify for unknown channel"));
571 silc_free(channel_id);
575 silc_free(channel_id);
578 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
581 SILC_GET32_MSB(mode, tmp);
583 /* Check if mode changed */
584 if (channel->mode == mode) {
585 SILC_LOG_DEBUG(("Mode is changed already"));
587 /* If this mode change has founder mode then we'll enforce the
588 change so that the server gets the real founder public key */
589 if (server->server_type != SILC_SERVER &&
590 sock != SILC_PRIMARY_ROUTE(server) &&
591 mode & SILC_CHANNEL_MODE_FOUNDER_AUTH && channel->founder_key) {
592 SILC_LOG_DEBUG(("Sending founder public key to server"));
593 silc_server_send_notify_cmode(server, sock, FALSE, channel,
594 channel->mode, server->id,
595 SILC_ID_SERVER, channel->cipher,
598 channel->founder_key);
601 /* If we received same mode from our primary check whether founder
602 mode and key in the notify is set. We update the founder key
603 here since we may have wrong one */
604 if (server->server_type == SILC_SERVER &&
605 sock == SILC_PRIMARY_ROUTE(server) &&
606 mode & SILC_CHANNEL_MODE_FOUNDER_AUTH) {
607 SILC_LOG_DEBUG(("Founder public key received from router"));
608 tmp = silc_argument_get_arg_type(args, 6, &tmp_len);
612 if (channel->founder_key)
613 silc_pkcs_public_key_free(channel->founder_key);
614 channel->founder_key = NULL;
615 silc_pkcs_public_key_payload_decode(tmp, tmp_len,
616 &channel->founder_key);
622 /* Get user's channel entry and check that mode change is allowed */
624 if (!silc_server_client_on_channel(client, channel, &chl))
626 if (!silc_server_check_cmode_rights(server, channel, chl, mode)) {
627 SILC_LOG_DEBUG(("CMODE change is not allowed"));
628 silc_server_send_notify_cmode(server, sock, FALSE, channel,
629 channel->mode, server->id,
630 SILC_ID_SERVER, channel->cipher,
633 channel->founder_key);
637 /* Assure that server is not removing founder mode from us */
638 if (server->server_type == SILC_ROUTER &&
639 sock != SILC_PRIMARY_ROUTE(server) &&
640 channel->mode & SILC_CHANNEL_MODE_FOUNDER_AUTH &&
641 !(mode & SILC_CHANNEL_MODE_FOUNDER_AUTH)) {
642 SILC_LOG_DEBUG(("Enforcing sender to change channel mode"));
643 silc_server_send_notify_cmode(server, sock, FALSE, channel,
644 channel->mode, server->id,
645 SILC_ID_SERVER, channel->cipher,
648 channel->founder_key);
652 /* If server is adding founder mode, check whether there is founder
653 on channel already and is not from this server */
654 if (server->server_type == SILC_ROUTER &&
655 sock != SILC_PRIMARY_ROUTE(server) &&
656 mode & SILC_CHANNEL_MODE_FOUNDER_AUTH) {
657 silc_hash_table_list(channel->user_list, &htl);
658 while (silc_hash_table_get(&htl, NULL, (void *)&chl))
659 if (chl->mode & SILC_CHANNEL_UMODE_CHANFO &&
660 chl->client->router != sock->user_data) {
661 SILC_LOG_DEBUG(("Enforcing sender to change channel mode"));
662 silc_server_send_notify_cmode(server, sock, FALSE, channel,
663 channel->mode, server->id,
664 SILC_ID_SERVER, channel->cipher,
667 channel->founder_key);
668 silc_hash_table_list_reset(&htl);
671 silc_hash_table_list_reset(&htl);
675 /* If the channel had private keys set and the mode was removed then
676 we must re-generate and re-distribute a new channel key */
677 if (channel->mode & SILC_CHANNEL_MODE_PRIVKEY &&
678 !(mode & SILC_CHANNEL_MODE_PRIVKEY)) {
679 /* Re-generate channel key */
680 if (!silc_server_create_channel_key(server, channel, 0))
683 /* Send the channel key. This sends it to our local clients and if
684 we are normal server to our router as well. */
685 silc_server_send_channel_key(server, NULL, channel,
686 server->server_type == SILC_ROUTER ?
687 FALSE : !server->standalone);
691 tmp = silc_argument_get_arg_type(args, 4, &tmp_len);
693 unsigned char hash[32];
696 silc_hmac_free(channel->hmac);
697 if (!silc_hmac_alloc(tmp, NULL, &channel->hmac))
700 /* Set the HMAC key out of current channel key. The client must do
702 silc_hash_make(silc_hmac_get_hash(channel->hmac), channel->key,
703 channel->key_len / 8, hash);
704 silc_hmac_set_key(channel->hmac, hash,
705 silc_hash_len(silc_hmac_get_hash(channel->hmac)));
706 memset(hash, 0, sizeof(hash));
709 /* Get the passphrase */
710 tmp = silc_argument_get_arg_type(args, 5, &tmp_len);
712 silc_free(channel->passphrase);
713 channel->passphrase = silc_memdup(tmp, tmp_len);
716 /* Get founder public key */
717 tmp = silc_argument_get_arg_type(args, 6, &tmp_len);
718 if (tmp && mode & SILC_CHANNEL_MODE_FOUNDER_AUTH) {
719 if (channel->founder_key)
720 silc_pkcs_public_key_free(channel->founder_key);
721 channel->founder_key = NULL;
722 silc_pkcs_public_key_payload_decode(tmp, tmp_len, &channel->founder_key);
724 if (!channel->founder_key ||
725 (client && client->data.public_key &&
726 server->server_type == SILC_ROUTER &&
727 !silc_pkcs_public_key_compare(channel->founder_key,
728 client->data.public_key))) {
729 /* A really buggy server isn't checking public keys correctly.
730 It's not possible that the mode setter and founder wouldn't
731 have same public key. */
732 SILC_LOG_DEBUG(("Enforcing sender to change channel mode"));
734 mode &= ~SILC_CHANNEL_MODE_FOUNDER_AUTH;
735 silc_server_send_notify_cmode(server, sock, FALSE, channel,
736 mode, server->id, SILC_ID_SERVER,
739 channel->passphrase, NULL);
740 if (channel->founder_key)
741 silc_pkcs_public_key_free(channel->founder_key);
742 channel->founder_key = NULL;
743 } else if (client && !client->data.public_key) {
744 client->data.public_key =
745 silc_pkcs_public_key_copy(channel->founder_key);
749 if (mode & SILC_CHANNEL_MODE_FOUNDER_AUTH && !channel->founder_key &&
750 server->server_type == SILC_ROUTER) {
751 SILC_LOG_DEBUG(("Enforcing sender to change channel mode"));
752 mode &= ~SILC_CHANNEL_MODE_FOUNDER_AUTH;
753 silc_server_send_notify_cmode(server, sock, FALSE, channel,
754 mode, server->id, SILC_ID_SERVER,
757 channel->passphrase, NULL);
760 /* Send the same notify to the channel */
761 silc_server_packet_send_to_channel(server, NULL, channel, packet->type,
762 FALSE, packet->buffer->data,
763 packet->buffer->len, FALSE);
766 channel->mode = mode;
768 if (!(channel->mode & SILC_CHANNEL_MODE_FOUNDER_AUTH) &&
769 channel->founder_key) {
770 silc_pkcs_public_key_free(channel->founder_key);
771 channel->founder_key = NULL;
776 case SILC_NOTIFY_TYPE_CUMODE_CHANGE:
779 * Distribute the notify to local clients on the channel
781 SilcChannelClientEntry chl2 = NULL;
782 bool notify_sent = FALSE;
784 SILC_LOG_DEBUG(("CUMODE CHANGE notify"));
787 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
790 client_id = silc_id_payload_parse_id(tmp, tmp_len, &id_type);
794 /* Get client entry */
795 if (id_type == SILC_ID_CLIENT) {
796 client = silc_idlist_find_client_by_id(server->global_list,
797 client_id, TRUE, &cache);
799 client = silc_idlist_find_client_by_id(server->local_list,
800 client_id, TRUE, &cache);
802 silc_free(client_id);
807 silc_free(client_id);
810 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
811 packet->dst_id_type);
816 /* Get channel entry */
817 channel = silc_idlist_find_channel_by_id(server->global_list,
820 channel = silc_idlist_find_channel_by_id(server->local_list,
823 SILC_LOG_DEBUG(("Notify for unknown channel"));
824 silc_free(channel_id);
830 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
832 silc_free(channel_id);
836 SILC_GET32_MSB(mode, tmp);
838 /* Get target client */
839 tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
842 client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
846 /* Get client entry */
847 client2 = silc_idlist_find_client_by_id(server->global_list,
848 client_id, TRUE, NULL);
850 client2 = silc_idlist_find_client_by_id(server->local_list,
851 client_id, TRUE, NULL);
853 silc_free(client_id);
857 silc_free(client_id);
860 /* Check that sender is on channel */
861 if (!silc_server_client_on_channel(client, channel, &chl))
864 if (client != client2 && server->server_type == SILC_ROUTER) {
865 /* Sender must be operator */
866 if (!(chl->mode & SILC_CHANNEL_UMODE_CHANOP) &&
867 !(chl->mode & SILC_CHANNEL_UMODE_CHANFO)) {
868 SILC_LOG_DEBUG(("CUMODE change is not allowed"));
872 if (!silc_server_client_on_channel(client2, channel, &chl))
875 /* If target is founder mode change is not allowed. */
876 if (chl->mode & SILC_CHANNEL_UMODE_CHANFO) {
877 SILC_LOG_DEBUG(("CUMODE change is not allowed"));
883 /* Get target channel user entry */
884 if (!silc_server_client_on_channel(client2, channel, &chl))
887 if (server->server_type == SILC_SERVER && chl->mode == mode) {
888 SILC_LOG_DEBUG(("Mode is changed already"));
892 if (mode & SILC_CHANNEL_UMODE_CHANFO &&
893 !(chl->mode & SILC_CHANNEL_UMODE_CHANFO) &&
894 server->server_type == SILC_ROUTER &&
895 sock != SILC_PRIMARY_ROUTE(server)) {
896 SilcPublicKey founder_key = NULL;
898 /* If channel doesn't have founder auth mode then it's impossible
899 that someone would be getting founder rights with CUMODE command.
900 In that case there already either is founder or there isn't
901 founder at all on the channel. */
902 if (client && !(channel->mode & SILC_CHANNEL_MODE_FOUNDER_AUTH)) {
903 /* Force the mode to not have founder mode */
904 chl->mode = mode &= ~SILC_CHANNEL_UMODE_CHANFO;
905 silc_server_force_cumode_change(server, sock, channel, chl, mode);
910 /* Get the founder of the channel and if found then this client
911 cannot be the founder since there already is one. */
912 silc_hash_table_list(channel->user_list, &htl);
913 while (silc_hash_table_get(&htl, NULL, (void *)&chl2))
914 if (chl2->mode & SILC_CHANNEL_UMODE_CHANFO) {
915 /* If the founder on the channel is not the one whom has set
916 the founder mode, then it's possible that this CUMODE_CHANGE
917 is correct. Due to netsplits it's possible that this
918 situation happens. */
919 if (!(channel->mode & SILC_CHANNEL_MODE_FOUNDER_AUTH) ||
920 (channel->founder_key && chl2->client->data.public_key &&
921 silc_pkcs_public_key_compare(
922 channel->founder_key,
923 chl2->client->data.public_key))) {
924 chl->mode = mode &= ~SILC_CHANNEL_UMODE_CHANFO;
925 silc_server_force_cumode_change(server, sock, channel,
931 silc_hash_table_list_reset(&htl);
932 if (!(mode & SILC_CHANNEL_UMODE_CHANFO))
935 /* Founder not found of the channel. Since the founder auth mode
936 is set on the channel now check whether this is the client that
937 originally set the mode. */
939 if (channel->founder_key) {
940 /* Get public key that must be present in notify */
941 tmp = silc_argument_get_arg_type(args, 4, &tmp_len);
942 if (!tmp || !silc_pkcs_public_key_payload_decode(tmp, tmp_len,
944 chl->mode = mode &= ~SILC_CHANNEL_UMODE_CHANFO;
945 silc_server_force_cumode_change(server, sock, channel, chl, mode);
950 /* Now match the public key we have cached and public key sent.
952 #if 0 /* The key may be other than the client's in 1.2 */
953 if (client && client->data.public_key &&
954 !silc_pkcs_public_key_compare(channel->founder_key,
955 client->data.public_key)) {
956 chl->mode = mode &= ~SILC_CHANNEL_UMODE_CHANFO;
957 silc_server_force_cumode_change(server, sock, channel, chl, mode);
962 if (!silc_pkcs_public_key_compare(channel->founder_key,
964 chl->mode = mode &= ~SILC_CHANNEL_UMODE_CHANFO;
965 silc_server_force_cumode_change(server, sock, channel, chl, mode);
971 /* There cannot be anyone else as founder on the channel now. This
972 client is definitely the founder due to this authentication */
973 silc_hash_table_list(channel->user_list, &htl);
974 while (silc_hash_table_get(&htl, NULL, (void *)&chl2))
975 if (chl2->mode & SILC_CHANNEL_UMODE_CHANFO) {
976 chl2->mode &= ~SILC_CHANNEL_UMODE_CHANFO;
977 silc_server_force_cumode_change(server, NULL, channel, chl2,
981 silc_hash_table_list_reset(&htl);
984 silc_pkcs_public_key_free(founder_key);
987 if (server->server_type != SILC_SERVER && chl->mode == mode) {
988 SILC_LOG_DEBUG(("Mode is changed already"));
992 SILC_LOG_DEBUG(("Changing %s channel user mode",
993 chl->client->nickname ? chl->client->nickname :
994 (unsigned char *)""));
996 /* Change the mode */
999 /* Send the same notify to the channel */
1001 silc_server_packet_send_to_channel(server, NULL, channel,
1003 FALSE, packet->buffer->data,
1004 packet->buffer->len, FALSE);
1006 silc_free(channel_id);
1010 case SILC_NOTIFY_TYPE_INVITE:
1012 if (packet->dst_id_type == SILC_ID_CLIENT)
1015 SILC_LOG_DEBUG(("INVITE notify"));
1017 /* Get Channel ID */
1018 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
1021 channel_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1025 /* Get channel entry */
1026 channel = silc_idlist_find_channel_by_id(server->global_list,
1029 channel = silc_idlist_find_channel_by_id(server->local_list,
1032 SILC_LOG_DEBUG(("Notify for unknown channel"));
1033 silc_free(channel_id);
1037 silc_free(channel_id);
1040 tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
1043 client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1047 /* Get client entry */
1048 client = silc_idlist_find_client_by_id(server->global_list,
1049 client_id, TRUE, &cache);
1051 client = silc_idlist_find_client_by_id(server->local_list,
1052 client_id, TRUE, &cache);
1054 silc_free(client_id);
1058 silc_free(client_id);
1060 /* Get user's channel entry and check that inviting is allowed. */
1061 if (!silc_server_client_on_channel(client, channel, &chl))
1063 if (channel->mode & SILC_CHANNEL_MODE_INVITE &&
1064 !(chl->mode & SILC_CHANNEL_UMODE_CHANOP) &&
1065 !(chl->mode & SILC_CHANNEL_UMODE_CHANFO)) {
1066 SILC_LOG_DEBUG(("Inviting is not allowed"));
1070 /* Get the invite action */
1071 tmp = silc_argument_get_arg_type(args, 4, &tmp_len);
1072 if (tmp && tmp_len == 1) {
1073 SilcUInt8 action = (SilcUInt8)tmp[0];
1074 SilcUInt16 iargc = 0;
1075 SilcArgumentPayload iargs;
1077 /* Get invite list */
1078 tmp = silc_argument_get_arg_type(args, 5, &tmp_len);
1079 if (!tmp || tmp_len < 2)
1082 /* Parse the arguments to see they are constructed correctly */
1083 SILC_GET16_MSB(iargc, tmp);
1084 iargs = silc_argument_payload_parse(tmp + 2, tmp_len - 2, iargc);
1088 if (action == 0 && !channel->invite_list)
1089 channel->invite_list = silc_hash_table_alloc(0, silc_hash_ptr,
1093 /* Proces the invite action */
1094 silc_server_inviteban_process(server, channel->invite_list, action,
1096 silc_argument_payload_free(iargs);
1101 case SILC_NOTIFY_TYPE_CHANNEL_CHANGE:
1103 * Distribute to the local clients on the channel and change the
1107 SILC_LOG_DEBUG(("CHANNEL CHANGE"));
1109 if (sock->type != SILC_SOCKET_TYPE_ROUTER)
1112 /* Get the old Channel ID */
1113 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
1116 channel_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1120 /* Get the channel entry */
1121 channel = silc_idlist_find_channel_by_id(server->local_list,
1124 channel = silc_idlist_find_channel_by_id(server->global_list,
1127 SILC_LOG_DEBUG(("Notify for unknown channel"));
1128 silc_free(channel_id);
1133 /* Send the notify to the channel */
1134 silc_server_packet_send_to_channel(server, sock, channel, packet->type,
1135 FALSE, packet->buffer->data,
1136 packet->buffer->len, FALSE);
1138 /* Get the new Channel ID */
1139 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
1142 channel_id2 = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1146 SILC_LOG_DEBUG(("Old Channel ID id(%s)",
1147 silc_id_render(channel_id, SILC_ID_CHANNEL)));
1148 SILC_LOG_DEBUG(("New Channel ID id(%s)",
1149 silc_id_render(channel_id2, SILC_ID_CHANNEL)));
1151 /* Replace the Channel ID */
1152 if (!silc_idlist_replace_channel_id(server->local_list, channel_id,
1154 if (!silc_idlist_replace_channel_id(server->global_list, channel_id,
1156 silc_free(channel_id2);
1161 SilcBuffer modes = NULL, users = NULL, users_modes = NULL;
1163 /* Re-announce this channel which ID was changed. */
1164 silc_server_send_new_channel(server, sock, FALSE, channel->channel_name,
1166 silc_id_get_len(channel->id,
1170 /* Re-announce our clients on the channel as the ID has changed now */
1171 silc_server_announce_get_channel_users(server, channel, &modes, &users,
1174 silc_buffer_push(users, users->data - users->head);
1175 silc_server_packet_send(server, sock,
1176 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
1177 users->data, users->len, FALSE);
1178 silc_buffer_free(users);
1181 silc_buffer_push(modes, modes->data - modes->head);
1182 silc_server_packet_send_dest(server, sock,
1183 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
1184 channel->id, SILC_ID_CHANNEL,
1185 modes->data, modes->len, FALSE);
1186 silc_buffer_free(modes);
1189 silc_buffer_push(users_modes, users_modes->data - users_modes->head);
1190 silc_server_packet_send_dest(server, sock,
1191 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
1192 channel->id, SILC_ID_CHANNEL,
1194 users_modes->len, FALSE);
1195 silc_buffer_free(users_modes);
1198 /* Re-announce channel's topic */
1199 if (channel->topic) {
1200 silc_server_send_notify_topic_set(server, sock,
1201 server->server_type == SILC_ROUTER ?
1202 TRUE : FALSE, channel,
1203 server->id, SILC_ID_SERVER,
1208 silc_free(channel_id);
1212 case SILC_NOTIFY_TYPE_SERVER_SIGNOFF:
1214 * Remove the server entry and all clients that this server owns.
1217 SILC_LOG_DEBUG(("SERVER SIGNOFF notify"));
1220 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
1223 server_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1227 /* If the ID is mine, this notify is not allowed. */
1228 if (SILC_ID_SERVER_COMPARE(server_id, server->id)) {
1229 SILC_LOG_DEBUG(("Ignoring my own ID for SERVER_SIGNOFF"));
1233 /* Get server entry */
1234 server_entry = silc_idlist_find_server_by_id(server->global_list,
1235 server_id, TRUE, NULL);
1237 if (!server_entry) {
1238 server_entry = silc_idlist_find_server_by_id(server->local_list,
1239 server_id, TRUE, NULL);
1241 if (!server_entry) {
1242 /* If we are normal server then we might not have the server. Check
1243 whether router was kind enough to send the list of all clients
1244 that actually was to be removed. Remove them if the list is
1246 if (server->server_type != SILC_ROUTER &&
1247 silc_argument_get_arg_num(args) > 1) {
1250 for (i = 1; i < silc_argument_get_arg_num(args); i++) {
1252 tmp = silc_argument_get_arg_type(args, i + 1, &tmp_len);
1255 client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1259 /* Get client entry */
1260 client = silc_idlist_find_client_by_id(server->global_list,
1261 client_id, TRUE, &cache);
1264 client = silc_idlist_find_client_by_id(server->local_list,
1265 client_id, TRUE, &cache);
1268 silc_free(client_id);
1272 silc_free(client_id);
1274 /* Update statistics */
1275 server->stat.clients--;
1276 if (server->stat.cell_clients)
1277 server->stat.cell_clients--;
1278 SILC_OPER_STATS_UPDATE(client, server, SILC_UMODE_SERVER_OPERATOR);
1279 SILC_OPER_STATS_UPDATE(client, router, SILC_UMODE_ROUTER_OPERATOR);
1281 /* Remove the client from all channels. */
1282 silc_server_remove_from_channels(server, NULL, client,
1285 /* Check if anyone is watching this nickname */
1286 if (server->server_type == SILC_ROUTER)
1287 silc_server_check_watcher_list(server, client, NULL,
1288 SILC_NOTIFY_TYPE_SERVER_SIGNOFF);
1290 /* Remove this client from watcher list if it is */
1292 silc_server_del_from_watcher_list(server, client);
1294 /* Remove the client */
1295 silc_idlist_del_data(client);
1296 silc_idlist_del_client(local ? server->local_list :
1297 server->global_list, client);
1301 silc_free(server_id);
1305 silc_free(server_id);
1307 /* Sending SERVER_SIGNOFF is not right way to signoff local connection */
1308 if (SILC_IS_LOCAL(server_entry))
1311 /* Remove all servers that are originated from this server, and
1312 remove the clients of those servers too. */
1313 silc_server_remove_servers_by_server(server, server_entry, TRUE);
1315 /* Remove the clients that this server owns as they will become
1317 silc_server_remove_clients_by_server(server, server_entry->router,
1318 server_entry, TRUE);
1319 silc_server_backup_del(server, server_entry);
1321 /* Remove the server entry */
1322 silc_idlist_del_server(local ? server->local_list :
1323 server->global_list, server_entry);
1325 /* Update statistics */
1326 if (server->server_type == SILC_ROUTER)
1327 server->stat.servers--;
1331 case SILC_NOTIFY_TYPE_KICKED:
1333 * Distribute the notify to local clients on the channel
1336 SILC_LOG_DEBUG(("KICKED notify"));
1339 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
1340 packet->dst_id_type);
1345 /* Get channel entry */
1346 channel = silc_idlist_find_channel_by_id(server->global_list,
1349 channel = silc_idlist_find_channel_by_id(server->local_list,
1352 SILC_LOG_DEBUG(("Notify for unknown channel"));
1353 silc_free(channel_id);
1357 silc_free(channel_id);
1360 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
1363 client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1367 /* If the the client is not in local list we check global list */
1368 client = silc_idlist_find_client_by_id(server->global_list,
1369 client_id, TRUE, NULL);
1371 client = silc_idlist_find_client_by_id(server->local_list,
1372 client_id, TRUE, NULL);
1374 silc_free(client_id);
1378 silc_free(client_id);
1380 /* If target is founder they cannot be kicked */
1381 if (!silc_server_client_on_channel(client, channel, &chl))
1383 if (chl->mode & SILC_CHANNEL_UMODE_CHANFO)
1386 /* Get the kicker's Client ID */
1387 tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
1390 client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1394 /* If the the client is not in local list we check global list */
1395 client2 = silc_idlist_find_client_by_id(server->global_list,
1396 client_id, TRUE, NULL);
1398 client2 = silc_idlist_find_client_by_id(server->local_list,
1399 client_id, TRUE, NULL);
1401 silc_free(client_id);
1405 silc_free(client_id);
1407 /* Kicker must be operator on channel */
1408 if (!silc_server_client_on_channel(client2, channel, &chl))
1410 if (!(chl->mode & SILC_CHANNEL_UMODE_CHANOP) &&
1411 !(chl->mode & SILC_CHANNEL_UMODE_CHANFO)) {
1412 SILC_LOG_DEBUG(("Kicking is not allowed"));
1416 /* Send to channel */
1417 silc_server_packet_send_to_channel(server, sock, channel, packet->type,
1418 FALSE, packet->buffer->data,
1419 packet->buffer->len, FALSE);
1421 /* Remove the client from channel's invite list */
1422 if (channel->invite_list && silc_hash_table_count(channel->invite_list)) {
1424 SilcArgumentPayload iargs;
1425 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
1426 ab = silc_argument_payload_encode_one(NULL, tmp, tmp_len, 3);
1427 iargs = silc_argument_payload_parse(ab->data, ab->len, 1);
1428 silc_server_inviteban_process(server, channel->invite_list, 1, iargs);
1429 silc_buffer_free(ab);
1430 silc_argument_payload_free(iargs);
1433 /* Remove the client from channel */
1434 silc_server_remove_from_one_channel(server, sock, channel, client, FALSE);
1438 case SILC_NOTIFY_TYPE_KILLED:
1441 * Distribute the notify to local clients on channels
1443 unsigned char *id, *comment;
1444 SilcUInt32 id_len, comment_len;
1446 SILC_LOG_DEBUG(("KILLED notify"));
1449 id = silc_argument_get_arg_type(args, 1, &id_len);
1452 client_id = silc_id_payload_parse_id(id, id_len, NULL);
1456 /* If the the client is not in local list we check global list */
1457 client = silc_idlist_find_client_by_id(server->global_list,
1458 client_id, TRUE, &cache);
1460 client = silc_idlist_find_client_by_id(server->local_list,
1461 client_id, TRUE, &cache);
1463 silc_free(client_id);
1467 silc_free(client_id);
1469 /* If the client is one of ours, then close the connection to the
1470 client now. This removes the client from all channels as well. */
1471 if (packet->dst_id_type == SILC_ID_CLIENT && client->connection) {
1472 sock = client->connection;
1473 silc_server_free_client_data(server, NULL, client, FALSE, NULL);
1474 silc_server_close_connection(server, sock);
1479 comment = silc_argument_get_arg_type(args, 2, &comment_len);
1480 if (comment_len > 128)
1483 /* Get the killer's Client ID */
1484 tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
1487 client_id = silc_id_payload_parse_id(tmp, tmp_len, &id_type);
1491 if (id_type == SILC_ID_CLIENT) {
1492 /* If the the client is not in local list we check global list */
1493 client2 = silc_idlist_find_client_by_id(server->global_list,
1494 client_id, TRUE, NULL);
1496 client2 = silc_idlist_find_client_by_id(server->local_list,
1497 client_id, TRUE, NULL);
1499 silc_free(client_id);
1503 silc_free(client_id);
1505 /* Killer must be router operator */
1506 if (server->server_type != SILC_SERVER &&
1507 !(client2->mode & SILC_UMODE_ROUTER_OPERATOR)) {
1508 SILC_LOG_DEBUG(("Killing is not allowed"));
1513 /* Send the notify to local clients on the channels except to the
1514 client who is killed. */
1515 silc_server_send_notify_on_channels(server, client, client,
1516 SILC_NOTIFY_TYPE_KILLED, 3,
1517 id, id_len, comment, comment_len,
1520 /* Remove the client from all channels */
1521 silc_server_remove_from_channels(server, NULL, client, FALSE, NULL,
1524 /* Check if anyone is watching this nickname */
1525 silc_server_check_watcher_list(server, client, NULL,
1526 SILC_NOTIFY_TYPE_KILLED);
1528 /* Update statistics */
1529 server->stat.clients--;
1530 if (server->stat.cell_clients)
1531 server->stat.cell_clients--;
1532 SILC_OPER_STATS_UPDATE(client, server, SILC_UMODE_SERVER_OPERATOR);
1533 SILC_OPER_STATS_UPDATE(client, router, SILC_UMODE_ROUTER_OPERATOR);
1535 if (SILC_IS_LOCAL(client)) {
1536 server->stat.my_clients--;
1537 silc_schedule_task_del_by_context(server->schedule, client);
1538 silc_idlist_del_data(client);
1542 client->data.status &= ~SILC_IDLIST_STATUS_REGISTERED;
1543 cache->expire = SILC_ID_CACHE_EXPIRE_DEF;
1547 case SILC_NOTIFY_TYPE_UMODE_CHANGE:
1549 * Save the mode of the client.
1552 SILC_LOG_DEBUG(("UMODE_CHANGE notify"));
1555 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
1558 client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1562 /* Get client entry */
1563 client = silc_idlist_find_client_by_id(server->global_list,
1564 client_id, TRUE, NULL);
1566 client = silc_idlist_find_client_by_id(server->local_list,
1567 client_id, TRUE, NULL);
1569 silc_free(client_id);
1573 silc_free(client_id);
1576 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
1579 SILC_GET32_MSB(mode, tmp);
1581 /* Remove internal resumed flag if client is marked detached now */
1582 if (mode & SILC_UMODE_DETACHED)
1583 client->data.status &= ~SILC_IDLIST_STATUS_RESUMED;
1585 /* Update statistics */
1586 if (server->server_type == SILC_ROUTER) {
1587 if (mode & SILC_UMODE_GONE) {
1588 if (!(client->mode & SILC_UMODE_GONE))
1589 server->stat.aways++;
1591 if (client->mode & SILC_UMODE_GONE)
1592 server->stat.aways--;
1594 if (mode & SILC_UMODE_DETACHED) {
1595 if (!(client->mode & SILC_UMODE_DETACHED))
1596 server->stat.detached++;
1598 if (client->mode & SILC_UMODE_DETACHED)
1599 server->stat.detached--;
1602 SILC_UMODE_STATS_UPDATE(server, SILC_UMODE_SERVER_OPERATOR);
1603 SILC_UMODE_STATS_UPDATE(router, SILC_UMODE_ROUTER_OPERATOR);
1605 /* Change the mode */
1606 client->mode = mode;
1608 /* Check if anyone is watching this nickname */
1609 if (server->server_type == SILC_ROUTER)
1610 silc_server_check_watcher_list(server, client, NULL,
1611 SILC_NOTIFY_TYPE_UMODE_CHANGE);
1615 case SILC_NOTIFY_TYPE_BAN:
1620 SILC_LOG_DEBUG(("BAN notify"));
1622 /* Get Channel ID */
1623 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
1626 channel_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1630 /* Get channel entry */
1631 channel = silc_idlist_find_channel_by_id(server->global_list,
1634 channel = silc_idlist_find_channel_by_id(server->local_list,
1637 SILC_LOG_DEBUG(("Notify for unknown channel"));
1638 silc_free(channel_id);
1642 silc_free(channel_id);
1644 /* Get the ban action */
1645 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
1646 if (tmp && tmp_len == 1) {
1647 SilcUInt8 action = (SilcUInt8)tmp[0];
1648 SilcUInt16 iargc = 0;
1649 SilcArgumentPayload iargs;
1652 tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
1653 if (!tmp || tmp_len < 2)
1656 /* Parse the arguments to see they are constructed correctly */
1657 SILC_GET16_MSB(iargc, tmp);
1658 iargs = silc_argument_payload_parse(tmp + 2, tmp_len - 2, iargc);
1662 if (action == 0 && !channel->ban_list)
1663 channel->ban_list = silc_hash_table_alloc(0, silc_hash_ptr,
1667 /* Proces the ban action */
1668 silc_server_inviteban_process(server, channel->ban_list, action,
1670 silc_argument_payload_free(iargs);
1674 case SILC_NOTIFY_TYPE_ERROR:
1681 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
1682 if (!tmp && tmp_len != 1)
1684 error = (SilcStatus)tmp[0];
1686 SILC_LOG_DEBUG(("ERROR notify (%d)", error));
1688 if (error == SILC_STATUS_ERR_NO_SUCH_CLIENT_ID &&
1689 sock->type == SILC_SOCKET_TYPE_ROUTER) {
1690 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
1692 SILC_LOG_DEBUG(("Received invalid client ID notification, deleting "
1693 "the entry from cache"));
1694 client_id = silc_id_payload_parse_id(tmp, tmp_len, NULL);
1697 client = silc_idlist_find_client_by_id(server->global_list,
1698 client_id, FALSE, NULL);
1700 silc_server_remove_from_channels(server, NULL, client, TRUE,
1702 silc_idlist_del_data(client);
1703 silc_idlist_del_client(server->global_list, client);
1705 silc_free(client_id);
1711 /* Ignore rest of the notify types for now */
1712 case SILC_NOTIFY_TYPE_NONE:
1713 case SILC_NOTIFY_TYPE_MOTD:
1720 silc_notify_payload_free(payload);
1723 void silc_server_notify_list(SilcServer server,
1724 SilcSocketConnection sock,
1725 SilcPacketContext *packet)
1727 SilcPacketContext *new;
1731 SILC_LOG_DEBUG(("Processing Notify List"));
1733 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
1734 packet->src_id_type != SILC_ID_SERVER)
1737 /* Make copy of the original packet context, except for the actual
1738 data buffer, which we will here now fetch from the original buffer. */
1739 new = silc_packet_context_alloc();
1740 new->type = SILC_PACKET_NOTIFY;
1741 new->flags = packet->flags;
1742 new->src_id = packet->src_id;
1743 new->src_id_len = packet->src_id_len;
1744 new->src_id_type = packet->src_id_type;
1745 new->dst_id = packet->dst_id;
1746 new->dst_id_len = packet->dst_id_len;
1747 new->dst_id_type = packet->dst_id_type;
1749 buffer = silc_buffer_alloc(1024);
1750 new->buffer = buffer;
1752 while (packet->buffer->len) {
1753 SILC_GET16_MSB(len, packet->buffer->data + 2);
1754 if (len > packet->buffer->len)
1757 if (len > buffer->truelen) {
1758 silc_buffer_free(buffer);
1759 buffer = silc_buffer_alloc(1024 + len);
1762 silc_buffer_pull_tail(buffer, len);
1763 silc_buffer_put(buffer, packet->buffer->data, len);
1765 /* Process the Notify */
1766 silc_server_notify(server, sock, new);
1768 silc_buffer_push_tail(buffer, len);
1769 silc_buffer_pull(packet->buffer, len);
1772 silc_buffer_free(buffer);
1776 /* Received private message. This resolves the destination of the message
1777 and sends the packet. This is used by both server and router. If the
1778 destination is our locally connected client this sends the packet to
1779 the client. This may also send the message for further routing if
1780 the destination is not in our server (or router). */
1782 void silc_server_private_message(SilcServer server,
1783 SilcSocketConnection sock,
1784 SilcPacketContext *packet)
1786 SilcSocketConnection dst_sock;
1787 SilcIDListData idata;
1788 SilcClientEntry client;
1790 SILC_LOG_DEBUG(("Start"));
1792 if (packet->src_id_type != SILC_ID_CLIENT ||
1793 packet->dst_id_type != SILC_ID_CLIENT || !packet->dst_id)
1796 /* Get the route to the client */
1797 dst_sock = silc_server_get_client_route(server, packet->dst_id,
1798 packet->dst_id_len, NULL,
1802 unsigned char error;
1804 if (client && client->mode & SILC_UMODE_DETACHED) {
1805 SILC_LOG_DEBUG(("Client is detached, discarding packet"));
1809 /* Send SILC_NOTIFY_TYPE_ERROR to indicate that such destination ID
1810 does not exist or is invalid. */
1811 idp = silc_id_payload_encode_data(packet->dst_id,
1813 packet->dst_id_type);
1817 error = SILC_STATUS_ERR_NO_SUCH_CLIENT_ID;
1818 if (packet->src_id_type == SILC_ID_CLIENT) {
1819 SilcClientID *client_id = silc_id_str2id(packet->src_id,
1821 packet->src_id_type);
1822 silc_server_send_notify_dest(server, sock, FALSE,
1823 client_id, SILC_ID_CLIENT,
1824 SILC_NOTIFY_TYPE_ERROR, 2,
1826 idp->data, idp->len);
1827 silc_free(client_id);
1829 silc_server_send_notify(server, sock, FALSE,
1830 SILC_NOTIFY_TYPE_ERROR, 2,
1832 idp->data, idp->len);
1835 silc_buffer_free(idp);
1839 /* Check whether destination client wishes to receive private messages */
1840 if (client && !(packet->flags & SILC_PACKET_FLAG_PRIVMSG_KEY) &&
1841 client->mode & SILC_UMODE_BLOCK_PRIVMSG) {
1842 SILC_LOG_DEBUG(("Client blocks private messages, discarding packet"));
1846 /* Send the private message */
1847 silc_server_send_private_message(server, dst_sock, idata->send_key,
1848 idata->hmac_send, idata->psn_send++,
1852 /* Received private message key packet.. This packet is never for us. It is to
1853 the client in the packet's destination ID. Sending of this sort of packet
1854 equals sending private message, ie. it is sent point to point from
1855 one client to another. */
1857 void silc_server_private_message_key(SilcServer server,
1858 SilcSocketConnection sock,
1859 SilcPacketContext *packet)
1861 SilcSocketConnection dst_sock;
1862 SilcIDListData idata;
1864 SILC_LOG_DEBUG(("Start"));
1866 if (packet->src_id_type != SILC_ID_CLIENT ||
1867 packet->dst_id_type != SILC_ID_CLIENT)
1870 if (!packet->dst_id)
1873 /* Get the route to the client */
1874 dst_sock = silc_server_get_client_route(server, packet->dst_id,
1875 packet->dst_id_len, NULL,
1880 /* Relay the packet */
1881 silc_server_relay_packet(server, dst_sock, idata->send_key,
1882 idata->hmac_send, idata->psn_send++, packet, FALSE);
1885 /* Processes incoming command reply packet. The command reply packet may
1886 be destined to one of our clients or it may directly for us. We will
1887 call the command reply routine after processing the packet. */
1889 void silc_server_command_reply(SilcServer server,
1890 SilcSocketConnection sock,
1891 SilcPacketContext *packet)
1893 SilcBuffer buffer = packet->buffer;
1894 SilcClientEntry client = NULL;
1895 SilcSocketConnection dst_sock;
1896 SilcIDListData idata;
1897 SilcClientID *id = NULL;
1899 SILC_LOG_DEBUG(("Start"));
1901 if (packet->dst_id_type == SILC_ID_CHANNEL)
1904 if (packet->dst_id_type == SILC_ID_CLIENT) {
1905 /* Destination must be one of ours */
1906 id = silc_id_str2id(packet->dst_id, packet->dst_id_len, SILC_ID_CLIENT);
1909 client = silc_idlist_find_client_by_id(server->local_list, id, TRUE, NULL);
1911 SILC_LOG_ERROR(("Cannot process command reply to unknown client"));
1917 if (packet->dst_id_type == SILC_ID_SERVER) {
1918 /* For now this must be for us */
1919 if (memcmp(packet->dst_id, server->id_string, server->id_string_len)) {
1920 SILC_LOG_ERROR(("Cannot process command reply to unknown server"));
1925 /* Execute command reply locally for the command */
1926 silc_server_command_reply_process(server, sock, buffer);
1928 if (packet->dst_id_type == SILC_ID_CLIENT && client && id) {
1929 /* Relay the packet to the client */
1930 const SilcBufferStruct p;
1932 dst_sock = (SilcSocketConnection)client->connection;
1933 idata = (SilcIDListData)client;
1935 silc_buffer_push(buffer, SILC_PACKET_HEADER_LEN + packet->src_id_len
1936 + packet->dst_id_len + packet->padlen);
1937 if (!silc_packet_send_prepare(dst_sock, 0, 0, buffer->len,
1938 idata->hmac_send, (const SilcBuffer)&p)) {
1939 SILC_LOG_ERROR(("Cannot send packet"));
1942 silc_buffer_put((SilcBuffer)&p, buffer->data, buffer->len);
1944 /* Encrypt packet */
1945 silc_packet_encrypt(idata->send_key, idata->hmac_send, idata->psn_send++,
1946 (SilcBuffer)&p, buffer->len);
1948 /* Send the packet */
1949 silc_server_packet_send_real(server, dst_sock, TRUE);
1955 /* Process received channel message. The message can be originated from
1956 client or server. */
1958 void silc_server_channel_message(SilcServer server,
1959 SilcSocketConnection sock,
1960 SilcPacketContext *packet)
1962 SilcChannelEntry channel = NULL;
1963 SilcChannelID *id = NULL;
1964 void *sender_id = NULL;
1965 SilcClientEntry sender_entry = NULL;
1966 SilcChannelClientEntry chl;
1969 SILC_LOG_DEBUG(("Processing channel message"));
1972 if (packet->dst_id_type != SILC_ID_CHANNEL) {
1973 SILC_LOG_DEBUG(("Received bad message for channel, dropped"));
1977 /* Find channel entry */
1978 id = silc_id_str2id(packet->dst_id, packet->dst_id_len, SILC_ID_CHANNEL);
1981 channel = silc_idlist_find_channel_by_id(server->local_list, id, NULL);
1983 channel = silc_idlist_find_channel_by_id(server->global_list, id, NULL);
1986 unsigned char error;
1988 /* Send SILC_NOTIFY_TYPE_ERROR to indicate that such destination ID
1989 does not exist or is invalid. */
1990 idp = silc_id_payload_encode_data(packet->dst_id,
1992 packet->dst_id_type);
1996 error = SILC_STATUS_ERR_NO_SUCH_CHANNEL_ID;
1997 if (packet->src_id_type == SILC_ID_CLIENT) {
1998 SilcClientID *client_id = silc_id_str2id(packet->src_id,
2000 packet->src_id_type);
2001 silc_server_send_notify_dest(server, sock, FALSE,
2002 client_id, SILC_ID_CLIENT,
2003 SILC_NOTIFY_TYPE_ERROR, 2,
2004 &error, 1, idp->data, idp->len);
2005 silc_free(client_id);
2007 silc_server_send_notify(server, sock, FALSE,
2008 SILC_NOTIFY_TYPE_ERROR, 2,
2009 &error, 1, idp->data, idp->len);
2012 silc_buffer_free(idp);
2017 /* See that this client is on the channel. If the original sender is
2018 not client (as it can be server as well) we don't do the check. */
2019 sender_id = silc_id_str2id(packet->src_id, packet->src_id_len,
2020 packet->src_id_type);
2023 if (packet->src_id_type == SILC_ID_CLIENT) {
2024 sender_entry = silc_idlist_find_client_by_id(server->local_list,
2025 sender_id, TRUE, NULL);
2026 if (!sender_entry) {
2028 sender_entry = silc_idlist_find_client_by_id(server->global_list,
2029 sender_id, TRUE, NULL);
2031 if (!sender_entry || !silc_server_client_on_channel(sender_entry,
2033 SILC_LOG_DEBUG(("Client not on channel"));
2037 /* If channel is moderated check that client is allowed to send
2039 if (channel->mode & SILC_CHANNEL_MODE_SILENCE_USERS &&
2040 !(chl->mode & SILC_CHANNEL_UMODE_CHANOP) &&
2041 !(chl->mode & SILC_CHANNEL_UMODE_CHANFO)) {
2042 SILC_LOG_DEBUG(("Channel is silenced from normal users"));
2045 if (channel->mode & SILC_CHANNEL_MODE_SILENCE_OPERS &&
2046 chl->mode & SILC_CHANNEL_UMODE_CHANOP &&
2047 !(chl->mode & SILC_CHANNEL_UMODE_CHANFO)) {
2048 SILC_LOG_DEBUG(("Channel is silenced from operators"));
2051 if (chl->mode & SILC_CHANNEL_UMODE_QUIET) {
2052 SILC_LOG_DEBUG(("Sender is quieted on the channel"));
2056 /* If the packet is coming from router, but the client entry is local
2057 entry to us then some router is rerouting this to us and it is not
2058 allowed. When the client is local to us it means that we've routed
2059 this packet to network, and now someone is routing it back to us. */
2060 if (server->server_type == SILC_ROUTER &&
2061 sock->type == SILC_SOCKET_TYPE_ROUTER && local) {
2062 SILC_LOG_DEBUG(("Channel message rerouted to the sender, drop it"));
2067 /* Distribute the packet to our local clients. This will send the
2068 packet for further routing as well, if needed. */
2069 silc_server_packet_relay_to_channel(server, sock, channel, sender_id,
2070 packet->src_id_type, sender_entry,
2071 packet->buffer->data,
2072 packet->buffer->len, FALSE);
2075 silc_free(sender_id);
2079 /* Received channel key packet. We distribute the key to all of our locally
2080 connected clients on the channel. */
2082 void silc_server_channel_key(SilcServer server,
2083 SilcSocketConnection sock,
2084 SilcPacketContext *packet)
2086 SilcBuffer buffer = packet->buffer;
2087 SilcChannelEntry channel;
2089 if (packet->src_id_type != SILC_ID_SERVER ||
2090 (server->server_type == SILC_ROUTER && !server->backup_router &&
2091 sock->type == SILC_SOCKET_TYPE_ROUTER))
2094 /* Save the channel key */
2095 channel = silc_server_save_channel_key(server, buffer, NULL);
2099 /* Distribute the key to everybody who is on the channel. If we are router
2100 we will also send it to locally connected servers. */
2101 silc_server_send_channel_key(server, sock, channel, FALSE);
2103 if (server->server_type != SILC_BACKUP_ROUTER) {
2104 /* Distribute to local cell backup routers. */
2105 silc_server_backup_send(server, sock->user_data,
2106 SILC_PACKET_CHANNEL_KEY, 0,
2107 buffer->data, buffer->len, FALSE, TRUE);
2111 /* Received New Client packet and processes it. Creates Client ID for the
2112 client. Client becomes registered after calling this functions. */
2114 SilcClientEntry silc_server_new_client(SilcServer server,
2115 SilcSocketConnection sock,
2116 SilcPacketContext *packet)
2118 SilcBuffer buffer = packet->buffer;
2119 SilcClientEntry client;
2120 SilcClientID *client_id;
2121 SilcIDListData idata;
2122 char *username = NULL, *realname = NULL;
2123 SilcUInt16 username_len;
2126 char *hostname, *nickname;
2129 SILC_LOG_DEBUG(("Creating new client"));
2131 if (sock->type != SILC_SOCKET_TYPE_CLIENT)
2134 /* Take client entry */
2135 client = (SilcClientEntry)sock->user_data;
2136 idata = (SilcIDListData)client;
2138 /* Remove the old cache entry. */
2139 if (!silc_idcache_del_by_context(server->local_list->clients, client)) {
2140 SILC_LOG_INFO(("Unauthenticated client attempted to register to network"));
2141 silc_server_disconnect_remote(server, sock,
2142 SILC_STATUS_ERR_NOT_AUTHENTICATED, NULL);
2143 if (sock->user_data)
2144 silc_server_free_sock_user_data(server, sock, NULL);
2148 /* Parse incoming packet */
2149 ret = silc_buffer_unformat(buffer,
2150 SILC_STR_UI16_NSTRING_ALLOC(&username,
2152 SILC_STR_UI16_STRING_ALLOC(&realname),
2155 silc_free(username);
2156 silc_free(realname);
2157 SILC_LOG_ERROR(("Client %s (%s) sent incomplete information, closing "
2158 "connection", sock->hostname, sock->ip));
2159 silc_server_disconnect_remote(server, sock,
2160 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
2162 if (sock->user_data)
2163 silc_server_free_sock_user_data(server, sock, NULL);
2168 silc_free(username);
2169 silc_free(realname);
2170 SILC_LOG_ERROR(("Client %s (%s) did not send its username, closing "
2171 "connection", sock->hostname, sock->ip));
2172 silc_server_disconnect_remote(server, sock,
2173 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
2175 if (sock->user_data)
2176 silc_server_free_sock_user_data(server, sock, NULL);
2180 if (username_len > 128)
2181 username[128] = '\0';
2183 /* Check for bad characters for nickname, and modify the nickname if
2184 it includes those. */
2185 if (silc_server_name_bad_chars(username, username_len)) {
2186 nickname = silc_server_name_modify_bad(username, username_len);
2188 nickname = strdup(username);
2191 /* Make sanity checks for the hostname of the client. If the hostname
2192 is provided in the `username' check that it is the same than the
2193 resolved hostname, or if not resolved the hostname that appears in
2194 the client's public key. If the hostname is not present then put
2195 it from the resolved name or from the public key. */
2196 if (strchr(username, '@')) {
2197 SilcPublicKeyIdentifier pident;
2198 int tlen = strcspn(username, "@");
2199 char *phostname = NULL;
2201 hostname = silc_memdup(username + tlen + 1, strlen(username) - tlen - 1);
2203 if (strcmp(sock->hostname, sock->ip) &&
2204 strcmp(sock->hostname, hostname)) {
2205 silc_free(username);
2206 silc_free(hostname);
2207 silc_free(realname);
2208 SILC_LOG_ERROR(("Client %s (%s) sent incomplete information, closing "
2209 "connection", sock->hostname, sock->ip));
2210 silc_server_disconnect_remote(server, sock,
2211 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
2213 if (sock->user_data)
2214 silc_server_free_sock_user_data(server, sock, NULL);
2218 pident = silc_pkcs_decode_identifier(client->data.public_key->identifier);
2220 phostname = strdup(pident->host);
2221 silc_pkcs_free_identifier(pident);
2224 if (!strcmp(sock->hostname, sock->ip) &&
2225 phostname && strcmp(phostname, hostname)) {
2226 silc_free(username);
2227 silc_free(hostname);
2228 silc_free(phostname);
2229 silc_free(realname);
2230 SILC_LOG_ERROR(("Client %s (%s) sent incomplete information, closing "
2231 "connection", sock->hostname, sock->ip));
2232 silc_server_disconnect_remote(server, sock,
2233 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
2235 if (sock->user_data)
2236 silc_server_free_sock_user_data(server, sock, NULL);
2240 silc_free(phostname);
2242 /* The hostname is not present, add it. */
2244 /* XXX For now we cannot take the host name from the public key since
2245 they are not trusted or we cannot verify them as trusted. Just take
2246 what the resolved name or address is. */
2248 if (strcmp(sock->hostname, sock->ip)) {
2250 newusername = silc_calloc(strlen(username) +
2251 strlen(sock->hostname) + 2,
2252 sizeof(*newusername));
2253 strncat(newusername, username, strlen(username));
2254 strncat(newusername, "@", 1);
2255 strncat(newusername, sock->hostname, strlen(sock->hostname));
2256 silc_free(username);
2257 username = newusername;
2260 SilcPublicKeyIdentifier pident =
2261 silc_pkcs_decode_identifier(client->data.public_key->identifier);
2264 newusername = silc_calloc(strlen(username) +
2265 strlen(pident->host) + 2,
2266 sizeof(*newusername));
2267 strncat(newusername, username, strlen(username));
2268 strncat(newusername, "@", 1);
2269 strncat(newusername, pident->host, strlen(pident->host));
2270 silc_free(username);
2271 username = newusername;
2272 silc_pkcs_free_identifier(pident);
2278 /* Create Client ID */
2279 while (!silc_id_create_client_id(server, server->id, server->rng,
2280 server->md5hash, nickname, &client_id)) {
2283 silc_server_disconnect_remote(server, sock,
2284 SILC_STATUS_ERR_BAD_NICKNAME, NULL);
2285 if (sock->user_data)
2286 silc_server_free_sock_user_data(server, sock, NULL);
2289 snprintf(&nickname[strlen(nickname) - 1], 1, "%d", nickfail);
2292 /* If client marked as anonymous, scramble the username and hostname */
2293 if (client->mode & SILC_UMODE_ANONYMOUS) {
2296 if (strlen(username) >= 2) {
2297 username[0] = silc_rng_get_byte_fast(server->rng);
2298 username[1] = silc_rng_get_byte_fast(server->rng);
2301 scramble = silc_hash_babbleprint(server->sha1hash, username,
2305 memcpy(&scramble[16], ".silc", 5);
2306 scramble[21] = '\0';
2307 silc_free(username);
2308 username = scramble;
2311 /* Update client entry */
2312 idata->status |= SILC_IDLIST_STATUS_REGISTERED;
2313 client->nickname = nickname;
2314 client->username = username;
2315 client->userinfo = realname ? realname : strdup(username);
2316 client->id = client_id;
2317 id_len = silc_id_get_len(client_id, SILC_ID_CLIENT);
2319 /* Add the client again to the ID cache */
2320 silc_idcache_add(server->local_list->clients, client->nickname,
2321 client_id, client, 0, NULL);
2323 /* Notify our router about new client on the SILC network */
2324 silc_server_send_new_id(server, SILC_PRIMARY_ROUTE(server),
2325 SILC_BROADCAST(server), client->id,
2326 SILC_ID_CLIENT, id_len);
2328 /* Distribute to backup routers */
2329 if (server->server_type == SILC_ROUTER) {
2330 SilcBuffer idp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
2331 silc_server_backup_send(server, sock->user_data, SILC_PACKET_NEW_ID, 0,
2332 idp->data, idp->len, FALSE, TRUE);
2333 silc_buffer_free(idp);
2336 /* Send the new client ID to the client. */
2337 silc_server_send_new_id(server, sock, FALSE, client->id, SILC_ID_CLIENT,
2338 silc_id_get_len(client->id, SILC_ID_CLIENT));
2340 /* Send some nice info to the client */
2341 silc_server_send_connect_notifys(server, sock, client);
2343 /* Check if anyone is watching this nickname */
2344 if (server->server_type == SILC_ROUTER)
2345 silc_server_check_watcher_list(server, client, NULL, 0);
2350 /* Create new server. This processes received New Server packet and
2351 saves the received Server ID. The server is our locally connected
2352 server thus we save all the information and save it to local list.
2353 This funtion can be used by both normal server and router server.
2354 If normal server uses this it means that its router has connected
2355 to the server. If router uses this it means that one of the cell's
2356 servers is connected to the router. */
2358 SilcServerEntry silc_server_new_server(SilcServer server,
2359 SilcSocketConnection sock,
2360 SilcPacketContext *packet)
2362 SilcBuffer buffer = packet->buffer;
2363 SilcServerEntry new_server, server_entry;
2364 SilcServerID *server_id;
2365 SilcIDListData idata;
2366 unsigned char *server_name, *id_string;
2367 SilcUInt16 id_len, name_len;
2371 SILC_LOG_DEBUG(("Creating new server"));
2373 if (sock->type != SILC_SOCKET_TYPE_SERVER &&
2374 sock->type != SILC_SOCKET_TYPE_ROUTER)
2377 /* Take server entry */
2378 new_server = (SilcServerEntry)sock->user_data;
2379 idata = (SilcIDListData)new_server;
2381 /* Remove the old cache entry */
2382 if (!silc_idcache_del_by_context(server->local_list->servers, new_server)) {
2383 if (!silc_idcache_del_by_context(server->global_list->servers,
2385 SILC_LOG_INFO(("Unauthenticated %s attempted to register to "
2386 "network", (sock->type == SILC_SOCKET_TYPE_SERVER ?
2387 "server" : "router")));
2388 silc_server_disconnect_remote(server, sock,
2389 SILC_STATUS_ERR_NOT_AUTHENTICATED, NULL);
2390 if (sock->user_data)
2391 silc_server_free_sock_user_data(server, sock, NULL);
2397 /* Parse the incoming packet */
2398 ret = silc_buffer_unformat(buffer,
2399 SILC_STR_UI16_NSTRING_ALLOC(&id_string, &id_len),
2400 SILC_STR_UI16_NSTRING_ALLOC(&server_name,
2404 silc_free(id_string);
2405 silc_free(server_name);
2406 silc_server_disconnect_remote(server, sock,
2407 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
2409 if (sock->user_data)
2410 silc_server_free_sock_user_data(server, sock, NULL);
2414 if (id_len > buffer->len) {
2415 silc_free(id_string);
2416 silc_free(server_name);
2417 silc_server_disconnect_remote(server, sock,
2418 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
2420 if (sock->user_data)
2421 silc_server_free_sock_user_data(server, sock, NULL);
2426 server_name[255] = '\0';
2429 server_id = silc_id_str2id(id_string, id_len, SILC_ID_SERVER);
2431 silc_free(id_string);
2432 silc_free(server_name);
2433 silc_server_disconnect_remote(server, sock,
2434 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
2436 if (sock->user_data)
2437 silc_server_free_sock_user_data(server, sock, NULL);
2440 silc_free(id_string);
2442 /* Check for valid server ID */
2443 if (!silc_id_is_valid_server_id(server, server_id, sock)) {
2444 SILC_LOG_INFO(("Invalid server ID sent by %s (%s)",
2445 sock->ip, sock->hostname));
2446 silc_server_disconnect_remote(server, sock,
2447 SILC_STATUS_ERR_BAD_SERVER_ID, NULL);
2448 if (sock->user_data)
2449 silc_server_free_sock_user_data(server, sock, NULL);
2450 silc_free(server_name);
2454 /* Check that we do not have this ID already */
2455 server_entry = silc_idlist_find_server_by_id(server->local_list,
2456 server_id, TRUE, NULL);
2458 silc_idcache_del_by_context(server->local_list->servers, server_entry);
2460 server_entry = silc_idlist_find_server_by_id(server->global_list,
2461 server_id, TRUE, NULL);
2463 silc_idcache_del_by_context(server->global_list->servers, server_entry);
2466 /* Update server entry */
2467 idata->status |= SILC_IDLIST_STATUS_REGISTERED;
2468 new_server->server_name = server_name;
2469 new_server->id = server_id;
2471 SILC_LOG_DEBUG(("New server id(%s)",
2472 silc_id_render(server_id, SILC_ID_SERVER)));
2474 /* Add again the entry to the ID cache. */
2475 silc_idcache_add(local ? server->local_list->servers :
2476 server->global_list->servers, server_name, server_id,
2477 new_server, 0, NULL);
2479 /* Distribute the information about new server in the SILC network
2480 to our router. If we are normal server we won't send anything
2481 since this connection must be our router connection. */
2482 if (server->server_type == SILC_ROUTER && !server->standalone &&
2483 SILC_PRIMARY_ROUTE(server) != sock)
2484 silc_server_send_new_id(server, SILC_PRIMARY_ROUTE(server),
2485 TRUE, new_server->id, SILC_ID_SERVER,
2486 silc_id_get_len(server_id, SILC_ID_SERVER));
2488 if (server->server_type == SILC_ROUTER) {
2489 /* Distribute to backup routers */
2490 SilcBuffer idp = silc_id_payload_encode(new_server->id, SILC_ID_SERVER);
2491 silc_server_backup_send(server, sock->user_data, SILC_PACKET_NEW_ID, 0,
2492 idp->data, idp->len, FALSE, TRUE);
2493 silc_buffer_free(idp);
2496 server->stat.cell_servers++;
2499 /* Check whether this router connection has been replaced by an
2500 backup router. If it has been then we'll disable the server and will
2501 ignore everything it will send until the backup router resuming
2502 protocol has been completed. */
2503 if (sock->type == SILC_SOCKET_TYPE_ROUTER &&
2504 silc_server_backup_replaced_get(server, server_id, NULL)) {
2505 /* Send packet to the server indicating that it cannot use this
2506 connection as it has been replaced by backup router. */
2507 SilcBuffer packet = silc_buffer_alloc(2);
2508 silc_buffer_pull_tail(packet, SILC_BUFFER_END(packet));
2509 silc_buffer_format(packet,
2510 SILC_STR_UI_CHAR(SILC_SERVER_BACKUP_REPLACED),
2511 SILC_STR_UI_CHAR(0),
2513 silc_server_packet_send(server, sock,
2514 SILC_PACKET_RESUME_ROUTER, 0,
2515 packet->data, packet->len, TRUE);
2516 silc_buffer_free(packet);
2518 /* Mark the router disabled. The data sent earlier will go but nothing
2519 after this does not go to this connection. */
2520 idata->status |= SILC_IDLIST_STATUS_DISABLED;
2522 /* If it is router announce our stuff to it. */
2523 if (sock->type == SILC_SOCKET_TYPE_ROUTER &&
2524 server->server_type == SILC_ROUTER) {
2525 silc_server_announce_servers(server, FALSE, 0, sock);
2526 silc_server_announce_clients(server, 0, sock);
2527 silc_server_announce_channels(server, 0, sock);
2530 /* Announce our information to backup router */
2531 if (new_server->server_type == SILC_BACKUP_ROUTER &&
2532 sock->type == SILC_SOCKET_TYPE_SERVER &&
2533 server->server_type == SILC_ROUTER) {
2534 silc_server_announce_servers(server, TRUE, 0, sock);
2535 silc_server_announce_clients(server, 0, sock);
2536 silc_server_announce_channels(server, 0, sock);
2539 /* If backup router, mark it as one of ours. This server is considered
2540 to be backup router after this setting. */
2541 if (new_server->server_type == SILC_BACKUP_ROUTER) {
2542 SilcServerConfigRouter *backup;
2543 backup = silc_server_config_find_backup_conn(server, sock->ip);
2545 backup = silc_server_config_find_backup_conn(server, sock->hostname);
2547 /* Add as our backup router */
2548 silc_server_backup_add(server, new_server, backup->backup_replace_ip,
2549 backup->backup_replace_port,
2550 backup->backup_local);
2554 /* By default the servers connected to backup router are disabled
2555 until backup router has become the primary */
2556 if (server->server_type == SILC_BACKUP_ROUTER &&
2557 sock->type == SILC_SOCKET_TYPE_SERVER)
2558 idata->status |= SILC_IDLIST_STATUS_DISABLED;
2564 /* Processes incoming New ID packet. New ID Payload is used to distribute
2565 information about newly registered clients and servers. */
2567 static void silc_server_new_id_real(SilcServer server,
2568 SilcSocketConnection sock,
2569 SilcPacketContext *packet,
2572 SilcBuffer buffer = packet->buffer;
2574 SilcServerEntry router, server_entry;
2575 SilcSocketConnection router_sock;
2580 SILC_LOG_DEBUG(("Processing new ID"));
2582 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
2583 server->server_type == SILC_SERVER ||
2584 packet->src_id_type != SILC_ID_SERVER)
2587 idp = silc_id_payload_parse(buffer->data, buffer->len);
2591 id_type = silc_id_payload_get_type(idp);
2593 /* Normal server cannot have other normal server connections */
2594 server_entry = (SilcServerEntry)sock->user_data;
2595 if (id_type == SILC_ID_SERVER && sock->type == SILC_SOCKET_TYPE_SERVER &&
2596 server_entry->server_type == SILC_SERVER)
2599 id = silc_id_payload_get_id(idp);
2603 /* If the packet is coming from server then use the sender as the
2604 origin of the the packet. If it came from router then check the real
2605 sender of the packet and use that as the origin. */
2606 if (sock->type == SILC_SOCKET_TYPE_SERVER) {
2607 id_list = server->local_list;
2609 router = sock->user_data;
2611 /* If the sender is backup router and ID is server (and we are not
2612 backup router) then switch the entry to global list. */
2613 if (server_entry->server_type == SILC_BACKUP_ROUTER &&
2614 id_type == SILC_ID_SERVER &&
2615 server->id_entry->server_type != SILC_BACKUP_ROUTER) {
2616 id_list = server->global_list;
2617 router_sock = server->router ? SILC_PRIMARY_ROUTE(server) : sock;
2620 void *sender_id = silc_id_str2id(packet->src_id, packet->src_id_len,
2621 packet->src_id_type);
2622 router = silc_idlist_find_server_by_id(server->global_list,
2623 sender_id, TRUE, NULL);
2625 router = silc_idlist_find_server_by_id(server->local_list,
2626 sender_id, TRUE, NULL);
2627 silc_free(sender_id);
2629 id_list = server->global_list;
2636 case SILC_ID_CLIENT:
2638 SilcClientEntry entry;
2640 /* Check that we do not have this client already */
2641 entry = silc_idlist_find_client_by_id(server->global_list,
2642 id, server->server_type,
2645 entry = silc_idlist_find_client_by_id(server->local_list,
2646 id, server->server_type,
2649 SILC_LOG_DEBUG(("Ignoring client that we already have"));
2653 SILC_LOG_DEBUG(("New client id(%s) from [%s] %s",
2654 silc_id_render(id, SILC_ID_CLIENT),
2655 sock->type == SILC_SOCKET_TYPE_SERVER ?
2656 "Server" : "Router", sock->hostname));
2658 /* As a router we keep information of all global information in our
2659 global list. Cell wide information however is kept in the local
2661 entry = silc_idlist_add_client(id_list, NULL, NULL, NULL,
2662 id, router, NULL, 0);
2664 SILC_LOG_ERROR(("Could not add new client to the ID Cache"));
2666 /* Inform the sender that the ID is not usable */
2667 silc_server_send_notify_signoff(server, sock, FALSE, id, NULL);
2670 entry->nickname = NULL;
2671 entry->data.status |= SILC_IDLIST_STATUS_REGISTERED;
2673 if (sock->type == SILC_SOCKET_TYPE_SERVER)
2674 server->stat.cell_clients++;
2675 server->stat.clients++;
2677 /* Check if anyone is watching this nickname */
2678 if (server->server_type == SILC_ROUTER && id_list == server->local_list)
2679 silc_server_check_watcher_list(server, entry, NULL, 0);
2683 case SILC_ID_SERVER:
2685 SilcServerEntry entry;
2687 /* If the ID is mine, ignore it. */
2688 if (SILC_ID_SERVER_COMPARE(id, server->id)) {
2689 SILC_LOG_DEBUG(("Ignoring my own ID as new ID"));
2693 /* If the ID is the sender's ID, ignore it (we have it already) */
2694 if (SILC_ID_SERVER_COMPARE(id, router->id)) {
2695 SILC_LOG_DEBUG(("Ignoring sender's own ID"));
2699 /* Check that we do not have this server already */
2700 entry = silc_idlist_find_server_by_id(server->global_list,
2701 id, server->server_type,
2704 entry = silc_idlist_find_server_by_id(server->local_list,
2705 id, server->server_type,
2708 SILC_LOG_DEBUG(("Ignoring server that we already have"));
2712 SILC_LOG_DEBUG(("New server id(%s) from [%s] %s",
2713 silc_id_render(id, SILC_ID_SERVER),
2714 sock->type == SILC_SOCKET_TYPE_SERVER ?
2715 "Server" : "Router", sock->hostname));
2717 /* As a router we keep information of all global information in our
2718 global list. Cell wide information however is kept in the local
2720 entry = silc_idlist_add_server(id_list, NULL, 0, id, router,
2723 SILC_LOG_ERROR(("Could not add new server to the ID Cache"));
2726 entry->data.status |= SILC_IDLIST_STATUS_REGISTERED;
2728 if (sock->type == SILC_SOCKET_TYPE_SERVER)
2729 server->stat.cell_servers++;
2730 server->stat.servers++;
2734 case SILC_ID_CHANNEL:
2735 SILC_LOG_ERROR(("Channel cannot be registered with NEW_ID packet"));
2744 /* If the sender of this packet is server and we are router we need to
2745 broadcast this packet to other routers in the network. */
2746 if (broadcast && server->server_type == SILC_ROUTER &&
2747 sock->type == SILC_SOCKET_TYPE_SERVER &&
2748 !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
2749 SILC_LOG_DEBUG(("Broadcasting received New ID packet"));
2750 silc_server_packet_send(server, SILC_PRIMARY_ROUTE(server),
2752 packet->flags | SILC_PACKET_FLAG_BROADCAST,
2753 buffer->data, buffer->len, FALSE);
2754 silc_server_backup_send(server, sock->user_data,
2755 packet->type, packet->flags,
2756 packet->buffer->data, packet->buffer->len,
2761 silc_id_payload_free(idp);
2765 /* Processes incoming New ID packet. New ID Payload is used to distribute
2766 information about newly registered clients and servers. */
2768 void silc_server_new_id(SilcServer server, SilcSocketConnection sock,
2769 SilcPacketContext *packet)
2771 silc_server_new_id_real(server, sock, packet, TRUE);
2774 /* Receoved New Id List packet, list of New ID payloads inside one
2775 packet. Process the New ID payloads one by one. */
2777 void silc_server_new_id_list(SilcServer server, SilcSocketConnection sock,
2778 SilcPacketContext *packet)
2780 SilcPacketContext *new_id;
2784 SILC_LOG_DEBUG(("Processing New ID List"));
2786 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
2787 packet->src_id_type != SILC_ID_SERVER)
2790 /* If the sender of this packet is server and we are router we need to
2791 broadcast this packet to other routers in the network. Broadcast
2792 this list packet instead of multiple New ID packets. */
2793 if (server->server_type == SILC_ROUTER &&
2794 sock->type == SILC_SOCKET_TYPE_SERVER &&
2795 !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
2796 SILC_LOG_DEBUG(("Broadcasting received New ID List packet"));
2797 silc_server_packet_send(server, SILC_PRIMARY_ROUTE(server),
2799 packet->flags | SILC_PACKET_FLAG_BROADCAST,
2800 packet->buffer->data,
2801 packet->buffer->len, FALSE);
2802 silc_server_backup_send(server, sock->user_data,
2803 packet->type, packet->flags,
2804 packet->buffer->data, packet->buffer->len,
2808 /* Make copy of the original packet context, except for the actual
2809 data buffer, which we will here now fetch from the original buffer. */
2810 new_id = silc_packet_context_alloc();
2811 new_id->type = SILC_PACKET_NEW_ID;
2812 new_id->flags = packet->flags & (~SILC_PACKET_FLAG_LIST);
2813 new_id->src_id = packet->src_id;
2814 new_id->src_id_len = packet->src_id_len;
2815 new_id->src_id_type = packet->src_id_type;
2816 new_id->dst_id = packet->dst_id;
2817 new_id->dst_id_len = packet->dst_id_len;
2818 new_id->dst_id_type = packet->dst_id_type;
2820 idp = silc_buffer_alloc(256);
2821 new_id->buffer = idp;
2823 while (packet->buffer->len) {
2824 SILC_GET16_MSB(id_len, packet->buffer->data + 2);
2825 if ((id_len > packet->buffer->len) ||
2826 (id_len > idp->truelen))
2829 silc_buffer_pull_tail(idp, 4 + id_len);
2830 silc_buffer_put(idp, packet->buffer->data, 4 + id_len);
2832 /* Process the New ID */
2833 silc_server_new_id_real(server, sock, new_id, FALSE);
2835 silc_buffer_push_tail(idp, 4 + id_len);
2836 silc_buffer_pull(packet->buffer, 4 + id_len);
2839 silc_buffer_free(idp);
2843 /* Received New Channel packet. Information about new channels in the
2844 network are distributed using this packet. Save the information about
2845 the new channel. This usually comes from router but also normal server
2846 can send this to notify channels it has when it connects to us. */
2848 void silc_server_new_channel(SilcServer server,
2849 SilcSocketConnection sock,
2850 SilcPacketContext *packet)
2852 SilcChannelPayload payload;
2853 SilcChannelID *channel_id;
2855 SilcUInt32 name_len;
2857 SilcUInt32 id_len, cipher_len;
2858 SilcServerEntry server_entry;
2859 SilcChannelEntry channel;
2862 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
2863 packet->src_id_type != SILC_ID_SERVER ||
2864 server->server_type == SILC_SERVER)
2867 /* Parse the channel payload */
2868 payload = silc_channel_payload_parse(packet->buffer->data,
2869 packet->buffer->len);
2873 /* Get the channel ID */
2874 channel_id = silc_channel_get_id_parse(payload);
2876 silc_channel_payload_free(payload);
2880 channel_name = silc_channel_get_name(payload, &name_len);
2882 channel_name[255] = '\0';
2884 id = silc_channel_get_id(payload, &id_len);
2886 server_entry = (SilcServerEntry)sock->user_data;
2888 if (sock->type == SILC_SOCKET_TYPE_ROUTER) {
2889 /* Add the channel to global list as it is coming from router. It
2890 cannot be our own channel as it is coming from router. */
2892 /* Check that we don't already have this channel */
2893 channel = silc_idlist_find_channel_by_name(server->local_list,
2894 channel_name, NULL);
2896 channel = silc_idlist_find_channel_by_name(server->global_list,
2897 channel_name, NULL);
2899 SILC_LOG_DEBUG(("New channel id(%s) from [Router] %s",
2900 silc_id_render(channel_id, SILC_ID_CHANNEL),
2904 silc_idlist_add_channel(server->global_list, strdup(channel_name),
2905 0, channel_id, sock->user_data, NULL, NULL, 0);
2907 silc_channel_payload_free(payload);
2908 silc_free(channel_id);
2911 channel->disabled = TRUE; /* Disabled until someone JOINs */
2913 server->stat.channels++;
2914 if (server->server_type == SILC_ROUTER)
2915 channel->users_resolved = TRUE;
2918 /* The channel is coming from our server, thus it is in our cell
2919 we will add it to our local list. */
2922 SILC_LOG_DEBUG(("Channel id(%s) from [Server] %s",
2923 silc_id_render(channel_id, SILC_ID_CHANNEL),
2926 /* Check that we don't already have this channel */
2927 channel = silc_idlist_find_channel_by_name(server->local_list,
2928 channel_name, NULL);
2930 channel = silc_idlist_find_channel_by_name(server->global_list,
2931 channel_name, NULL);
2933 /* If the channel does not exist, then create it. This creates a new
2934 key to the channel as well that we will send to the server. */
2936 SILC_LOG_DEBUG(("Channel is new to us"));
2938 /* The protocol says that the Channel ID's IP address must be based
2939 on the router's IP address. Check whether the ID is based in our
2940 IP and if it is not then create a new ID and enforce the server
2941 to switch the ID. */
2942 if (server_entry->server_type != SILC_BACKUP_ROUTER &&
2943 !SILC_ID_COMPARE(channel_id, server->id, server->id->ip.data_len)) {
2945 SILC_LOG_DEBUG(("Forcing the server to change Channel ID"));
2946 if (silc_id_create_channel_id(server, server->id, server->rng, &tmp)) {
2947 silc_server_send_notify_channel_change(server, sock, FALSE,
2949 silc_channel_payload_free(payload);
2950 silc_free(channel_id);
2954 /* Wait that server re-announces this channel */
2958 /* Create the channel with the provided Channel ID */
2959 channel = silc_server_create_new_channel_with_id(server, NULL, NULL,
2963 silc_channel_payload_free(payload);
2964 silc_free(channel_id);
2967 channel->disabled = TRUE; /* Disabled until someone JOINs */
2969 #if 0 /* We assume that CMODE_CHANGE notify is sent to us after this. */
2971 /* XXX Dunno if this is supposed to be set in any server type. If set
2972 here the CMODE_CHANGE that may follow sets mode that we already
2973 have, and we may loose data from the CMODE_CHANGE notify. */
2974 if (server_entry->server_type != SILC_BACKUP_ROUTER)
2975 channel->mode = silc_channel_get_mode(payload);
2978 /* Send the new channel key to the server */
2979 id = silc_id_id2str(channel->id, SILC_ID_CHANNEL);
2980 id_len = silc_id_get_len(channel->id, SILC_ID_CHANNEL);
2981 cipher = silc_cipher_get_name(channel->channel_key);
2982 cipher_len = strlen(cipher);
2983 chk = silc_channel_key_payload_encode(id_len, id,
2985 channel->key_len / 8,
2987 silc_server_packet_send(server, sock, SILC_PACKET_CHANNEL_KEY, 0,
2988 chk->data, chk->len, FALSE);
2989 silc_buffer_free(chk);
2992 /* The channel exist by that name, check whether the ID's match.
2993 If they don't then we'll force the server to use the ID we have.
2994 We also create a new key for the channel. */
2995 SilcBuffer modes = NULL, users = NULL, users_modes = NULL;
2997 SILC_LOG_DEBUG(("Channel already exists"));
2999 if (!SILC_ID_CHANNEL_COMPARE(channel_id, channel->id)) {
3000 /* They don't match, send CHANNEL_CHANGE notify to the server to
3001 force the ID change. */
3002 SILC_LOG_DEBUG(("Forcing the server to change Channel ID"));
3003 silc_server_send_notify_channel_change(server, sock, FALSE,
3004 channel_id, channel->id);
3005 silc_channel_payload_free(payload);
3006 silc_free(channel_id);
3008 /* Wait that server re-announces this channel */
3012 #if 0 /* We will announce our CMODE anyway for this channel, so no need
3013 to check it (implicit enforce). */
3015 /* If the mode is different from what we have then enforce the
3017 mode = silc_channel_get_mode(payload);
3018 if (channel->mode != mode) {
3019 SILC_LOG_DEBUG(("Forcing the server to change channel mode"));
3020 silc_server_send_notify_cmode(server, sock, FALSE, channel,
3021 channel->mode, server->id,
3022 SILC_ID_SERVER, channel->cipher,
3024 channel->passphrase,
3025 channel->founder_key);
3029 /* Create new key for the channel and send it to the server and
3030 everybody else possibly on the channel. */
3031 if (!(channel->mode & SILC_CHANNEL_MODE_PRIVKEY)) {
3033 if (silc_hash_table_count(channel->user_list)) {
3034 if (!silc_server_create_channel_key(server, channel, 0)) {
3035 silc_channel_payload_free(payload);
3036 silc_free(channel_id);
3040 /* Send to the channel */
3041 silc_server_send_channel_key(server, sock, channel, FALSE);
3044 /* Send to the server */
3045 id = silc_id_id2str(channel->id, SILC_ID_CHANNEL);
3046 id_len = silc_id_get_len(channel->id, SILC_ID_CHANNEL);
3047 cipher = silc_cipher_get_name(channel->channel_key);
3048 cipher_len = strlen(cipher);
3049 chk = silc_channel_key_payload_encode(id_len, id,
3051 channel->key_len / 8,
3053 silc_server_packet_send(server, sock, SILC_PACKET_CHANNEL_KEY, 0,
3054 chk->data, chk->len, FALSE);
3055 silc_buffer_free(chk);
3059 silc_free(channel_id);
3061 /* Since the channel is coming from server and we also know about it
3062 then send the JOIN notify to the server so that it see's our
3063 users on the channel "joining" the channel. */
3064 silc_server_announce_get_channel_users(server, channel, &modes, &users,
3067 silc_buffer_push(users, users->data - users->head);
3068 silc_server_packet_send(server, sock,
3069 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
3070 users->data, users->len, FALSE);
3071 silc_buffer_free(users);
3074 silc_buffer_push(modes, modes->data - modes->head);
3075 silc_server_packet_send_dest(server, sock,
3076 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
3077 channel->id, SILC_ID_CHANNEL,
3078 modes->data, modes->len, FALSE);
3079 silc_buffer_free(modes);
3082 silc_buffer_push(users_modes, users_modes->data - users_modes->head);
3083 silc_server_packet_send_dest(server, sock,
3084 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
3085 channel->id, SILC_ID_CHANNEL,
3087 users_modes->len, FALSE);
3088 silc_buffer_free(users_modes);
3090 if (channel->topic) {
3091 silc_server_send_notify_topic_set(server, sock,
3092 server->server_type == SILC_ROUTER ?
3093 TRUE : FALSE, channel,
3094 server->id, SILC_ID_SERVER,
3100 /* If the sender of this packet is server and we are router we need to
3101 broadcast this packet to other routers in the network. Broadcast
3102 this list packet instead of multiple New Channel packets. */
3103 if (server->server_type == SILC_ROUTER &&
3104 sock->type == SILC_SOCKET_TYPE_SERVER &&
3105 !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
3106 SILC_LOG_DEBUG(("Broadcasting received New Channel packet"));
3107 silc_server_packet_send(server, SILC_PRIMARY_ROUTE(server),
3109 packet->flags | SILC_PACKET_FLAG_BROADCAST,
3110 packet->buffer->data,
3111 packet->buffer->len, FALSE);
3112 silc_server_backup_send(server, sock->user_data,
3113 packet->type, packet->flags,
3114 packet->buffer->data, packet->buffer->len,
3118 silc_channel_payload_free(payload);
3121 /* Received New Channel List packet, list of New Channel List payloads inside
3122 one packet. Process the New Channel payloads one by one. */
3124 void silc_server_new_channel_list(SilcServer server,
3125 SilcSocketConnection sock,
3126 SilcPacketContext *packet)
3128 SilcPacketContext *new;
3130 SilcUInt16 len1, len2;
3132 SILC_LOG_DEBUG(("Processing New Channel List"));
3134 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
3135 packet->src_id_type != SILC_ID_SERVER ||
3136 server->server_type == SILC_SERVER)
3139 /* Make copy of the original packet context, except for the actual
3140 data buffer, which we will here now fetch from the original buffer. */
3141 new = silc_packet_context_alloc();
3142 new->type = SILC_PACKET_NEW_CHANNEL;
3143 new->flags = packet->flags & (~SILC_PACKET_FLAG_LIST);
3144 new->src_id = packet->src_id;
3145 new->src_id_len = packet->src_id_len;
3146 new->src_id_type = packet->src_id_type;
3147 new->dst_id = packet->dst_id;
3148 new->dst_id_len = packet->dst_id_len;
3149 new->dst_id_type = packet->dst_id_type;
3151 buffer = silc_buffer_alloc(512);
3152 new->buffer = buffer;
3154 while (packet->buffer->len) {
3155 SILC_GET16_MSB(len1, packet->buffer->data);
3156 if ((len1 > packet->buffer->len) ||
3157 (len1 > buffer->truelen))
3160 SILC_GET16_MSB(len2, packet->buffer->data + 2 + len1);
3161 if ((len2 > packet->buffer->len) ||
3162 (len2 > buffer->truelen))
3165 silc_buffer_pull_tail(buffer, 8 + len1 + len2);
3166 silc_buffer_put(buffer, packet->buffer->data, 8 + len1 + len2);
3168 /* Process the New Channel */
3169 silc_server_new_channel(server, sock, new);
3171 silc_buffer_push_tail(buffer, 8 + len1 + len2);
3172 silc_buffer_pull(packet->buffer, 8 + len1 + len2);
3175 silc_buffer_free(buffer);
3179 /* Received key agreement packet. This packet is never for us. It is to
3180 the client in the packet's destination ID. Sending of this sort of packet
3181 equals sending private message, ie. it is sent point to point from
3182 one client to another. */
3184 void silc_server_key_agreement(SilcServer server,
3185 SilcSocketConnection sock,
3186 SilcPacketContext *packet)
3188 SilcSocketConnection dst_sock;
3189 SilcIDListData idata;
3191 SILC_LOG_DEBUG(("Start"));
3193 if (packet->src_id_type != SILC_ID_CLIENT ||
3194 packet->dst_id_type != SILC_ID_CLIENT)
3197 if (!packet->dst_id)
3200 /* Get the route to the client */
3201 dst_sock = silc_server_get_client_route(server, packet->dst_id,
3202 packet->dst_id_len, NULL,
3207 /* Relay the packet */
3208 silc_server_relay_packet(server, dst_sock, idata->send_key,
3209 idata->hmac_send, idata->psn_send++,
3213 /* Received connection auth request packet that is used during connection
3214 phase to resolve the mandatory authentication method. This packet can
3215 actually be received at anytime but usually it is used only during
3216 the connection authentication phase. Now, protocol says that this packet
3217 can come from client or server, however, we support only this coming
3218 from client and expect that server always knows what authentication
3221 void silc_server_connection_auth_request(SilcServer server,
3222 SilcSocketConnection sock,
3223 SilcPacketContext *packet)
3225 SilcServerConfigClient *client = NULL;
3226 SilcUInt16 conn_type;
3228 SilcAuthMethod auth_meth = SILC_AUTH_NONE;
3230 if (packet->src_id_type && packet->src_id_type != SILC_ID_CLIENT) {
3231 SILC_LOG_DEBUG(("Request not from client"));
3235 /* Parse the payload */
3236 ret = silc_buffer_unformat(packet->buffer,
3237 SILC_STR_UI_SHORT(&conn_type),
3238 SILC_STR_UI_SHORT(NULL),
3243 if (conn_type != SILC_SOCKET_TYPE_CLIENT)
3246 /* Get the authentication method for the client */
3247 auth_meth = SILC_AUTH_NONE;
3248 client = silc_server_config_find_client(server, sock->ip);
3250 client = silc_server_config_find_client(server, sock->hostname);
3252 if (client->passphrase) {
3253 if (client->publickeys && !server->config->prefer_passphrase_auth)
3254 auth_meth = SILC_AUTH_PUBLIC_KEY;
3256 auth_meth = SILC_AUTH_PASSWORD;
3257 } else if (client->publickeys)
3258 auth_meth = SILC_AUTH_PUBLIC_KEY;
3261 SILC_LOG_DEBUG(("Authentication method is [%s]",
3262 (auth_meth == SILC_AUTH_NONE ? "None" :
3263 auth_meth == SILC_AUTH_PASSWORD ? "Passphrase" :
3264 "Digital signatures")));
3266 /* Send it back to the client */
3267 silc_server_send_connection_auth_request(server, sock, conn_type, auth_meth);
3270 /* Received REKEY packet. The sender of the packet wants to regenerate
3271 its session keys. This starts the REKEY protocol. */
3273 void silc_server_rekey(SilcServer server,
3274 SilcSocketConnection sock,
3275 SilcPacketContext *packet)
3277 SilcProtocol protocol;
3278 SilcServerRekeyInternalContext *proto_ctx;
3279 SilcIDListData idata = (SilcIDListData)sock->user_data;
3281 SILC_LOG_DEBUG(("Start"));
3283 /* Allocate internal protocol context. This is sent as context
3285 proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
3286 proto_ctx->server = (void *)server;
3287 proto_ctx->sock = sock;
3288 proto_ctx->responder = TRUE;
3289 proto_ctx->pfs = idata->rekey->pfs;
3291 /* Perform rekey protocol. Will call the final callback after the
3292 protocol is over. */
3293 silc_protocol_alloc(SILC_PROTOCOL_SERVER_REKEY,
3294 &protocol, proto_ctx, silc_server_rekey_final);
3295 sock->protocol = protocol;
3297 if (proto_ctx->pfs == FALSE)
3298 /* Run the protocol */
3299 silc_protocol_execute(protocol, server->schedule, 0, 0);
3302 /* Received file transger packet. This packet is never for us. It is to
3303 the client in the packet's destination ID. Sending of this sort of packet
3304 equals sending private message, ie. it is sent point to point from
3305 one client to another. */
3307 void silc_server_ftp(SilcServer server,
3308 SilcSocketConnection sock,
3309 SilcPacketContext *packet)
3311 SilcSocketConnection dst_sock;
3312 SilcIDListData idata;
3314 SILC_LOG_DEBUG(("Start"));
3316 if (packet->src_id_type != SILC_ID_CLIENT ||
3317 packet->dst_id_type != SILC_ID_CLIENT)
3320 if (!packet->dst_id)
3323 /* Get the route to the client */
3324 dst_sock = silc_server_get_client_route(server, packet->dst_id,
3325 packet->dst_id_len, NULL,
3330 /* Relay the packet */
3331 silc_server_relay_packet(server, dst_sock, idata->send_key,
3332 idata->hmac_send, idata->psn_send++,
3338 SilcSocketConnection sock;
3339 SilcPacketContext *packet;
3341 } *SilcServerResumeResolve;
3343 SILC_SERVER_CMD_FUNC(resume_resolve)
3345 SilcServerResumeResolve r = (SilcServerResumeResolve)context;
3346 SilcServer server = r->server;
3347 SilcSocketConnection sock = r->sock;
3348 SilcServerCommandReplyContext reply = context2;
3349 SilcClientEntry client;
3351 SILC_LOG_DEBUG(("Start"));
3353 if (!reply || !silc_command_get_status(reply->payload, NULL, NULL)) {
3354 SILC_LOG_ERROR(("Client %s (%s) tried to resume unknown client, "
3355 "closing connection", sock->hostname, sock->ip));
3356 silc_server_disconnect_remote(server, sock,
3357 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
3358 "Resuming not possible");
3359 if (sock->user_data)
3360 silc_server_free_sock_user_data(server, sock, NULL);
3364 if (reply && silc_command_get(reply->payload) == SILC_COMMAND_WHOIS) {
3365 /* Get entry to the client, and resolve it if we don't have it. */
3366 client = silc_idlist_find_client_by_id(server->local_list,
3367 r->data, TRUE, NULL);
3369 client = silc_idlist_find_client_by_id(server->global_list,
3370 r->data, TRUE, NULL);
3372 SILC_LOG_ERROR(("Client %s (%s) tried to resume unknown client, "
3373 "closing connection", sock->hostname, sock->ip));
3374 silc_server_disconnect_remote(server, sock,
3375 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
3376 "Resuming not possible");
3377 if (sock->user_data)
3378 silc_server_free_sock_user_data(server, sock, NULL);
3383 if (!(client->mode & SILC_UMODE_DETACHED)) {
3384 SILC_LOG_ERROR(("Client %s (%s) tried to resume un-detached client, "
3385 "closing connection", sock->hostname, sock->ip));
3386 silc_server_disconnect_remote(server, sock,
3387 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
3388 "Resuming not possible");
3389 if (sock->user_data)
3390 silc_server_free_sock_user_data(server, sock, NULL);
3394 client->data.status |= SILC_IDLIST_STATUS_RESUME_RES;
3397 /* Reprocess the packet */
3398 silc_server_resume_client(server, sock, r->packet);
3401 silc_socket_free(r->sock);
3402 silc_packet_context_free(r->packet);
3407 /* Received client resuming packet. This is used to resume detached
3408 client session. It can be sent by the client who wishes to resume
3409 but this is also sent by servers and routers to notify other routers
3410 that the client is not detached anymore. */
3412 void silc_server_resume_client(SilcServer server,
3413 SilcSocketConnection sock,
3414 SilcPacketContext *packet)
3416 SilcBuffer buffer = packet->buffer, buf;
3417 SilcIDListData idata;
3418 SilcIDCacheEntry id_cache = NULL;
3419 SilcClientEntry detached_client;
3420 SilcClientID *client_id = NULL;
3421 unsigned char *id_string, *auth = NULL;
3422 SilcUInt16 id_len, auth_len = 0;
3423 int ret, nickfail = 0;
3424 bool resolved, local, nick_change = FALSE, resolve = FALSE;
3425 SilcChannelEntry channel;
3426 SilcHashTableList htl;
3427 SilcChannelClientEntry chl;
3428 SilcServerResumeResolve r;
3431 ret = silc_buffer_unformat(buffer,
3432 SILC_STR_UI16_NSTRING(&id_string, &id_len),
3435 client_id = silc_id_str2id(id_string, id_len, SILC_ID_CLIENT);
3437 if (sock->type == SILC_SOCKET_TYPE_CLIENT) {
3438 /* Client send this and is attempting to resume to old client session */
3439 SilcClientEntry client;
3443 silc_buffer_pull(buffer, 2 + id_len);
3444 auth = buffer->data;
3445 auth_len = buffer->len;
3446 silc_buffer_push(buffer, 2 + id_len);
3449 if (!client_id || auth_len < 128) {
3450 SILC_LOG_ERROR(("Client %s (%s) sent incomplete resume information, "
3451 "closing connection", sock->hostname, sock->ip));
3452 silc_server_disconnect_remote(server, sock,
3453 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
3454 "Resuming not possible");
3455 if (sock->user_data)
3456 silc_server_free_sock_user_data(server, sock, NULL);
3457 silc_free(client_id);
3461 /* Take client entry of this connection */
3462 client = (SilcClientEntry)sock->user_data;
3463 idata = (SilcIDListData)client;
3465 /* Get entry to the client, and resolve it if we don't have it. */
3466 detached_client = silc_server_query_client(server, client_id, FALSE,
3468 if (!detached_client) {
3470 /* The client info is being resolved. Reprocess this packet after
3471 receiving the reply to the query. */
3472 SILC_LOG_DEBUG(("Resolving client"));
3473 r = silc_calloc(1, sizeof(*r));
3477 r->sock = silc_socket_dup(sock);
3478 r->packet = silc_packet_context_dup(packet);
3479 r->data = client_id;
3480 silc_server_command_pending(server, SILC_COMMAND_WHOIS,
3482 silc_server_command_resume_resolve, r);
3484 SILC_LOG_ERROR(("Client %s (%s) tried to resume unknown client, "
3485 "closing connection", sock->hostname, sock->ip));
3486 silc_server_disconnect_remote(server, sock,
3487 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
3488 "Resuming not possible");
3489 if (sock->user_data)
3490 silc_server_free_sock_user_data(server, sock, NULL);
3491 silc_free(client_id);
3496 if (!(detached_client->mode & SILC_UMODE_DETACHED))
3498 if (!silc_hash_table_count(detached_client->channels) &&
3499 detached_client->router)
3501 if (!detached_client->nickname)
3503 if (detached_client->data.status & SILC_IDLIST_STATUS_RESUME_RES)
3507 if (server->server_type == SILC_SERVER && !server->standalone) {
3508 /* The client info is being resolved. Reprocess this packet after
3509 receiving the reply to the query. */
3510 SILC_LOG_DEBUG(("Resolving client info"));
3511 silc_server_query_client(server, client_id, TRUE, NULL);
3512 r = silc_calloc(1, sizeof(*r));
3516 r->sock = silc_socket_dup(sock);
3517 r->packet = silc_packet_context_dup(packet);
3518 r->data = client_id;
3519 silc_server_command_pending(server, SILC_COMMAND_WHOIS,
3521 silc_server_command_resume_resolve, r);
3524 if (server->server_type == SILC_SERVER) {
3525 SILC_LOG_ERROR(("Client %s (%s) tried to resume un-detached client, "
3526 "closing connection", sock->hostname, sock->ip));
3527 silc_server_disconnect_remote(server, sock,
3528 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
3529 "Resuming not possible");
3530 if (sock->user_data)
3531 silc_server_free_sock_user_data(server, sock, NULL);
3532 silc_free(client_id);
3537 /* Check that we have the public key of the client, if not then we must
3538 resolve it first. */
3539 if (!detached_client->data.public_key) {
3540 if (server->server_type == SILC_SERVER && server->standalone) {
3541 SILC_LOG_ERROR(("Detached client's public key not present, "
3542 "closing connection"));
3543 silc_server_disconnect_remote(server, sock,
3544 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
3545 "Resuming not possible");
3546 if (sock->user_data)
3547 silc_server_free_sock_user_data(server, sock, NULL);
3548 silc_free(client_id);
3550 /* We must retrieve the detached client's public key by sending
3551 GETKEY command. Reprocess this packet after receiving the key */
3552 SilcBuffer idp = silc_id_payload_encode(client_id, SILC_ID_CLIENT);
3553 SilcSocketConnection dest_sock =
3554 silc_server_get_client_route(server, NULL, 0, client_id, NULL, NULL);
3556 SILC_LOG_DEBUG(("Resolving client public key"));
3558 silc_server_send_command(server, dest_sock ? dest_sock :
3559 SILC_PRIMARY_ROUTE(server),
3560 SILC_COMMAND_GETKEY, ++server->cmd_ident,
3561 1, 1, idp->data, idp->len);
3563 r = silc_calloc(1, sizeof(*r));
3565 silc_free(client_id);
3570 r->sock = silc_socket_dup(sock);
3571 r->packet = silc_packet_context_dup(packet);
3572 silc_server_command_pending(server, SILC_COMMAND_GETKEY,
3574 silc_server_command_resume_resolve, r);
3576 silc_buffer_free(idp);
3578 silc_free(client_id);
3580 } else if (!silc_pkcs_public_key_compare(detached_client->data.public_key,
3581 idata->public_key)) {
3582 /* We require that the connection and resuming authentication data
3583 must be using same key pair. */
3584 SILC_LOG_ERROR(("Resuming attempted with wrong public key, "
3585 "closing connection"));
3586 silc_server_disconnect_remote(server, sock,
3587 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
3588 "Resuming not possible");
3589 if (sock->user_data)
3590 silc_server_free_sock_user_data(server, sock, NULL);
3591 silc_free(client_id);
3595 /* Verify the authentication payload. This has to be successful in
3596 order to allow the resuming */
3598 !silc_auth_verify_data(auth, auth_len, SILC_AUTH_PUBLIC_KEY,
3599 detached_client->data.public_key, 0,
3600 idata->hash, detached_client->id,
3602 SILC_LOG_ERROR(("Client %s (%s) resume authentication failed, "
3603 "closing connection", sock->hostname, sock->ip));
3604 silc_server_disconnect_remote(server, sock,
3605 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
3606 "Resuming not possible");
3607 if (sock->user_data)
3608 silc_server_free_sock_user_data(server, sock, NULL);
3609 silc_free(client_id);
3613 /* Now resume the client to the network */
3615 silc_schedule_task_del_by_context(server->schedule, detached_client);
3616 sock->user_data = detached_client;
3617 detached_client->connection = sock;
3619 /* Take new keys and stuff into use in the old entry */
3620 silc_idlist_del_data(detached_client);
3621 silc_idlist_add_data(detached_client, idata);
3622 detached_client->data.status |= SILC_IDLIST_STATUS_REGISTERED;
3623 detached_client->data.status |= SILC_IDLIST_STATUS_RESUMED;
3624 detached_client->data.status |= SILC_IDLIST_STATUS_LOCAL;
3625 detached_client->data.status &= ~SILC_IDLIST_STATUS_RESUME_RES;
3626 detached_client->mode &= ~SILC_UMODE_DETACHED;
3627 server->stat.my_detached--;
3629 /* Send the RESUME_CLIENT packet to our primary router so that others
3630 know this client isn't detached anymore. */
3631 buf = silc_buffer_alloc_size(2 + id_len);
3632 silc_buffer_format(buf,
3633 SILC_STR_UI_SHORT(id_len),
3634 SILC_STR_UI_XNSTRING(id_string, id_len),
3637 /* Send to primary router */
3638 silc_server_packet_send(server, SILC_PRIMARY_ROUTE(server),
3639 SILC_PACKET_RESUME_CLIENT, 0,
3640 buf->data, buf->len, TRUE);
3641 silc_server_backup_send(server, detached_client->router,
3642 SILC_PACKET_RESUME_CLIENT, 0,
3643 buf->data, buf->len, TRUE, TRUE);
3645 /* As router we must deliver this packet directly to the original
3646 server whom this client was earlier. */
3647 if (server->server_type == SILC_ROUTER && detached_client->router &&
3648 detached_client->router->server_type != SILC_ROUTER)
3649 silc_server_packet_send(server, detached_client->router->connection,
3650 SILC_PACKET_RESUME_CLIENT, 0,
3651 buf->data, buf->len, TRUE);
3652 silc_buffer_free(buf);
3654 detached_client->router = NULL;
3656 /* Delete this client entry since we're resuming to old one. */
3657 server->stat.my_clients--;
3658 server->stat.clients--;
3659 if (server->stat.cell_clients)
3660 server->stat.cell_clients--;
3661 silc_server_remove_from_channels(server, NULL, client, FALSE, NULL, FALSE);
3662 silc_server_del_from_watcher_list(server, client);
3663 if (!silc_idlist_del_client(server->local_list, client))
3664 silc_idlist_del_client(server->global_list, client);
3665 client = detached_client;
3666 silc_free(client->servername);
3667 client->servername = strdup(server->server_name);
3669 /* If the ID is not based in our ID then change it */
3670 if (!SILC_ID_COMPARE(client->id, server->id, server->id->ip.data_len)) {
3671 silc_free(client_id);
3672 while (!silc_id_create_client_id(server, server->id, server->rng,
3673 server->md5hash, client->nickname,
3677 silc_server_disconnect_remote(server, sock,
3678 SILC_STATUS_ERR_BAD_NICKNAME, NULL);
3679 if (sock->user_data)
3680 silc_server_free_sock_user_data(server, sock, NULL);
3683 snprintf(&client->nickname[strlen(client->nickname) - 1], 1,
3690 /* Notify about Client ID change, nickname doesn't actually change. */
3691 silc_server_send_notify_nick_change(server, SILC_PRIMARY_ROUTE(server),
3692 SILC_BROADCAST(server),
3693 client->id, client_id,
3697 /* Resolve users on those channels that client has joined but we
3698 haven't resolved user list yet. */
3699 if (server->server_type == SILC_SERVER && !server->standalone) {
3700 silc_hash_table_list(client->channels, &htl);
3701 while (silc_hash_table_get(&htl, NULL, (void **)&chl)) {
3702 channel = chl->channel;
3703 SILC_LOG_DEBUG(("Resolving users for %s channel",
3704 channel->channel_name));
3705 if (channel->disabled || !channel->users_resolved) {
3706 silc_server_send_command(server, SILC_PRIMARY_ROUTE(server),
3707 SILC_COMMAND_USERS, ++server->cmd_ident,
3708 1, 2, channel->channel_name,
3709 strlen(channel->channel_name));
3712 silc_hash_table_list_reset(&htl);
3715 /* Send the new client ID to the client. After this client may start
3716 receiving other packets, and may start sending packets too. */
3717 silc_server_send_new_id(server, sock, FALSE, client_id, SILC_ID_CLIENT,
3718 silc_id_get_len(client_id, SILC_ID_CLIENT));
3721 /* Send NICK change notify to channels as well. */
3722 SilcBuffer oidp, nidp;
3723 oidp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
3724 nidp = silc_id_payload_encode(client_id, SILC_ID_CLIENT);
3725 silc_server_send_notify_on_channels(server, NULL, client,
3726 SILC_NOTIFY_TYPE_NICK_CHANGE, 3,
3727 oidp->data, oidp->len,
3728 nidp->data, nidp->len,
3730 strlen(client->nickname));
3731 silc_buffer_free(oidp);
3732 silc_buffer_free(nidp);
3735 /* Add the client again to the ID cache to get it to correct list */
3736 if (!silc_idcache_del_by_context(server->local_list->clients, client))
3737 silc_idcache_del_by_context(server->global_list->clients, client);
3738 silc_free(client->id);
3739 client->id = client_id;
3741 silc_idcache_add(server->local_list->clients, client->nickname,
3742 client->id, client, 0, NULL);
3744 /* Send some nice info to the client */
3745 silc_server_send_connect_notifys(server, sock, client);
3747 /* Send all channel keys of channels the client has joined */
3748 silc_hash_table_list(client->channels, &htl);
3749 while (silc_hash_table_get(&htl, NULL, (void **)&chl)) {
3750 bool created = FALSE;
3751 channel = chl->channel;
3753 if (channel->mode & SILC_CHANNEL_MODE_PRIVKEY)
3756 /* If we don't have channel key, then create one */
3757 if (!channel->channel_key) {
3758 if (!silc_server_create_channel_key(server, channel, 0))
3763 id_string = silc_id_id2str(channel->id, SILC_ID_CHANNEL);
3764 cipher = silc_cipher_get_name(channel->channel_key);
3766 silc_channel_key_payload_encode(silc_id_get_len(channel->id,
3769 strlen(cipher), cipher,
3770 channel->key_len / 8, channel->key);
3771 silc_free(id_string);
3773 /* Send the channel key to the client */
3774 silc_server_packet_send(server, sock, SILC_PACKET_CHANNEL_KEY, 0,
3775 keyp->data, keyp->len, FALSE);
3777 /* Distribute the channel key to channel */
3779 silc_server_send_channel_key(server, NULL, channel,
3780 server->server_type == SILC_ROUTER ?
3781 FALSE : !server->standalone);
3782 silc_server_backup_send(server, NULL, SILC_PACKET_CHANNEL_KEY, 0,
3783 keyp->data, keyp->len, FALSE, TRUE);
3786 silc_buffer_free(keyp);
3788 silc_hash_table_list_reset(&htl);
3790 } else if (sock->type != SILC_SOCKET_TYPE_CLIENT) {
3791 /* Server or router sent this to us to notify that that a client has
3793 SilcServerEntry server_entry;
3794 SilcServerID *server_id;
3797 SILC_LOG_DEBUG(("Malformed resuming packet"));
3801 /* Get entry to the client, and resolve it if we don't have it. */
3802 detached_client = silc_idlist_find_client_by_id(server->local_list,
3805 if (!detached_client) {
3806 detached_client = silc_idlist_find_client_by_id(server->global_list,
3809 if (!detached_client) {
3810 SILC_LOG_DEBUG(("Resuming client is unknown"));
3811 silc_free(client_id);
3816 /* Check that the client has not been resumed already because it is
3817 protocol error to attempt to resume more than once. The client
3818 will be killed if this protocol error occurs. */
3819 if (detached_client->data.status & SILC_IDLIST_STATUS_RESUMED &&
3820 !(detached_client->mode & SILC_UMODE_DETACHED)) {
3821 /* The client is clearly attempting to resume more than once and
3822 perhaps playing around by resuming from several different places
3823 at the same time. */
3824 SILC_LOG_DEBUG(("Attempting to re-resume client, killing both"));
3825 silc_server_kill_client(server, detached_client, NULL,
3826 server->id, SILC_ID_SERVER);
3827 silc_free(client_id);
3831 /* Check whether client is detached at all */
3832 if (!(detached_client->mode & SILC_UMODE_DETACHED)) {
3833 SILC_LOG_DEBUG(("Client is not detached"));
3834 silc_free(client_id);
3838 SILC_LOG_DEBUG(("Resuming detached client"));
3840 /* If the sender of this packet is server and we are router we need to
3841 broadcast this packet to other routers in the network. */
3842 if (server->server_type == SILC_ROUTER &&
3843 sock->type == SILC_SOCKET_TYPE_SERVER &&
3844 !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
3845 SILC_LOG_DEBUG(("Broadcasting received Resume Client packet"));
3846 silc_server_packet_send(server, SILC_PRIMARY_ROUTE(server),
3848 packet->flags | SILC_PACKET_FLAG_BROADCAST,
3849 buffer->data, buffer->len, FALSE);
3850 silc_server_backup_send(server, sock->user_data,
3851 packet->type, packet->flags,
3852 packet->buffer->data, packet->buffer->len,
3856 /* Client is detached, and now it is resumed. Remove the detached
3857 mode and mark that it is resumed. */
3858 silc_idlist_del_data(detached_client);
3859 detached_client->mode &= ~SILC_UMODE_DETACHED;
3860 detached_client->data.status |= SILC_IDLIST_STATUS_RESUMED;
3861 detached_client->data.status &= ~SILC_IDLIST_STATUS_LOCAL;
3862 id_cache->expire = 0;
3864 silc_schedule_task_del_by_context(server->schedule, detached_client);
3866 /* Get the new owner of the resumed client */
3867 server_id = silc_id_str2id(packet->src_id, packet->src_id_len,
3868 packet->src_id_type);
3870 silc_free(client_id);
3874 /* Get server entry */
3875 server_entry = silc_idlist_find_server_by_id(server->global_list,
3876 server_id, TRUE, NULL);
3878 if (!server_entry) {
3879 server_entry = silc_idlist_find_server_by_id(server->local_list,
3880 server_id, TRUE, NULL);
3882 if (!server_entry) {
3883 silc_free(server_id);
3884 silc_free(client_id);
3889 if (server->server_type == SILC_ROUTER &&
3890 sock->type == SILC_SOCKET_TYPE_ROUTER &&
3891 server_entry->server_type == SILC_ROUTER)
3894 /* Change the client to correct list. */
3895 if (!silc_idcache_del_by_context(server->local_list->clients,
3897 silc_idcache_del_by_context(server->global_list->clients,
3899 silc_idcache_add(local && server->server_type == SILC_ROUTER ?
3900 server->local_list->clients :
3901 server->global_list->clients,
3902 detached_client->nickname,
3903 detached_client->id, detached_client, FALSE, NULL);
3905 /* Change the owner of the client */
3906 detached_client->router = server_entry;
3908 /* Update channel information regarding global clients on channel. */
3909 if (server->server_type != SILC_ROUTER) {
3910 silc_hash_table_list(detached_client->channels, &htl);
3911 while (silc_hash_table_get(&htl, NULL, (void **)&chl))
3912 chl->channel->global_users =
3913 silc_server_channel_has_global(chl->channel);
3914 silc_hash_table_list_reset(&htl);
3917 silc_free(server_id);
3920 silc_free(client_id);
3921 silc_idlist_del_data(detached_client);