5 Author: Pekka Riikonen <priikone@poseidon.pspt.fi>
7 Copyright (C) 1997 - 2001 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 extern char *server_version;
30 /* Received notify packet. Server can receive notify packets from router.
31 Server then relays the notify messages to clients if needed. */
33 void silc_server_notify(SilcServer server,
34 SilcSocketConnection sock,
35 SilcPacketContext *packet)
37 SilcNotifyPayload payload;
39 SilcArgumentPayload args;
40 SilcChannelID *channel_id = NULL, *channel_id2;
41 SilcClientID *client_id, *client_id2;
42 SilcServerID *server_id;
43 SilcChannelEntry channel;
44 SilcClientEntry client;
45 SilcServerEntry server_entry;
46 SilcChannelClientEntry chl;
47 SilcIDCacheEntry cache;
48 SilcHashTableList htl;
53 SILC_LOG_DEBUG(("Start"));
55 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
56 packet->src_id_type != SILC_ID_SERVER)
62 /* If the packet is destined directly to a client then relay the packet
63 before processing it. */
64 if (packet->dst_id_type == SILC_ID_CLIENT) {
66 SilcSocketConnection dst_sock;
68 /* Get the route to the client */
69 dst_sock = silc_server_get_client_route(server, packet->dst_id,
70 packet->dst_id_len, NULL, &idata);
72 /* Relay the packet */
73 silc_server_relay_packet(server, dst_sock, idata->send_key,
74 idata->hmac_receive, idata->psn_send++,
78 /* Parse the Notify Payload */
79 payload = silc_notify_payload_parse(packet->buffer);
83 /* If we are router and this packet is not already broadcast packet
84 we will broadcast it. The sending socket really cannot be router or
85 the router is buggy. If this packet is coming from router then it must
86 have the broadcast flag set already and we won't do anything. */
87 if (!server->standalone && server->server_type == SILC_ROUTER &&
88 sock->type == SILC_SOCKET_TYPE_SERVER &&
89 !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
90 SILC_LOG_DEBUG(("Broadcasting received Notify packet"));
91 if (packet->dst_id_type == SILC_ID_CHANNEL) {
92 /* Packet is destined to channel */
93 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
98 silc_server_packet_send_dest(server, server->router->connection,
100 packet->flags | SILC_PACKET_FLAG_BROADCAST,
101 channel_id, SILC_ID_CHANNEL,
102 packet->buffer->data, packet->buffer->len,
104 silc_server_backup_send_dest(server, (SilcServerEntry)sock->user_data,
105 packet->type, packet->flags,
106 channel_id, SILC_ID_CHANNEL,
107 packet->buffer->data, packet->buffer->len,
110 /* Packet is destined to client or server */
111 silc_server_packet_send(server, server->router->connection,
113 packet->flags | SILC_PACKET_FLAG_BROADCAST,
114 packet->buffer->data, packet->buffer->len,
116 silc_server_backup_send(server, (SilcServerEntry)sock->user_data,
117 packet->type, packet->flags,
118 packet->buffer->data, packet->buffer->len,
123 type = silc_notify_get_type(payload);
124 args = silc_notify_get_args(payload);
129 case SILC_NOTIFY_TYPE_JOIN:
131 * Distribute the notify to local clients on the channel
133 SILC_LOG_DEBUG(("JOIN notify"));
136 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
139 channel_id = silc_id_payload_parse_id(tmp, tmp_len);
143 /* Get channel entry */
144 channel = silc_idlist_find_channel_by_id(server->global_list,
147 channel = silc_idlist_find_channel_by_id(server->local_list,
150 silc_free(channel_id);
154 silc_free(channel_id);
157 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
160 client_id = silc_id_payload_parse_id(tmp, tmp_len);
164 /* If the the client is not in local list we check global list (ie. the
165 channel will be global channel) and if it does not exist then create
166 entry for the client. */
167 client = silc_idlist_find_client_by_id(server->global_list,
168 client_id, server->server_type,
171 client = silc_idlist_find_client_by_id(server->local_list,
172 client_id, server->server_type,
175 /* If router did not find the client the it is bogus */
176 if (server->server_type != SILC_SERVER)
180 silc_idlist_add_client(server->global_list, NULL, NULL, NULL,
181 silc_id_dup(client_id, SILC_ID_CLIENT),
182 sock->user_data, NULL);
184 SILC_LOG_ERROR(("Could not add new client to the ID Cache"));
185 silc_free(client_id);
189 client->data.status |= SILC_IDLIST_STATUS_REGISTERED;
193 /* Do not process the notify if the client is not registered */
194 if (!(client->data.status & SILC_IDLIST_STATUS_REGISTERED))
197 /* Do not add client to channel if it is there already */
198 if (silc_server_client_on_channel(client, channel)) {
199 SILC_LOG_DEBUG(("Client already on channel"));
203 /* Send to channel */
204 silc_server_packet_send_to_channel(server, sock, channel, packet->type,
205 FALSE, packet->buffer->data,
206 packet->buffer->len, FALSE);
208 if (server->server_type != SILC_ROUTER &&
209 sock->type == SILC_SOCKET_TYPE_ROUTER)
210 /* The channel is global now */
211 channel->global_users = TRUE;
213 /* JOIN the global client to the channel (local clients (if router
214 created the channel) is joined in the pending JOIN command). */
215 chl = silc_calloc(1, sizeof(*chl));
216 chl->client = client;
217 chl->channel = channel;
219 /* If this is the first one on the channel then it is the founder of
221 if (!silc_hash_table_count(channel->user_list))
222 chl->mode = (SILC_CHANNEL_UMODE_CHANOP | SILC_CHANNEL_UMODE_CHANFO);
224 silc_hash_table_add(channel->user_list, client, chl);
225 silc_hash_table_add(client->channels, channel, chl);
226 silc_free(client_id);
230 case SILC_NOTIFY_TYPE_LEAVE:
232 * Distribute the notify to local clients on the channel
234 SILC_LOG_DEBUG(("LEAVE notify"));
237 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
238 packet->dst_id_type);
243 /* Get channel entry */
244 channel = silc_idlist_find_channel_by_id(server->global_list,
247 channel = silc_idlist_find_channel_by_id(server->local_list,
250 silc_free(channel_id);
256 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
258 silc_free(channel_id);
261 client_id = silc_id_payload_parse_id(tmp, tmp_len);
263 silc_free(channel_id);
267 /* Get client entry */
268 client = silc_idlist_find_client_by_id(server->global_list,
269 client_id, TRUE, NULL);
271 client = silc_idlist_find_client_by_id(server->local_list,
272 client_id, TRUE, NULL);
274 silc_free(client_id);
275 silc_free(channel_id);
279 silc_free(client_id);
281 /* Check if on channel */
282 if (!silc_server_client_on_channel(client, channel))
285 /* Send the leave notify to channel */
286 silc_server_packet_send_to_channel(server, sock, channel, packet->type,
287 FALSE, packet->buffer->data,
288 packet->buffer->len, FALSE);
290 /* Remove the user from channel */
291 silc_server_remove_from_one_channel(server, sock, channel, client, FALSE);
294 case SILC_NOTIFY_TYPE_SIGNOFF:
296 * Distribute the notify to local clients on the channel
298 SILC_LOG_DEBUG(("SIGNOFF notify"));
301 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
304 client_id = silc_id_payload_parse_id(tmp, tmp_len);
308 /* Get client entry */
309 client = silc_idlist_find_client_by_id(server->global_list,
310 client_id, TRUE, &cache);
312 client = silc_idlist_find_client_by_id(server->local_list,
313 client_id, TRUE, &cache);
315 silc_free(client_id);
319 silc_free(client_id);
321 /* Get signoff message */
322 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
326 /* Remove the client from all channels. */
327 silc_server_remove_from_channels(server, NULL, client, TRUE, tmp, FALSE);
329 client->data.status &= ~SILC_IDLIST_STATUS_REGISTERED;
330 cache->expire = SILC_ID_CACHE_EXPIRE_DEF;
331 server->stat.clients--;
332 if (server->server_type == SILC_ROUTER)
333 server->stat.cell_clients--;
336 case SILC_NOTIFY_TYPE_TOPIC_SET:
338 * Distribute the notify to local clients on the channel
341 SILC_LOG_DEBUG(("TOPIC SET notify"));
344 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
345 packet->dst_id_type);
350 /* Get channel entry */
351 channel = silc_idlist_find_channel_by_id(server->global_list,
354 channel = silc_idlist_find_channel_by_id(server->local_list,
357 silc_free(channel_id);
363 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
365 silc_free(channel_id);
370 silc_free(channel->topic);
371 channel->topic = silc_calloc(tmp_len + 1, sizeof(*channel->topic));
372 memcpy(channel->topic, tmp, tmp_len);
374 /* Send the same notify to the channel */
375 silc_server_packet_send_to_channel(server, sock, channel, packet->type,
376 FALSE, packet->buffer->data,
377 packet->buffer->len, FALSE);
378 silc_free(channel_id);
381 case SILC_NOTIFY_TYPE_NICK_CHANGE:
384 * Distribute the notify to local clients on the channel
386 unsigned char *id, *id2;
388 SILC_LOG_DEBUG(("NICK CHANGE notify"));
390 /* Get old client ID */
391 id = silc_argument_get_arg_type(args, 1, &tmp_len);
394 client_id = silc_id_payload_parse_id(id, tmp_len);
398 /* Get new client ID */
399 id2 = silc_argument_get_arg_type(args, 2, &tmp_len);
402 client_id2 = silc_id_payload_parse_id(id2, tmp_len);
406 SILC_LOG_DEBUG(("Old Client ID id(%s)",
407 silc_id_render(client_id, SILC_ID_CLIENT)));
408 SILC_LOG_DEBUG(("New Client ID id(%s)",
409 silc_id_render(client_id2, SILC_ID_CLIENT)));
411 /* Replace the Client ID */
412 client = silc_idlist_replace_client_id(server->global_list, client_id,
415 client = silc_idlist_replace_client_id(server->local_list, client_id,
419 /* The nickname is not valid anymore, set it NULL. This causes that
420 the nickname will be queried if someone wants to know it. */
421 if (client->nickname)
422 silc_free(client->nickname);
423 client->nickname = NULL;
425 /* Send the NICK_CHANGE notify type to local clients on the channels
426 this client is joined to. */
427 silc_server_send_notify_on_channels(server, NULL, client,
428 SILC_NOTIFY_TYPE_NICK_CHANGE, 2,
433 silc_free(client_id);
435 silc_free(client_id2);
439 case SILC_NOTIFY_TYPE_CMODE_CHANGE:
441 * Distribute the notify to local clients on the channel
444 SILC_LOG_DEBUG(("CMODE CHANGE notify"));
447 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
448 packet->dst_id_type);
453 /* Get channel entry */
454 channel = silc_idlist_find_channel_by_id(server->global_list,
457 channel = silc_idlist_find_channel_by_id(server->local_list,
460 silc_free(channel_id);
466 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
468 silc_free(channel_id);
472 SILC_GET32_MSB(mode, tmp);
474 /* Check if mode changed */
475 if (channel->mode == mode)
478 /* Send the same notify to the channel */
479 silc_server_packet_send_to_channel(server, sock, channel, packet->type,
480 FALSE, packet->buffer->data,
481 packet->buffer->len, FALSE);
483 /* If the channel had private keys set and the mode was removed then
484 we must re-generate and re-distribute a new channel key */
485 if (channel->mode & SILC_CHANNEL_MODE_PRIVKEY &&
486 !(mode & SILC_CHANNEL_MODE_PRIVKEY)) {
487 /* Re-generate channel key */
488 if (!silc_server_create_channel_key(server, channel, 0))
491 /* Send the channel key. This sends it to our local clients and if
492 we are normal server to our router as well. */
493 silc_server_send_channel_key(server, NULL, channel,
494 server->server_type == SILC_ROUTER ?
495 FALSE : !server->standalone);
499 channel->mode = mode;
500 silc_free(channel_id);
503 tmp = silc_argument_get_arg_type(args, 4, &tmp_len);
505 unsigned char hash[32];
508 silc_hmac_free(channel->hmac);
509 if (!silc_hmac_alloc(tmp, NULL, &channel->hmac))
512 /* Set the HMAC key out of current channel key. The client must do
514 silc_hash_make(silc_hmac_get_hash(channel->hmac), channel->key,
515 channel->key_len / 8,
517 silc_hmac_set_key(channel->hmac, hash,
518 silc_hash_len(silc_hmac_get_hash(channel->hmac)));
519 memset(hash, 0, sizeof(hash));
524 case SILC_NOTIFY_TYPE_CUMODE_CHANGE:
527 * Distribute the notify to local clients on the channel
529 SilcChannelClientEntry chl2 = NULL;
530 bool notify_sent = FALSE;
532 SILC_LOG_DEBUG(("CUMODE CHANGE notify"));
535 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
536 packet->dst_id_type);
541 /* Get channel entry */
542 channel = silc_idlist_find_channel_by_id(server->global_list,
545 channel = silc_idlist_find_channel_by_id(server->local_list,
548 silc_free(channel_id);
554 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
556 silc_free(channel_id);
560 SILC_GET32_MSB(mode, tmp);
562 /* Get target client */
563 tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
566 client_id = silc_id_payload_parse_id(tmp, tmp_len);
570 /* Get client entry */
571 client = silc_idlist_find_client_by_id(server->global_list,
572 client_id, TRUE, NULL);
574 client = silc_idlist_find_client_by_id(server->local_list,
575 client_id, TRUE, NULL);
577 silc_free(client_id);
581 silc_free(client_id);
583 /* Get entry to the channel user list */
584 silc_hash_table_list(channel->user_list, &htl);
585 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
586 /* If the mode is channel founder and we already find a client
587 to have that mode on the channel we will enforce the sender
588 to change the channel founder mode away. There can be only one
589 channel founder on the channel. */
590 if (server->server_type == SILC_ROUTER &&
591 mode & SILC_CHANNEL_UMODE_CHANFO &&
592 chl->mode & SILC_CHANNEL_UMODE_CHANFO) {
594 unsigned char cumode[4];
596 if (chl->client == client && chl->mode == mode) {
601 mode &= ~SILC_CHANNEL_UMODE_CHANFO;
602 silc_server_send_notify_cumode(server, sock, FALSE, channel, mode,
603 client->id, SILC_ID_CLIENT,
606 idp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
607 SILC_PUT32_MSB(mode, cumode);
608 silc_server_send_notify_to_channel(server, sock, channel, FALSE,
609 SILC_NOTIFY_TYPE_CUMODE_CHANGE,
610 3, idp->data, idp->len,
612 idp->data, idp->len);
613 silc_buffer_free(idp);
616 /* Force the mode change if we alredy set the mode */
619 silc_free(channel_id);
624 if (chl->client == client) {
625 if (chl->mode == mode) {
630 /* Change the mode */
632 if (!(mode & SILC_CHANNEL_UMODE_CHANFO))
639 /* Send the same notify to the channel */
641 silc_server_packet_send_to_channel(server, sock, channel,
643 FALSE, packet->buffer->data,
644 packet->buffer->len, FALSE);
646 silc_free(channel_id);
650 case SILC_NOTIFY_TYPE_INVITE:
652 if (packet->dst_id_type == SILC_ID_CLIENT)
655 SILC_LOG_DEBUG(("INVITE notify"));
658 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
661 channel_id = silc_id_payload_parse_id(tmp, tmp_len);
665 /* Get channel entry */
666 channel = silc_idlist_find_channel_by_id(server->global_list,
669 channel = silc_idlist_find_channel_by_id(server->local_list,
672 silc_free(channel_id);
676 silc_free(channel_id);
678 /* Get the added invite */
679 tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
681 if (!channel->invite_list)
682 channel->invite_list = silc_calloc(tmp_len + 2,
683 sizeof(*channel->invite_list));
685 channel->invite_list = silc_realloc(channel->invite_list,
686 sizeof(*channel->invite_list) *
688 strlen(channel->invite_list) +
690 if (tmp[tmp_len - 1] == ',')
691 tmp[tmp_len - 1] = '\0';
693 strncat(channel->invite_list, tmp, tmp_len);
694 strncat(channel->invite_list, ",", 1);
697 /* Get the deleted invite */
698 tmp = silc_argument_get_arg_type(args, 4, &tmp_len);
699 if (tmp && channel->invite_list) {
700 char *start, *end, *n;
702 if (!strncmp(channel->invite_list, tmp,
703 strlen(channel->invite_list) - 1)) {
704 silc_free(channel->invite_list);
705 channel->invite_list = NULL;
707 start = strstr(channel->invite_list, tmp);
708 if (start && strlen(start) >= tmp_len) {
709 end = start + tmp_len;
710 n = silc_calloc(strlen(channel->invite_list) - tmp_len, sizeof(*n));
711 strncat(n, channel->invite_list, start - channel->invite_list);
712 strncat(n, end + 1, ((channel->invite_list +
713 strlen(channel->invite_list)) - end) - 1);
714 silc_free(channel->invite_list);
715 channel->invite_list = n;
722 case SILC_NOTIFY_TYPE_CHANNEL_CHANGE:
724 * Distribute to the local clients on the channel and change the
728 SILC_LOG_DEBUG(("CHANNEL CHANGE"));
730 if (sock->type != SILC_SOCKET_TYPE_ROUTER)
733 /* Get the old Channel ID */
734 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
737 channel_id = silc_id_payload_parse_id(tmp, tmp_len);
741 /* Get the channel entry */
742 channel = silc_idlist_find_channel_by_id(server->global_list,
745 channel = silc_idlist_find_channel_by_id(server->local_list,
748 silc_free(channel_id);
753 /* Send the notify to the channel */
754 silc_server_packet_send_to_channel(server, sock, channel, packet->type,
755 FALSE, packet->buffer->data,
756 packet->buffer->len, FALSE);
758 /* Get the new Channel ID */
759 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
762 channel_id2 = silc_id_payload_parse_id(tmp, tmp_len);
766 SILC_LOG_DEBUG(("Old Channel ID id(%s)",
767 silc_id_render(channel_id, SILC_ID_CHANNEL)));
768 SILC_LOG_DEBUG(("New Channel ID id(%s)",
769 silc_id_render(channel_id2, SILC_ID_CHANNEL)));
771 /* Replace the Channel ID */
772 if (!silc_idlist_replace_channel_id(server->global_list, channel_id,
774 if (!silc_idlist_replace_channel_id(server->local_list, channel_id,
776 silc_free(channel_id2);
781 SilcBuffer users = NULL, users_modes = NULL;
783 /* Re-announce our clients on the channel as the ID has changed now */
784 silc_server_announce_get_channel_users(server, channel, &users,
787 silc_buffer_push(users, users->data - users->head);
788 silc_server_packet_send(server, sock,
789 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
790 users->data, users->len, FALSE);
791 silc_buffer_free(users);
794 silc_buffer_push(users_modes, users_modes->data - users_modes->head);
795 silc_server_packet_send_dest(server, sock,
796 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
797 channel->id, SILC_ID_CHANNEL,
799 users_modes->len, FALSE);
800 silc_buffer_free(users_modes);
804 silc_free(channel_id);
808 case SILC_NOTIFY_TYPE_SERVER_SIGNOFF:
810 * Remove the server entry and all clients that this server owns.
813 SILC_LOG_DEBUG(("SERVER SIGNOFF notify"));
816 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
819 server_id = silc_id_payload_parse_id(tmp, tmp_len);
823 /* Get server entry */
824 server_entry = silc_idlist_find_server_by_id(server->global_list,
825 server_id, TRUE, NULL);
827 server_entry = silc_idlist_find_server_by_id(server->local_list,
828 server_id, TRUE, NULL);
830 silc_free(server_id);
834 silc_free(server_id);
836 /* Free all client entries that this server owns as they will
837 become invalid now as well. */
838 silc_server_remove_clients_by_server(server, server_entry, TRUE);
840 /* Remove the server entry */
841 if (!silc_idlist_del_server(server->global_list, server_entry))
842 silc_idlist_del_server(server->local_list, server_entry);
844 /* XXX update statistics */
848 case SILC_NOTIFY_TYPE_KICKED:
850 * Distribute the notify to local clients on the channel
853 SILC_LOG_DEBUG(("KICKED notify"));
856 channel_id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
857 packet->dst_id_type);
862 /* Get channel entry */
863 channel = silc_idlist_find_channel_by_id(server->global_list,
866 channel = silc_idlist_find_channel_by_id(server->local_list,
869 silc_free(channel_id);
873 silc_free(channel_id);
876 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
879 client_id = silc_id_payload_parse_id(tmp, tmp_len);
883 /* If the the client is not in local list we check global list */
884 client = silc_idlist_find_client_by_id(server->global_list,
885 client_id, TRUE, NULL);
887 client = silc_idlist_find_client_by_id(server->local_list,
888 client_id, TRUE, NULL);
890 silc_free(client_id);
895 /* Send to channel */
896 silc_server_packet_send_to_channel(server, sock, channel, packet->type,
897 FALSE, packet->buffer->data,
898 packet->buffer->len, FALSE);
900 /* Remove the client from channel */
901 silc_server_remove_from_one_channel(server, sock, channel, client, FALSE);
905 case SILC_NOTIFY_TYPE_KILLED:
908 * Distribute the notify to local clients on channels
913 SILC_LOG_DEBUG(("KILLED notify"));
916 id = silc_argument_get_arg_type(args, 1, &id_len);
919 client_id = silc_id_payload_parse_id(id, id_len);
923 /* If the the client is not in local list we check global list */
924 client = silc_idlist_find_client_by_id(server->global_list,
925 client_id, TRUE, NULL);
927 client = silc_idlist_find_client_by_id(server->local_list,
928 client_id, TRUE, NULL);
930 silc_free(client_id);
934 silc_free(client_id);
936 /* If the client is one of ours, then close the connection to the
937 client now. This removes the client from all channels as well. */
938 if (packet->dst_id_type == SILC_ID_CLIENT && client->connection) {
939 sock = client->connection;
940 silc_server_free_client_data(server, NULL, client, FALSE, NULL);
941 silc_server_close_connection(server, sock);
946 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
950 /* Send the notify to local clients on the channels except to the
951 client who is killed. */
952 silc_server_send_notify_on_channels(server, client, client,
953 SILC_NOTIFY_TYPE_KILLED,
958 /* Remove the client from all channels */
959 silc_server_remove_from_channels(server, NULL, client, FALSE, NULL,
965 case SILC_NOTIFY_TYPE_UMODE_CHANGE:
967 * Save the mode of the client.
970 SILC_LOG_DEBUG(("UMODE_CHANGE notify"));
973 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
976 client_id = silc_id_payload_parse_id(tmp, tmp_len);
980 /* Get client entry */
981 client = silc_idlist_find_client_by_id(server->global_list,
982 client_id, TRUE, NULL);
984 client = silc_idlist_find_client_by_id(server->local_list,
985 client_id, TRUE, NULL);
987 silc_free(client_id);
991 silc_free(client_id);
994 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
999 SILC_GET32_MSB(client->mode, tmp);
1003 case SILC_NOTIFY_TYPE_BAN:
1008 SILC_LOG_DEBUG(("BAN notify"));
1010 /* Get Channel ID */
1011 tmp = silc_argument_get_arg_type(args, 1, &tmp_len);
1014 channel_id = silc_id_payload_parse_id(tmp, tmp_len);
1018 /* Get channel entry */
1019 channel = silc_idlist_find_channel_by_id(server->global_list,
1022 channel = silc_idlist_find_channel_by_id(server->local_list,
1025 silc_free(channel_id);
1029 silc_free(channel_id);
1031 /* Get the new ban and add it to the ban list */
1032 tmp = silc_argument_get_arg_type(args, 2, &tmp_len);
1034 if (!channel->ban_list)
1035 channel->ban_list = silc_calloc(tmp_len + 2,
1036 sizeof(*channel->ban_list));
1038 channel->ban_list = silc_realloc(channel->ban_list,
1039 sizeof(*channel->ban_list) *
1041 strlen(channel->ban_list) + 2));
1042 strncat(channel->ban_list, tmp, tmp_len);
1043 strncat(channel->ban_list, ",", 1);
1046 /* Get the ban to be removed and remove it from the list */
1047 tmp = silc_argument_get_arg_type(args, 3, &tmp_len);
1048 if (tmp && channel->ban_list) {
1049 char *start, *end, *n;
1051 if (!strcmp(channel->ban_list, tmp)) {
1052 silc_free(channel->ban_list);
1053 channel->ban_list = NULL;
1055 start = strstr(channel->ban_list, tmp);
1056 if (start && strlen(start) >= tmp_len) {
1057 end = start + tmp_len;
1058 n = silc_calloc(strlen(channel->ban_list) - tmp_len, sizeof(*n));
1059 strncat(n, channel->ban_list, start - channel->ban_list);
1060 strncat(n, end + 1, ((channel->ban_list +
1061 strlen(channel->ban_list)) - end) - 1);
1062 silc_free(channel->ban_list);
1063 channel->ban_list = n;
1070 /* Ignore rest of the notify types for now */
1071 case SILC_NOTIFY_TYPE_NONE:
1072 case SILC_NOTIFY_TYPE_MOTD:
1079 silc_notify_payload_free(payload);
1082 void silc_server_notify_list(SilcServer server,
1083 SilcSocketConnection sock,
1084 SilcPacketContext *packet)
1086 SilcPacketContext *new;
1090 SILC_LOG_DEBUG(("Processing Notify List"));
1092 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
1093 packet->src_id_type != SILC_ID_SERVER)
1096 /* Make copy of the original packet context, except for the actual
1097 data buffer, which we will here now fetch from the original buffer. */
1098 new = silc_packet_context_alloc();
1099 new->type = SILC_PACKET_NOTIFY;
1100 new->flags = packet->flags;
1101 new->src_id = packet->src_id;
1102 new->src_id_len = packet->src_id_len;
1103 new->src_id_type = packet->src_id_type;
1104 new->dst_id = packet->dst_id;
1105 new->dst_id_len = packet->dst_id_len;
1106 new->dst_id_type = packet->dst_id_type;
1108 buffer = silc_buffer_alloc(1024);
1109 new->buffer = buffer;
1111 while (packet->buffer->len) {
1112 SILC_GET16_MSB(len, packet->buffer->data + 2);
1113 if (len > packet->buffer->len)
1116 if (len > buffer->truelen) {
1117 silc_buffer_free(buffer);
1118 buffer = silc_buffer_alloc(1024 + len);
1121 silc_buffer_pull_tail(buffer, len);
1122 silc_buffer_put(buffer, packet->buffer->data, len);
1124 /* Process the Notify */
1125 silc_server_notify(server, sock, new);
1127 silc_buffer_push_tail(buffer, len);
1128 silc_buffer_pull(packet->buffer, len);
1131 silc_buffer_free(buffer);
1135 /* Received private message. This resolves the destination of the message
1136 and sends the packet. This is used by both server and router. If the
1137 destination is our locally connected client this sends the packet to
1138 the client. This may also send the message for further routing if
1139 the destination is not in our server (or router). */
1141 void silc_server_private_message(SilcServer server,
1142 SilcSocketConnection sock,
1143 SilcPacketContext *packet)
1145 SilcSocketConnection dst_sock;
1146 SilcIDListData idata;
1148 SILC_LOG_DEBUG(("Start"));
1150 if (packet->src_id_type != SILC_ID_CLIENT ||
1151 packet->dst_id_type != SILC_ID_CLIENT)
1154 if (!packet->dst_id)
1157 /* Get the route to the client */
1158 dst_sock = silc_server_get_client_route(server, packet->dst_id,
1159 packet->dst_id_len, NULL, &idata);
1163 /* Send the private message */
1164 silc_server_send_private_message(server, dst_sock, idata->send_key,
1165 idata->hmac_send, idata->psn_send++,
1169 /* Received private message key packet.. This packet is never for us. It is to
1170 the client in the packet's destination ID. Sending of this sort of packet
1171 equals sending private message, ie. it is sent point to point from
1172 one client to another. */
1174 void silc_server_private_message_key(SilcServer server,
1175 SilcSocketConnection sock,
1176 SilcPacketContext *packet)
1178 SilcSocketConnection dst_sock;
1179 SilcIDListData idata;
1181 SILC_LOG_DEBUG(("Start"));
1183 if (packet->src_id_type != SILC_ID_CLIENT ||
1184 packet->dst_id_type != SILC_ID_CLIENT)
1187 if (!packet->dst_id)
1190 /* Get the route to the client */
1191 dst_sock = silc_server_get_client_route(server, packet->dst_id,
1192 packet->dst_id_len, NULL, &idata);
1196 /* Relay the packet */
1197 silc_server_relay_packet(server, dst_sock, idata->send_key,
1198 idata->hmac_send, idata->psn_send++, packet, FALSE);
1201 /* Processes incoming command reply packet. The command reply packet may
1202 be destined to one of our clients or it may directly for us. We will
1203 call the command reply routine after processing the packet. */
1205 void silc_server_command_reply(SilcServer server,
1206 SilcSocketConnection sock,
1207 SilcPacketContext *packet)
1209 SilcBuffer buffer = packet->buffer;
1210 SilcClientEntry client = NULL;
1211 SilcSocketConnection dst_sock;
1212 SilcIDListData idata;
1213 SilcClientID *id = NULL;
1215 SILC_LOG_DEBUG(("Start"));
1217 /* Source must be server or router */
1218 if (packet->src_id_type != SILC_ID_SERVER &&
1219 sock->type != SILC_SOCKET_TYPE_ROUTER)
1222 if (packet->dst_id_type == SILC_ID_CHANNEL)
1225 if (packet->dst_id_type == SILC_ID_CLIENT) {
1226 /* Destination must be one of ours */
1227 id = silc_id_str2id(packet->dst_id, packet->dst_id_len, SILC_ID_CLIENT);
1230 client = silc_idlist_find_client_by_id(server->local_list, id, TRUE, NULL);
1232 SILC_LOG_ERROR(("Cannot process command reply to unknown client"));
1238 if (packet->dst_id_type == SILC_ID_SERVER) {
1239 /* For now this must be for us */
1240 if (memcmp(packet->dst_id, server->id_string, packet->dst_id_len)) {
1241 SILC_LOG_ERROR(("Cannot process command reply to unknown server"));
1246 /* Execute command reply locally for the command */
1247 silc_server_command_reply_process(server, sock, buffer);
1249 if (packet->dst_id_type == SILC_ID_CLIENT && client && id) {
1250 /* Relay the packet to the client */
1252 dst_sock = (SilcSocketConnection)client->connection;
1253 silc_buffer_push(buffer, SILC_PACKET_HEADER_LEN + packet->src_id_len
1254 + packet->dst_id_len + packet->padlen);
1256 silc_packet_send_prepare(dst_sock, 0, 0, buffer->len);
1257 silc_buffer_put(dst_sock->outbuf, buffer->data, buffer->len);
1259 idata = (SilcIDListData)client;
1261 /* Encrypt packet */
1262 silc_packet_encrypt(idata->send_key, idata->hmac_send, idata->psn_send++,
1263 dst_sock->outbuf, buffer->len);
1265 /* Send the packet */
1266 silc_server_packet_send_real(server, dst_sock, TRUE);
1272 /* Process received channel message. The message can be originated from
1273 client or server. */
1275 void silc_server_channel_message(SilcServer server,
1276 SilcSocketConnection sock,
1277 SilcPacketContext *packet)
1279 SilcChannelEntry channel = NULL;
1280 SilcChannelID *id = NULL;
1281 void *sender = NULL;
1282 void *sender_entry = NULL;
1285 SILC_LOG_DEBUG(("Processing channel message"));
1288 if (packet->dst_id_type != SILC_ID_CHANNEL) {
1289 SILC_LOG_DEBUG(("Received bad message for channel, dropped"));
1293 /* Find channel entry */
1294 id = silc_id_str2id(packet->dst_id, packet->dst_id_len, SILC_ID_CHANNEL);
1297 channel = silc_idlist_find_channel_by_id(server->local_list, id, NULL);
1299 channel = silc_idlist_find_channel_by_id(server->global_list, id, NULL);
1301 SILC_LOG_DEBUG(("Could not find channel"));
1306 /* See that this client is on the channel. If the original sender is
1307 not client (as it can be server as well) we don't do the check. */
1308 sender = silc_id_str2id(packet->src_id, packet->src_id_len,
1309 packet->src_id_type);
1312 if (packet->src_id_type == SILC_ID_CLIENT) {
1313 sender_entry = silc_idlist_find_client_by_id(server->local_list,
1314 sender, TRUE, NULL);
1315 if (!sender_entry) {
1317 sender_entry = silc_idlist_find_client_by_id(server->global_list,
1318 sender, TRUE, NULL);
1320 if (!sender_entry || !silc_server_client_on_channel(sender_entry,
1322 SILC_LOG_DEBUG(("Client not on channel"));
1326 /* If the packet is coming from router, but the client entry is
1327 local entry to us then some router is rerouting this to us and it is
1329 if (server->server_type == SILC_ROUTER &&
1330 sock->type == SILC_SOCKET_TYPE_ROUTER && local) {
1331 SILC_LOG_DEBUG(("Channel message rerouted to the sender, drop it"));
1336 /* Distribute the packet to our local clients. This will send the
1337 packet for further routing as well, if needed. */
1338 silc_server_packet_relay_to_channel(server, sock, channel, sender,
1339 packet->src_id_type, sender_entry,
1340 packet->buffer->data,
1341 packet->buffer->len, FALSE);
1350 /* Received channel key packet. We distribute the key to all of our locally
1351 connected clients on the channel. */
1353 void silc_server_channel_key(SilcServer server,
1354 SilcSocketConnection sock,
1355 SilcPacketContext *packet)
1357 SilcBuffer buffer = packet->buffer;
1358 SilcChannelEntry channel;
1360 if (packet->src_id_type != SILC_ID_SERVER ||
1361 (server->server_type == SILC_ROUTER &&
1362 sock->type == SILC_SOCKET_TYPE_ROUTER))
1365 /* Save the channel key */
1366 channel = silc_server_save_channel_key(server, buffer, NULL);
1370 /* Distribute the key to everybody who is on the channel. If we are router
1371 we will also send it to locally connected servers. */
1372 silc_server_send_channel_key(server, sock, channel, FALSE);
1374 if (server->server_type != SILC_BACKUP_ROUTER) {
1375 /* Distribute to local cell backup routers. */
1376 silc_server_backup_send(server, (SilcServerEntry)sock->user_data,
1377 SILC_PACKET_CHANNEL_KEY, 0,
1378 buffer->data, buffer->len, FALSE, TRUE);
1382 /* Received New Client packet and processes it. Creates Client ID for the
1383 client. Client becomes registered after calling this functions. */
1385 SilcClientEntry silc_server_new_client(SilcServer server,
1386 SilcSocketConnection sock,
1387 SilcPacketContext *packet)
1389 SilcBuffer buffer = packet->buffer;
1390 SilcClientEntry client;
1391 SilcClientID *client_id;
1393 SilcIDListData idata;
1394 char *username = NULL, *realname = NULL, *id_string;
1397 char *hostname, *nickname;
1400 SILC_LOG_DEBUG(("Creating new client"));
1402 if (sock->type != SILC_SOCKET_TYPE_CLIENT)
1405 /* Take client entry */
1406 client = (SilcClientEntry)sock->user_data;
1407 idata = (SilcIDListData)client;
1409 /* Remove the old cache entry */
1410 if (!silc_idcache_del_by_context(server->local_list->clients, client)) {
1411 SILC_LOG_ERROR(("Lost client's cache entry - bad thing"));
1412 silc_server_disconnect_remote(server, sock, "Server closed connection: "
1417 /* Parse incoming packet */
1418 ret = silc_buffer_unformat(buffer,
1419 SILC_STR_UI16_STRING_ALLOC(&username),
1420 SILC_STR_UI16_STRING_ALLOC(&realname),
1424 silc_free(username);
1426 silc_free(realname);
1427 silc_server_disconnect_remote(server, sock, "Server closed connection: "
1428 "Incomplete client information");
1433 silc_free(username);
1435 silc_free(realname);
1436 silc_server_disconnect_remote(server, sock, "Server closed connection: "
1437 "Incomplete client information");
1441 if (strlen(username) > 128)
1442 username[127] = '\0';
1444 nickname = strdup(username);
1446 /* Make sanity checks for the hostname of the client. If the hostname
1447 is provided in the `username' check that it is the same than the
1448 resolved hostname, or if not resolved the hostname that appears in
1449 the client's public key. If the hostname is not present then put
1450 it from the resolved name or from the public key. */
1451 if (strchr(username, '@')) {
1452 SilcPublicKeyIdentifier pident;
1453 int tlen = strcspn(username, "@");
1454 char *phostname = NULL;
1456 hostname = silc_calloc((strlen(username) - tlen) + 1, sizeof(char));
1457 memcpy(hostname, username + tlen + 1, strlen(username) - tlen - 1);
1459 if (strcmp(sock->hostname, sock->ip) &&
1460 strcmp(sock->hostname, hostname)) {
1461 silc_free(username);
1462 silc_free(hostname);
1464 silc_free(realname);
1465 silc_server_disconnect_remote(server, sock,
1466 "Server closed connection: "
1467 "Incomplete client information");
1471 pident = silc_pkcs_decode_identifier(client->data.public_key->identifier);
1473 phostname = strdup(pident->host);
1474 silc_pkcs_free_identifier(pident);
1477 if (!strcmp(sock->hostname, sock->ip) &&
1478 phostname && strcmp(phostname, hostname)) {
1479 silc_free(username);
1480 silc_free(hostname);
1482 silc_free(phostname);
1484 silc_free(realname);
1485 silc_server_disconnect_remote(server, sock,
1486 "Server closed connection: "
1487 "Incomplete client information");
1492 silc_free(phostname);
1494 /* The hostname is not present, add it. */
1496 /* XXX For now we cannot take the host name from the public key since
1497 they are not trusted or we cannot verify them as trusted. Just take
1498 what the resolved name or address is. */
1500 if (strcmp(sock->hostname, sock->ip)) {
1502 newusername = silc_calloc(strlen(username) +
1503 strlen(sock->hostname) + 2,
1504 sizeof(*newusername));
1505 strncat(newusername, username, strlen(username));
1506 strncat(newusername, "@", 1);
1507 strncat(newusername, sock->hostname, strlen(sock->hostname));
1508 silc_free(username);
1509 username = newusername;
1512 SilcPublicKeyIdentifier pident =
1513 silc_pkcs_decode_identifier(client->data.public_key->identifier);
1516 newusername = silc_calloc(strlen(username) +
1517 strlen(pident->host) + 2,
1518 sizeof(*newusername));
1519 strncat(newusername, username, strlen(username));
1520 strncat(newusername, "@", 1);
1521 strncat(newusername, pident->host, strlen(pident->host));
1522 silc_free(username);
1523 username = newusername;
1524 silc_pkcs_free_identifier(pident);
1530 /* Create Client ID */
1531 while (!silc_id_create_client_id(server, server->id, server->rng,
1532 server->md5hash, nickname, &client_id)) {
1534 snprintf(&nickname[strlen(nickname) - 1], 1, "%d", nickfail);
1537 /* Update client entry */
1538 idata->status |= SILC_IDLIST_STATUS_REGISTERED;
1539 client->nickname = nickname;
1540 client->username = username;
1541 client->userinfo = realname ? realname : strdup(" ");
1542 client->id = client_id;
1543 id_len = silc_id_get_len(client_id, SILC_ID_CLIENT);
1545 /* Add the client again to the ID cache */
1546 silc_idcache_add(server->local_list->clients, client->nickname,
1547 client_id, client, FALSE);
1549 /* Notify our router about new client on the SILC network */
1550 if (!server->standalone)
1551 silc_server_send_new_id(server, (SilcSocketConnection)
1552 server->router->connection,
1553 server->server_type == SILC_ROUTER ? TRUE : FALSE,
1554 client->id, SILC_ID_CLIENT, id_len);
1556 /* Send the new client ID to the client. */
1557 id_string = silc_id_id2str(client->id, SILC_ID_CLIENT);
1558 reply = silc_buffer_alloc(2 + 2 + id_len);
1559 silc_buffer_pull_tail(reply, SILC_BUFFER_END(reply));
1560 silc_buffer_format(reply,
1561 SILC_STR_UI_SHORT(SILC_ID_CLIENT),
1562 SILC_STR_UI_SHORT(id_len),
1563 SILC_STR_UI_XNSTRING(id_string, id_len),
1565 silc_server_packet_send(server, sock, SILC_PACKET_NEW_ID, 0,
1566 reply->data, reply->len, FALSE);
1567 silc_free(id_string);
1568 silc_buffer_free(reply);
1570 /* Send some nice info to the client */
1571 SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1572 ("Welcome to the SILC Network %s",
1574 SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1575 ("Your host is %s, running version %s",
1576 server->config->server_info->server_name,
1578 if (server->server_type == SILC_ROUTER) {
1579 SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1580 ("There are %d clients on %d servers in SILC "
1581 "Network", server->stat.clients,
1582 server->stat.servers + 1));
1583 SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1584 ("There are %d clients on %d server in our cell",
1585 server->stat.cell_clients,
1586 server->stat.cell_servers + 1));
1587 SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1588 ("I have %d clients, %d channels, %d servers and "
1590 server->stat.my_clients,
1591 server->stat.my_channels,
1592 server->stat.my_servers,
1593 server->stat.my_routers));
1594 SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1595 ("%d server operators and %d router operators "
1597 server->stat.my_server_ops,
1598 server->stat.my_router_ops));
1600 SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1601 ("I have %d clients and %d channels formed",
1602 server->stat.my_clients,
1603 server->stat.my_channels));
1604 SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1605 ("%d operators online",
1606 server->stat.my_server_ops));
1608 SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1609 ("Your connection is secured with %s cipher, "
1610 "key length %d bits",
1611 idata->send_key->cipher->name,
1612 idata->send_key->cipher->key_len));
1613 SILC_SERVER_SEND_NOTIFY(server, sock, SILC_NOTIFY_TYPE_NONE,
1614 ("Your current nickname is %s",
1618 silc_server_send_motd(server, sock);
1623 /* Create new server. This processes received New Server packet and
1624 saves the received Server ID. The server is our locally connected
1625 server thus we save all the information and save it to local list.
1626 This funtion can be used by both normal server and router server.
1627 If normal server uses this it means that its router has connected
1628 to the server. If router uses this it means that one of the cell's
1629 servers is connected to the router. */
1631 SilcServerEntry silc_server_new_server(SilcServer server,
1632 SilcSocketConnection sock,
1633 SilcPacketContext *packet)
1635 SilcBuffer buffer = packet->buffer;
1636 SilcServerEntry new_server, server_entry;
1637 SilcServerID *server_id;
1638 SilcIDListData idata;
1639 unsigned char *server_name, *id_string;
1640 uint16 id_len, name_len;
1644 SILC_LOG_DEBUG(("Creating new server"));
1646 if (sock->type != SILC_SOCKET_TYPE_SERVER &&
1647 sock->type != SILC_SOCKET_TYPE_ROUTER)
1650 /* Take server entry */
1651 new_server = (SilcServerEntry)sock->user_data;
1652 idata = (SilcIDListData)new_server;
1654 /* Remove the old cache entry */
1655 if (!silc_idcache_del_by_context(server->local_list->servers, new_server)) {
1656 silc_idcache_del_by_context(server->global_list->servers, new_server);
1660 /* Parse the incoming packet */
1661 ret = silc_buffer_unformat(buffer,
1662 SILC_STR_UI16_NSTRING_ALLOC(&id_string, &id_len),
1663 SILC_STR_UI16_NSTRING_ALLOC(&server_name,
1668 silc_free(id_string);
1670 silc_free(server_name);
1674 if (id_len > buffer->len) {
1675 silc_free(id_string);
1676 silc_free(server_name);
1681 server_name[255] = '\0';
1684 server_id = silc_id_str2id(id_string, id_len, SILC_ID_SERVER);
1686 silc_free(id_string);
1687 silc_free(server_name);
1690 silc_free(id_string);
1692 /* Check that we do not have this ID already */
1693 server_entry = silc_idlist_find_server_by_id(server->local_list,
1694 server_id, TRUE, NULL);
1696 silc_idcache_del_by_context(server->local_list->servers, server_entry);
1698 server_entry = silc_idlist_find_server_by_id(server->global_list,
1699 server_id, TRUE, NULL);
1701 silc_idcache_del_by_context(server->global_list->servers, server_entry);
1704 /* Update server entry */
1705 idata->status |= SILC_IDLIST_STATUS_REGISTERED;
1706 new_server->server_name = server_name;
1707 new_server->id = server_id;
1709 SILC_LOG_DEBUG(("New server id(%s)",
1710 silc_id_render(server_id, SILC_ID_SERVER)));
1712 /* Add again the entry to the ID cache. */
1713 silc_idcache_add(local ? server->local_list->servers :
1714 server->global_list->servers, server_name, server_id,
1717 /* Distribute the information about new server in the SILC network
1718 to our router. If we are normal server we won't send anything
1719 since this connection must be our router connection. */
1720 if (server->server_type == SILC_ROUTER && !server->standalone &&
1721 server->router->connection != sock)
1722 silc_server_send_new_id(server, server->router->connection,
1723 TRUE, new_server->id, SILC_ID_SERVER,
1724 silc_id_get_len(server_id, SILC_ID_SERVER));
1726 if (server->server_type == SILC_ROUTER)
1727 server->stat.cell_servers++;
1729 /* Check whether this router connection has been replaced by an
1730 backup router. If it has been then we'll disable the server and will
1731 ignore everything it will send until the backup router resuming
1732 protocol has been completed. */
1733 if (sock->type == SILC_SOCKET_TYPE_ROUTER &&
1734 silc_server_backup_replaced_get(server, server_id, NULL)) {
1735 /* Send packet to the server indicating that it cannot use this
1736 connection as it has been replaced by backup router. */
1737 SilcBuffer packet = silc_buffer_alloc(2);
1738 silc_buffer_pull_tail(packet, SILC_BUFFER_END(packet));
1739 silc_buffer_format(packet,
1740 SILC_STR_UI_CHAR(SILC_SERVER_BACKUP_REPLACED),
1741 SILC_STR_UI_CHAR(0),
1743 silc_server_packet_send(server, sock,
1744 SILC_PACKET_RESUME_ROUTER, 0,
1745 packet->data, packet->len, TRUE);
1746 silc_buffer_free(packet);
1748 /* Mark the router disabled. The data sent earlier will go but nothing
1749 after this does not go to this connection. */
1750 idata->status |= SILC_IDLIST_STATUS_DISABLED;
1752 /* If it is router announce our stuff to it. */
1753 if (sock->type == SILC_SOCKET_TYPE_ROUTER &&
1754 server->server_type == SILC_ROUTER) {
1755 silc_server_announce_servers(server, FALSE, 0, sock);
1756 silc_server_announce_clients(server, 0, sock);
1757 silc_server_announce_channels(server, 0, sock);
1764 /* Processes incoming New ID packet. New ID Payload is used to distribute
1765 information about newly registered clients and servers. */
1767 static void silc_server_new_id_real(SilcServer server,
1768 SilcSocketConnection sock,
1769 SilcPacketContext *packet,
1772 SilcBuffer buffer = packet->buffer;
1774 SilcServerEntry router, server_entry;
1775 SilcSocketConnection router_sock;
1780 SILC_LOG_DEBUG(("Processing new ID"));
1782 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
1783 server->server_type == SILC_SERVER ||
1784 packet->src_id_type != SILC_ID_SERVER)
1787 idp = silc_id_payload_parse(buffer);
1791 id_type = silc_id_payload_get_type(idp);
1793 /* Normal server cannot have other normal server connections */
1794 server_entry = (SilcServerEntry)sock->user_data;
1795 if (id_type == SILC_ID_SERVER && sock->type == SILC_SOCKET_TYPE_SERVER &&
1796 server_entry->server_type == SILC_SERVER)
1799 id = silc_id_payload_get_id(idp);
1803 /* If the packet is coming from server then use the sender as the
1804 origin of the the packet. If it came from router then check the real
1805 sender of the packet and use that as the origin. */
1806 if (sock->type == SILC_SOCKET_TYPE_SERVER) {
1807 id_list = server->local_list;
1809 router = sock->user_data;
1811 /* If the sender is backup router and ID is server (and we are not
1812 backup router) then switch the entry to global list. */
1813 if (server_entry->server_type == SILC_BACKUP_ROUTER &&
1814 id_type == SILC_ID_SERVER &&
1815 server->id_entry->server_type != SILC_BACKUP_ROUTER) {
1816 id_list = server->global_list;
1817 router_sock = server->router ? server->router->connection : sock;
1820 void *sender_id = silc_id_str2id(packet->src_id, packet->src_id_len,
1821 packet->src_id_type);
1822 router = silc_idlist_find_server_by_id(server->global_list,
1823 sender_id, TRUE, NULL);
1825 router = silc_idlist_find_server_by_id(server->local_list,
1826 sender_id, TRUE, NULL);
1827 silc_free(sender_id);
1831 id_list = server->global_list;
1835 case SILC_ID_CLIENT:
1837 SilcClientEntry entry;
1839 /* Check that we do not have this client already */
1840 entry = silc_idlist_find_client_by_id(server->global_list,
1841 id, server->server_type,
1844 entry = silc_idlist_find_client_by_id(server->local_list,
1845 id, server->server_type,
1848 SILC_LOG_DEBUG(("Ignoring client that we already have"));
1852 SILC_LOG_DEBUG(("New client id(%s) from [%s] %s",
1853 silc_id_render(id, SILC_ID_CLIENT),
1854 sock->type == SILC_SOCKET_TYPE_SERVER ?
1855 "Server" : "Router", sock->hostname));
1857 /* As a router we keep information of all global information in our
1858 global list. Cell wide information however is kept in the local
1860 entry = silc_idlist_add_client(id_list, NULL, NULL, NULL,
1863 SILC_LOG_ERROR(("Could not add new client to the ID Cache"));
1865 /* Inform the sender that the ID is not usable */
1866 silc_server_send_notify_signoff(server, sock, FALSE, id, NULL);
1869 entry->nickname = NULL;
1870 entry->data.status |= SILC_IDLIST_STATUS_REGISTERED;
1872 if (sock->type == SILC_SOCKET_TYPE_SERVER)
1873 server->stat.cell_clients++;
1874 server->stat.clients++;
1878 case SILC_ID_SERVER:
1880 SilcServerEntry entry;
1882 /* If the ID is mine, ignore it. */
1883 if (SILC_ID_SERVER_COMPARE(id, server->id)) {
1884 SILC_LOG_DEBUG(("Ignoring my own ID as new ID"));
1888 /* If the ID is the sender's ID, ignore it (we have it already) */
1889 if (SILC_ID_SERVER_COMPARE(id, router->id)) {
1890 SILC_LOG_DEBUG(("Ignoring sender's own ID"));
1894 /* Check that we do not have this server already */
1895 entry = silc_idlist_find_server_by_id(server->global_list,
1896 id, server->server_type,
1899 entry = silc_idlist_find_server_by_id(server->local_list,
1900 id, server->server_type,
1903 SILC_LOG_DEBUG(("Ignoring server that we already have"));
1907 SILC_LOG_DEBUG(("New server id(%s) from [%s] %s",
1908 silc_id_render(id, SILC_ID_SERVER),
1909 sock->type == SILC_SOCKET_TYPE_SERVER ?
1910 "Server" : "Router", sock->hostname));
1912 /* As a router we keep information of all global information in our
1913 global list. Cell wide information however is kept in the local
1915 entry = silc_idlist_add_server(id_list, NULL, 0, id, router,
1918 SILC_LOG_ERROR(("Could not add new server to the ID Cache"));
1921 entry->data.status |= SILC_IDLIST_STATUS_REGISTERED;
1923 if (sock->type == SILC_SOCKET_TYPE_SERVER)
1924 server->stat.cell_servers++;
1925 server->stat.servers++;
1929 case SILC_ID_CHANNEL:
1930 SILC_LOG_ERROR(("Channel cannot be registered with NEW_ID packet"));
1939 /* If the sender of this packet is server and we are router we need to
1940 broadcast this packet to other routers in the network. */
1941 if (broadcast && !server->standalone && server->server_type == SILC_ROUTER &&
1942 sock->type == SILC_SOCKET_TYPE_SERVER &&
1943 !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
1944 SILC_LOG_DEBUG(("Broadcasting received New ID packet"));
1945 silc_server_packet_send(server, server->router->connection,
1947 packet->flags | SILC_PACKET_FLAG_BROADCAST,
1948 buffer->data, buffer->len, FALSE);
1949 silc_server_backup_send(server, (SilcServerEntry)sock->user_data,
1950 packet->type, packet->flags,
1951 packet->buffer->data, packet->buffer->len,
1956 silc_id_payload_free(idp);
1960 /* Processes incoming New ID packet. New ID Payload is used to distribute
1961 information about newly registered clients and servers. */
1963 void silc_server_new_id(SilcServer server, SilcSocketConnection sock,
1964 SilcPacketContext *packet)
1966 silc_server_new_id_real(server, sock, packet, TRUE);
1969 /* Receoved New Id List packet, list of New ID payloads inside one
1970 packet. Process the New ID payloads one by one. */
1972 void silc_server_new_id_list(SilcServer server, SilcSocketConnection sock,
1973 SilcPacketContext *packet)
1975 SilcPacketContext *new_id;
1979 SILC_LOG_DEBUG(("Processing New ID List"));
1981 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
1982 packet->src_id_type != SILC_ID_SERVER)
1985 /* If the sender of this packet is server and we are router we need to
1986 broadcast this packet to other routers in the network. Broadcast
1987 this list packet instead of multiple New ID packets. */
1988 if (!server->standalone && server->server_type == SILC_ROUTER &&
1989 sock->type == SILC_SOCKET_TYPE_SERVER &&
1990 !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
1991 SILC_LOG_DEBUG(("Broadcasting received New ID List packet"));
1992 silc_server_packet_send(server, server->router->connection,
1994 packet->flags | SILC_PACKET_FLAG_BROADCAST,
1995 packet->buffer->data, packet->buffer->len, FALSE);
1996 silc_server_backup_send(server, (SilcServerEntry)sock->user_data,
1997 packet->type, packet->flags,
1998 packet->buffer->data, packet->buffer->len,
2002 /* Make copy of the original packet context, except for the actual
2003 data buffer, which we will here now fetch from the original buffer. */
2004 new_id = silc_packet_context_alloc();
2005 new_id->type = SILC_PACKET_NEW_ID;
2006 new_id->flags = packet->flags;
2007 new_id->src_id = packet->src_id;
2008 new_id->src_id_len = packet->src_id_len;
2009 new_id->src_id_type = packet->src_id_type;
2010 new_id->dst_id = packet->dst_id;
2011 new_id->dst_id_len = packet->dst_id_len;
2012 new_id->dst_id_type = packet->dst_id_type;
2014 idp = silc_buffer_alloc(256);
2015 new_id->buffer = idp;
2017 while (packet->buffer->len) {
2018 SILC_GET16_MSB(id_len, packet->buffer->data + 2);
2019 if ((id_len > packet->buffer->len) ||
2020 (id_len > idp->truelen))
2023 silc_buffer_pull_tail(idp, 4 + id_len);
2024 silc_buffer_put(idp, packet->buffer->data, 4 + id_len);
2026 /* Process the New ID */
2027 silc_server_new_id_real(server, sock, new_id, FALSE);
2029 silc_buffer_push_tail(idp, 4 + id_len);
2030 silc_buffer_pull(packet->buffer, 4 + id_len);
2033 silc_buffer_free(idp);
2037 /* Received New Channel packet. Information about new channels in the
2038 network are distributed using this packet. Save the information about
2039 the new channel. This usually comes from router but also normal server
2040 can send this to notify channels it has when it connects to us. */
2042 void silc_server_new_channel(SilcServer server,
2043 SilcSocketConnection sock,
2044 SilcPacketContext *packet)
2046 SilcChannelPayload payload;
2047 SilcChannelID *channel_id;
2053 SilcServerEntry server_entry;
2054 SilcChannelEntry channel;
2056 SILC_LOG_DEBUG(("Processing New Channel"));
2058 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
2059 packet->src_id_type != SILC_ID_SERVER ||
2060 server->server_type == SILC_SERVER)
2063 /* Parse the channel payload */
2064 payload = silc_channel_payload_parse(packet->buffer);
2068 /* Get the channel ID */
2069 channel_id = silc_channel_get_id_parse(payload);
2071 silc_channel_payload_free(payload);
2075 channel_name = silc_channel_get_name(payload, &name_len);
2077 channel_name[255] = '\0';
2079 id = silc_channel_get_id(payload, &id_len);
2081 server_entry = (SilcServerEntry)sock->user_data;
2083 if (sock->type == SILC_SOCKET_TYPE_ROUTER) {
2084 /* Add the channel to global list as it is coming from router. It
2085 cannot be our own channel as it is coming from router. */
2087 /* Check that we don't already have this channel */
2088 channel = silc_idlist_find_channel_by_name(server->local_list,
2089 channel_name, NULL);
2091 channel = silc_idlist_find_channel_by_name(server->global_list,
2092 channel_name, NULL);
2094 SILC_LOG_DEBUG(("New channel id(%s) from [Router] %s",
2095 silc_id_render(channel_id, SILC_ID_CHANNEL),
2098 silc_idlist_add_channel(server->global_list, strdup(channel_name),
2099 0, channel_id, sock->user_data, NULL, NULL);
2100 server->stat.channels++;
2103 /* The channel is coming from our server, thus it is in our cell
2104 we will add it to our local list. */
2107 SILC_LOG_DEBUG(("Channel id(%s) from [Server] %s",
2108 silc_id_render(channel_id, SILC_ID_CHANNEL),
2111 /* Check that we don't already have this channel */
2112 channel = silc_idlist_find_channel_by_name(server->local_list,
2113 channel_name, NULL);
2115 channel = silc_idlist_find_channel_by_name(server->global_list,
2116 channel_name, NULL);
2118 /* If the channel does not exist, then create it. This creates a new
2119 key to the channel as well that we will send to the server. */
2121 /* The protocol says that the Channel ID's IP address must be based
2122 on the router's IP address. Check whether the ID is based in our
2123 IP and if it is not then create a new ID and enforce the server
2124 to switch the ID. */
2125 if (server_entry->server_type != SILC_BACKUP_ROUTER &&
2126 !SILC_ID_COMPARE(channel_id, server->id, server->id->ip.data_len)) {
2128 SILC_LOG_DEBUG(("Forcing the server to change Channel ID"));
2130 if (silc_id_create_channel_id(server, server->id, server->rng, &tmp)) {
2131 silc_server_send_notify_channel_change(server, sock, FALSE,
2133 silc_free(channel_id);
2138 /* Create the channel with the provided Channel ID */
2139 channel = silc_server_create_new_channel_with_id(server, NULL, NULL,
2143 silc_channel_payload_free(payload);
2144 silc_free(channel_id);
2148 /* Get the mode and set it to the channel */
2149 channel->mode = silc_channel_get_mode(payload);
2151 /* Send the new channel key to the server */
2152 chk = silc_channel_key_payload_encode(id_len, id,
2153 strlen(channel->channel_key->
2155 channel->channel_key->cipher->name,
2156 channel->key_len / 8,
2158 silc_server_packet_send(server, sock, SILC_PACKET_CHANNEL_KEY, 0,
2159 chk->data, chk->len, FALSE);
2160 silc_buffer_free(chk);
2163 /* The channel exist by that name, check whether the ID's match.
2164 If they don't then we'll force the server to use the ID we have.
2165 We also create a new key for the channel. */
2166 SilcBuffer users = NULL, users_modes = NULL;
2168 if (!SILC_ID_CHANNEL_COMPARE(channel_id, channel->id)) {
2169 /* They don't match, send CHANNEL_CHANGE notify to the server to
2170 force the ID change. */
2171 SILC_LOG_DEBUG(("Forcing the server to change Channel ID"));
2172 silc_server_send_notify_channel_change(server, sock, FALSE,
2173 channel_id, channel->id);
2176 /* If the mode is different from what we have then enforce the
2178 mode = silc_channel_get_mode(payload);
2179 if (channel->mode != mode) {
2180 SILC_LOG_DEBUG(("Forcing the server to change channel mode"));
2181 silc_server_send_notify_cmode(server, sock, FALSE, channel,
2182 channel->mode, server->id,
2184 channel->cipher, channel->hmac_name);
2187 /* Create new key for the channel and send it to the server and
2188 everybody else possibly on the channel. */
2190 if (!(channel->mode & SILC_CHANNEL_MODE_PRIVKEY)) {
2191 if (!silc_server_create_channel_key(server, channel, 0))
2194 /* Send to the channel */
2195 silc_server_send_channel_key(server, sock, channel, FALSE);
2196 id = silc_id_id2str(channel->id, SILC_ID_CHANNEL);
2197 id_len = SILC_ID_CHANNEL_LEN;
2199 /* Send to the server */
2200 chk = silc_channel_key_payload_encode(id_len, id,
2201 strlen(channel->channel_key->
2203 channel->channel_key->
2205 channel->key_len / 8,
2207 silc_server_packet_send(server, sock, SILC_PACKET_CHANNEL_KEY, 0,
2208 chk->data, chk->len, FALSE);
2209 silc_buffer_free(chk);
2213 silc_free(channel_id);
2215 /* Since the channel is coming from server and we also know about it
2216 then send the JOIN notify to the server so that it see's our
2217 users on the channel "joining" the channel. */
2218 silc_server_announce_get_channel_users(server, channel, &users,
2221 silc_buffer_push(users, users->data - users->head);
2222 silc_server_packet_send(server, sock,
2223 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
2224 users->data, users->len, FALSE);
2225 silc_buffer_free(users);
2228 silc_buffer_push(users_modes, users_modes->data - users_modes->head);
2229 silc_server_packet_send_dest(server, sock,
2230 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
2231 channel->id, SILC_ID_CHANNEL,
2233 users_modes->len, FALSE);
2234 silc_buffer_free(users_modes);
2239 silc_channel_payload_free(payload);
2242 /* Received New Channel List packet, list of New Channel List payloads inside
2243 one packet. Process the New Channel payloads one by one. */
2245 void silc_server_new_channel_list(SilcServer server,
2246 SilcSocketConnection sock,
2247 SilcPacketContext *packet)
2249 SilcPacketContext *new;
2253 SILC_LOG_DEBUG(("Processing New Channel List"));
2255 if (sock->type == SILC_SOCKET_TYPE_CLIENT ||
2256 packet->src_id_type != SILC_ID_SERVER ||
2257 server->server_type == SILC_SERVER)
2260 /* If the sender of this packet is server and we are router we need to
2261 broadcast this packet to other routers in the network. Broadcast
2262 this list packet instead of multiple New Channel packets. */
2263 if (!server->standalone && server->server_type == SILC_ROUTER &&
2264 sock->type == SILC_SOCKET_TYPE_SERVER &&
2265 !(packet->flags & SILC_PACKET_FLAG_BROADCAST)) {
2266 SILC_LOG_DEBUG(("Broadcasting received New Channel List packet"));
2267 silc_server_packet_send(server, server->router->connection,
2269 packet->flags | SILC_PACKET_FLAG_BROADCAST,
2270 packet->buffer->data, packet->buffer->len, FALSE);
2271 silc_server_backup_send(server, (SilcServerEntry)sock->user_data,
2272 packet->type, packet->flags,
2273 packet->buffer->data, packet->buffer->len,
2277 /* Make copy of the original packet context, except for the actual
2278 data buffer, which we will here now fetch from the original buffer. */
2279 new = silc_packet_context_alloc();
2280 new->type = SILC_PACKET_NEW_CHANNEL;
2281 new->flags = packet->flags;
2282 new->src_id = packet->src_id;
2283 new->src_id_len = packet->src_id_len;
2284 new->src_id_type = packet->src_id_type;
2285 new->dst_id = packet->dst_id;
2286 new->dst_id_len = packet->dst_id_len;
2287 new->dst_id_type = packet->dst_id_type;
2289 buffer = silc_buffer_alloc(512);
2290 new->buffer = buffer;
2292 while (packet->buffer->len) {
2293 SILC_GET16_MSB(len1, packet->buffer->data);
2294 if ((len1 > packet->buffer->len) ||
2295 (len1 > buffer->truelen))
2298 SILC_GET16_MSB(len2, packet->buffer->data + 2 + len1);
2299 if ((len2 > packet->buffer->len) ||
2300 (len2 > buffer->truelen))
2303 silc_buffer_pull_tail(buffer, 8 + len1 + len2);
2304 silc_buffer_put(buffer, packet->buffer->data, 8 + len1 + len2);
2306 /* Process the New Channel */
2307 silc_server_new_channel(server, sock, new);
2309 silc_buffer_push_tail(buffer, 8 + len1 + len2);
2310 silc_buffer_pull(packet->buffer, 8 + len1 + len2);
2313 silc_buffer_free(buffer);
2317 /* Received key agreement packet. This packet is never for us. It is to
2318 the client in the packet's destination ID. Sending of this sort of packet
2319 equals sending private message, ie. it is sent point to point from
2320 one client to another. */
2322 void silc_server_key_agreement(SilcServer server,
2323 SilcSocketConnection sock,
2324 SilcPacketContext *packet)
2326 SilcSocketConnection dst_sock;
2327 SilcIDListData idata;
2329 SILC_LOG_DEBUG(("Start"));
2331 if (packet->src_id_type != SILC_ID_CLIENT ||
2332 packet->dst_id_type != SILC_ID_CLIENT)
2335 if (!packet->dst_id)
2338 /* Get the route to the client */
2339 dst_sock = silc_server_get_client_route(server, packet->dst_id,
2340 packet->dst_id_len, NULL, &idata);
2344 /* Relay the packet */
2345 silc_server_relay_packet(server, dst_sock, idata->send_key,
2346 idata->hmac_send, idata->psn_send++,
2350 /* Received connection auth request packet that is used during connection
2351 phase to resolve the mandatory authentication method. This packet can
2352 actually be received at anytime but usually it is used only during
2353 the connection authentication phase. Now, protocol says that this packet
2354 can come from client or server, however, we support only this coming
2355 from client and expect that server always knows what authentication
2358 void silc_server_connection_auth_request(SilcServer server,
2359 SilcSocketConnection sock,
2360 SilcPacketContext *packet)
2362 SilcServerConfigSectionClientConnection *client = NULL;
2365 SilcAuthMethod auth_meth;
2367 SILC_LOG_DEBUG(("Start"));
2369 if (packet->src_id_type && packet->src_id_type != SILC_ID_CLIENT)
2372 /* Parse the payload */
2373 ret = silc_buffer_unformat(packet->buffer,
2374 SILC_STR_UI_SHORT(&conn_type),
2375 SILC_STR_UI_SHORT(NULL),
2380 if (conn_type != SILC_SOCKET_TYPE_CLIENT)
2383 /* Get the authentication method for the client */
2384 auth_meth = SILC_AUTH_NONE;
2385 port = server->sockets[server->sock]->port; /* Listenning port */
2386 client = silc_server_config_find_client_conn(server->config,
2390 client = silc_server_config_find_client_conn(server->config,
2394 auth_meth = client->auth_meth;
2396 /* Send it back to the client */
2397 silc_server_send_connection_auth_request(server, sock,
2402 /* Received REKEY packet. The sender of the packet wants to regenerate
2403 its session keys. This starts the REKEY protocol. */
2405 void silc_server_rekey(SilcServer server,
2406 SilcSocketConnection sock,
2407 SilcPacketContext *packet)
2409 SilcProtocol protocol;
2410 SilcServerRekeyInternalContext *proto_ctx;
2411 SilcIDListData idata = (SilcIDListData)sock->user_data;
2413 SILC_LOG_DEBUG(("Start"));
2415 /* Allocate internal protocol context. This is sent as context
2417 proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
2418 proto_ctx->server = (void *)server;
2419 proto_ctx->sock = sock;
2420 proto_ctx->responder = TRUE;
2421 proto_ctx->pfs = idata->rekey->pfs;
2423 /* Perform rekey protocol. Will call the final callback after the
2424 protocol is over. */
2425 silc_protocol_alloc(SILC_PROTOCOL_SERVER_REKEY,
2426 &protocol, proto_ctx, silc_server_rekey_final);
2427 sock->protocol = protocol;
2429 if (proto_ctx->pfs == FALSE)
2430 /* Run the protocol */
2431 silc_protocol_execute(protocol, server->schedule, 0, 0);
2434 /* Received file transger packet. This packet is never for us. It is to
2435 the client in the packet's destination ID. Sending of this sort of packet
2436 equals sending private message, ie. it is sent point to point from
2437 one client to another. */
2439 void silc_server_ftp(SilcServer server,
2440 SilcSocketConnection sock,
2441 SilcPacketContext *packet)
2443 SilcSocketConnection dst_sock;
2444 SilcIDListData idata;
2446 SILC_LOG_DEBUG(("Start"));
2448 if (packet->src_id_type != SILC_ID_CLIENT ||
2449 packet->dst_id_type != SILC_ID_CLIENT)
2452 if (!packet->dst_id)
2455 /* Get the route to the client */
2456 dst_sock = silc_server_get_client_route(server, packet->dst_id,
2457 packet->dst_id_len, NULL, &idata);
2461 /* Relay the packet */
2462 silc_server_relay_packet(server, dst_sock, idata->send_key,
2463 idata->hmac_send, idata->psn_send++,