5 Author: Pekka Riikonen <priikone@silcnet.org>
7 Copyright (C) 1997 - 2008 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; version 2 of the License.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
20 #include "serverincludes.h"
21 #include "server_internal.h"
23 /************************* Types and definitions ****************************/
25 SILC_TASK_CALLBACK(silc_server_get_stats);
26 SILC_TASK_CALLBACK(silc_server_connect_router);
27 SILC_TASK_CALLBACK(silc_server_connect_to_router_retry);
28 SILC_TASK_CALLBACK(silc_server_do_rekey);
29 SILC_TASK_CALLBACK(silc_server_purge_expired_clients);
30 static void silc_server_accept_new_connection(SilcNetStatus status,
33 static void silc_server_packet_parse_type(SilcServer server,
34 SilcPacketStream sock,
36 static void silc_server_rekey(SilcServer server, SilcPacketStream sock,
40 /************************ Static utility functions **************************/
42 /* SKE public key verification callback */
45 silc_server_verify_key(SilcSKE ske,
46 SilcPublicKey public_key,
48 SilcSKEVerifyCbCompletion completion,
49 void *completion_context)
51 SilcPacketStream sock = context;
52 SilcUnknownEntry entry = silc_packet_get_context(sock);
54 SILC_LOG_DEBUG(("Verifying public key"));
56 if (silc_pkcs_get_type(public_key) != SILC_SKE_PK_TYPE_SILC) {
57 SILC_LOG_WARNING(("We don't support %s (%s) port %d public key type %d",
58 entry->hostname, entry->ip, entry->port,
59 silc_pkcs_get_type(public_key)));
60 completion(ske, SILC_SKE_STATUS_UNSUPPORTED_PUBLIC_KEY,
65 /* We accept all keys without explicit verification */
66 completion(ske, SILC_SKE_STATUS_OK, completion_context);
70 /************************ Packet engine callbacks ***************************/
72 /* Packet engine callback to receive a packet */
74 static SilcBool silc_server_packet_receive(SilcPacketEngine engine,
75 SilcPacketStream stream,
77 void *callback_context,
80 SilcServer server = callback_context;
81 SilcIDListData idata = stream_context;
86 /* Packets we do not handle */
87 switch (packet->type) {
88 case SILC_PACKET_HEARTBEAT:
89 case SILC_PACKET_SUCCESS:
90 case SILC_PACKET_FAILURE:
91 case SILC_PACKET_REJECT:
92 case SILC_PACKET_KEY_EXCHANGE:
93 case SILC_PACKET_KEY_EXCHANGE_1:
94 case SILC_PACKET_KEY_EXCHANGE_2:
95 case SILC_PACKET_REKEY_DONE:
96 case SILC_PACKET_CONNECTION_AUTH:
101 /* Only specific packets can come without source ID present. */
102 if ((!packet->src_id ||
103 !(idata->status & SILC_IDLIST_STATUS_REGISTERED)) &&
104 packet->type != SILC_PACKET_NEW_CLIENT &&
105 packet->type != SILC_PACKET_NEW_SERVER &&
106 packet->type != SILC_PACKET_RESUME_CLIENT &&
107 packet->type != SILC_PACKET_CONNECTION_AUTH_REQUEST &&
108 packet->type != SILC_PACKET_DISCONNECT)
111 /* NEW_CLIENT and NEW_SERVER are accepted only without source ID and
112 for unregistered connection. */
113 if (packet->src_id && (packet->type == SILC_PACKET_NEW_CLIENT ||
114 packet->type == SILC_PACKET_NEW_SERVER) &&
115 (idata->status & SILC_IDLIST_STATUS_REGISTERED))
118 /* Ignore packets from disabled connection */
119 if (idata->status & SILC_IDLIST_STATUS_DISABLED &&
120 packet->type != SILC_PACKET_HEARTBEAT &&
121 packet->type != SILC_PACKET_RESUME_ROUTER &&
122 packet->type != SILC_PACKET_REKEY)
125 /* Check that the the current client ID is same as in the client's packet. */
126 if (idata->conn_type == SILC_CONN_CLIENT) {
127 SilcClientEntry client = (SilcClientEntry)silc_packet_get_context(stream);
128 SilcClientID client_id;
130 if (client->id && packet->src_id &&
131 silc_id_str2id(packet->src_id, packet->src_id_len,
132 packet->src_id_type, &client_id, sizeof(client_id))) {
133 if (!SILC_ID_CLIENT_COMPARE(client->id, &client_id)) {
134 SILC_LOG_DEBUG(("Packet source is not same as sender, packet %s",
135 silc_get_packet_name(packet->type)));
141 if (server->server_type == SILC_ROUTER) {
142 /* Route the packet if it is not destined to us. Other ID types but
143 server are handled separately after processing them. */
144 if (packet->dst_id &&
145 !(packet->flags & SILC_PACKET_FLAG_BROADCAST) &&
146 packet->dst_id_type == SILC_ID_SERVER &&
147 idata->conn_type != SILC_CONN_CLIENT &&
148 memcmp(packet->dst_id, server->id_string, server->id_string_len)) {
149 SilcPacketStream conn;
150 SilcServerID server_id;
152 silc_id_str2id(packet->dst_id, packet->dst_id_len, packet->dst_id_type,
153 &server_id, sizeof(server_id));
155 conn = silc_server_route_get(server, &server_id, SILC_ID_SERVER);
157 SILC_LOG_WARNING(("Packet to unknown server ID %s, dropped (no route)",
158 silc_id_render(&server_id, SILC_ID_SERVER)));
162 silc_server_packet_route(server, conn, packet);
163 silc_packet_free(packet);
168 /* Broadcast packet if it is marked as broadcast packet and it is
169 originated from router and we are router. */
170 if (server->server_type == SILC_ROUTER &&
171 idata->conn_type == SILC_CONN_ROUTER &&
172 packet->flags & SILC_PACKET_FLAG_BROADCAST) {
173 /* Broadcast to our primary route */
174 silc_server_packet_broadcast(server, SILC_PRIMARY_ROUTE(server), packet);
176 /* If we have backup routers then we need to feed all broadcast
177 data to those servers. */
178 silc_server_backup_broadcast(server, stream, packet);
182 silc_server_packet_parse_type(server, stream, packet);
187 /* Packet engine callback to indicate end of stream */
189 static void silc_server_packet_eos(SilcPacketEngine engine,
190 SilcPacketStream stream,
191 void *callback_context,
192 void *stream_context)
194 SilcServer server = callback_context;
195 SilcIDListData idata = silc_packet_get_context(stream);
197 SILC_LOG_DEBUG(("End of stream received, sock %p", stream));
202 if (server->router_conn && server->router_conn->sock == stream &&
203 !server->router && server->standalone) {
204 silc_server_create_connections(server);
205 silc_server_free_sock_user_data(server, stream, NULL);
207 /* If backup disconnected then mark that resuming will not be allowed */
208 if (server->server_type == SILC_ROUTER && !server->backup_router &&
209 idata->conn_type == SILC_CONN_SERVER) {
210 SilcServerEntry server_entry = (SilcServerEntry)idata;
211 if (server_entry->server_type == SILC_BACKUP_ROUTER)
212 server->backup_closed = TRUE;
215 silc_server_free_sock_user_data(server, stream, NULL);
218 silc_server_close_connection(server, stream);
221 SILC_TASK_CALLBACK(silc_server_packet_error_timeout)
223 SilcServer server = app_context;
224 SilcPacketStream stream = context;
225 SilcIDListData idata = silc_packet_get_context(stream);
230 if (server->router_conn && server->router_conn->sock == stream &&
231 !server->router && server->standalone) {
232 silc_server_create_connections(server);
234 /* If backup disconnected then mark that resuming will not be allowed */
235 if (server->server_type == SILC_ROUTER && !server->backup_router &&
236 idata->conn_type == SILC_CONN_SERVER) {
237 SilcServerEntry server_entry = (SilcServerEntry)idata;
238 if (server_entry->server_type == SILC_BACKUP_ROUTER)
239 server->backup_closed = TRUE;
242 silc_server_free_sock_user_data(server, stream, NULL);
245 silc_server_close_connection(server, stream);
248 /* Packet engine callback to indicate error */
250 static void silc_server_packet_error(SilcPacketEngine engine,
251 SilcPacketStream stream,
252 SilcPacketError error,
253 void *callback_context,
254 void *stream_context)
256 SilcServer server = callback_context;
257 SilcIDListData idata = silc_packet_get_context(stream);
258 SilcStream sock = silc_packet_stream_get_stream(stream);
262 SILC_LOG_DEBUG(("Packet error, sock %p", stream));
267 if (!silc_socket_stream_get_info(sock, NULL, NULL, &ip, &port))
270 SILC_LOG_ERROR(("Connection %s:%d [%s]: %s", ip, port,
271 SILC_CONNTYPE_STRING(idata->conn_type),
272 silc_packet_error_string(error)));
274 if (!silc_packet_stream_is_valid(stream))
277 silc_schedule_task_add_timeout(server->schedule,
278 silc_server_packet_error_timeout,
282 /* Packet stream callbacks */
283 static SilcPacketCallbacks silc_server_stream_cbs =
285 silc_server_packet_receive,
286 silc_server_packet_eos,
287 silc_server_packet_error
290 /* Parses the packet type and calls what ever routines the packet type
291 requires. This is done for all incoming packets. */
293 static void silc_server_packet_parse_type(SilcServer server,
294 SilcPacketStream sock,
297 SilcPacketType type = packet->type;
298 SilcIDListData idata = silc_packet_get_context(sock);
300 SILC_LOG_DEBUG(("Received %s packet [flags %d]",
301 silc_get_packet_name(type), packet->flags));
303 /* Parse the packet type */
305 case SILC_PACKET_NOTIFY:
307 * Received notify packet. Server can receive notify packets from
308 * router. Server then relays the notify messages to clients if needed.
310 if (packet->flags & SILC_PACKET_FLAG_LIST)
311 silc_server_notify_list(server, sock, packet);
313 silc_server_notify(server, sock, packet);
317 * Private Message packets
319 case SILC_PACKET_PRIVATE_MESSAGE:
321 * Received private message packet. The packet is coming from either
324 if (packet->flags & SILC_PACKET_FLAG_LIST)
326 idata->last_receive = time(NULL);
327 silc_server_private_message(server, sock, packet);
333 case SILC_PACKET_CHANNEL_MESSAGE:
335 * Received channel message. Channel messages are special packets
336 * (although probably most common ones) thus they are handled
339 if (packet->flags & SILC_PACKET_FLAG_LIST)
341 idata->last_receive = time(NULL);
342 silc_server_channel_message(server, sock, packet);
348 case SILC_PACKET_COMMAND:
350 * Recived command. Processes the command request and allocates the
351 * command context and calls the command.
353 if (packet->flags & SILC_PACKET_FLAG_LIST)
355 server->stat.commands_received++;
356 silc_server_command_process(server, sock, packet);
359 case SILC_PACKET_COMMAND_REPLY:
361 * Received command reply packet. Received command reply to command. It
362 * may be reply to command sent by us or reply to command sent by client
363 * that we've routed further.
365 if (packet->flags & SILC_PACKET_FLAG_LIST)
367 server->stat.commands_received++;
368 silc_server_command_reply(server, sock, packet);
371 case SILC_PACKET_DISCONNECT:
374 char *message = NULL;
375 const char *hostname, *ip;
377 if (packet->flags & SILC_PACKET_FLAG_LIST)
379 if (silc_buffer_len(&packet->buffer) < 1)
382 status = (SilcStatus)packet->buffer.data[0];
383 if (silc_buffer_len(&packet->buffer) > 1 &&
384 silc_utf8_valid(packet->buffer.data + 1,
385 silc_buffer_len(&packet->buffer) - 1))
386 message = silc_memdup(packet->buffer.data + 1,
387 silc_buffer_len(&packet->buffer) - 1);
389 if (!silc_socket_stream_get_info(silc_packet_stream_get_stream(sock),
390 NULL, &hostname, &ip, NULL))
393 SILC_LOG_INFO(("Disconnected by %s (%s): %s (%d) %s", ip, hostname,
394 silc_get_status_message(status), status,
395 message ? message : ""));
399 /* Do not switch to backup in case of error */
400 server->backup_noswitch = (status == SILC_STATUS_OK ? FALSE : TRUE);
402 /* If backup disconnected then mark that resuming will not be allowed */
403 if (server->server_type == SILC_ROUTER && !server->backup_router &&
404 idata->conn_type == SILC_CONN_SERVER) {
405 SilcServerEntry server_entry = (SilcServerEntry)idata;
406 if (server_entry->server_type == SILC_BACKUP_ROUTER)
407 server->backup_closed = TRUE;
410 /* Handle the disconnection from our end too */
411 if (SILC_IS_LOCAL(idata))
412 silc_server_free_sock_user_data(server, sock, NULL);
413 silc_server_close_connection(server, sock);
414 server->backup_noswitch = FALSE;
418 case SILC_PACKET_CHANNEL_KEY:
420 * Received key for channel. As channels are created by the router
421 * the keys are as well. We will distribute the key to all of our
422 * locally connected clients on the particular channel. Router
423 * never receives this channel and thus is ignored.
425 if (packet->flags & SILC_PACKET_FLAG_LIST)
427 silc_server_channel_key(server, sock, packet);
430 case SILC_PACKET_PRIVATE_MESSAGE_KEY:
432 * Private message key packet.
434 if (packet->flags & SILC_PACKET_FLAG_LIST)
436 silc_server_private_message_key(server, sock, packet);
439 case SILC_PACKET_CONNECTION_AUTH_REQUEST:
441 * Connection authentication request packet. When we receive this packet
442 * we will send to the other end information about our mandatory
443 * authentication method for the connection. This packet maybe received
446 if (packet->flags & SILC_PACKET_FLAG_LIST)
448 silc_server_connection_auth_request(server, sock, packet);
451 case SILC_PACKET_NEW_ID:
453 * Received New ID packet. This includes some new ID that has been
454 * created. It may be for client, server or channel. This is the way
455 * to distribute information about new registered entities in the
458 if (packet->flags & SILC_PACKET_FLAG_LIST)
459 silc_server_new_id_list(server, sock, packet);
461 silc_server_new_id(server, sock, packet);
464 case SILC_PACKET_NEW_CLIENT:
466 * Received new client packet. This includes client information that
467 * we will use to create initial client ID. After creating new
468 * ID we will send it to the client.
470 if (packet->flags & SILC_PACKET_FLAG_LIST)
472 silc_server_new_client(server, sock, packet);
475 case SILC_PACKET_NEW_SERVER:
477 * Received new server packet. This includes Server ID and some other
478 * information that we may save. This is received after server has
481 if (packet->flags & SILC_PACKET_FLAG_LIST)
483 silc_server_new_server(server, sock, packet);
486 case SILC_PACKET_NEW_CHANNEL:
488 * Received new channel packet. Information about new channel in the
489 * network are distributed using this packet.
491 if (packet->flags & SILC_PACKET_FLAG_LIST)
492 silc_server_new_channel_list(server, sock, packet);
494 silc_server_new_channel(server, sock, packet);
497 case SILC_PACKET_HEARTBEAT:
499 * Received heartbeat.
501 if (packet->flags & SILC_PACKET_FLAG_LIST)
505 case SILC_PACKET_KEY_AGREEMENT:
507 * Received heartbeat.
509 if (packet->flags & SILC_PACKET_FLAG_LIST)
511 silc_server_key_agreement(server, sock, packet);
514 case SILC_PACKET_REKEY:
516 * Received re-key packet. The sender wants to regenerate the session
519 if (packet->flags & SILC_PACKET_FLAG_LIST)
521 silc_server_rekey(server, sock, packet);
524 case SILC_PACKET_FTP:
526 if (packet->flags & SILC_PACKET_FLAG_LIST)
528 silc_server_ftp(server, sock, packet);
531 case SILC_PACKET_RESUME_CLIENT:
533 if (packet->flags & SILC_PACKET_FLAG_LIST)
535 silc_server_resume_client(server, sock, packet);
538 case SILC_PACKET_RESUME_ROUTER:
539 /* Resume router packet received. This packet is received for backup
540 router resuming protocol. */
541 if (packet->flags & SILC_PACKET_FLAG_LIST)
543 silc_server_backup_resume_router(server, sock, packet);
547 SILC_LOG_ERROR(("Incorrect packet type %d, packet dropped", type));
552 /****************************** Server API **********************************/
554 /* Allocates a new SILC server object. This has to be done before the server
555 can be used. After allocation one must call silc_server_init to initialize
556 the server. The new allocated server object is returned to the new_server
559 SilcBool silc_server_alloc(SilcServer *new_server)
563 SILC_LOG_DEBUG(("Allocating new server object"));
565 server = silc_calloc(1, sizeof(*server));
568 server->server_type = SILC_SERVER;
569 server->standalone = TRUE;
570 server->local_list = silc_calloc(1, sizeof(*server->local_list));
571 if (!server->local_list)
573 server->global_list = silc_calloc(1, sizeof(*server->global_list));
574 if (!server->global_list)
576 server->pending_commands = silc_dlist_init();
577 if (!server->pending_commands)
579 server->listeners = silc_dlist_init();
580 if (!server->listeners)
582 server->repository = silc_skr_alloc();
583 if (!server->repository)
585 server->conns = silc_dlist_init();
588 server->expired_clients = silc_dlist_init();
589 if (!server->expired_clients)
592 *new_server = server;
597 /* Free's the SILC server object. This is called at the very end before
600 void silc_server_free(SilcServer server)
603 SilcIDCacheEntry cache;
604 SilcIDListData idata;
606 SILC_LOG_DEBUG(("Free server %p", server));
611 silc_server_backup_free(server);
612 silc_server_config_unref(&server->config_ref);
614 silc_rng_free(server->rng);
615 if (server->public_key)
616 silc_pkcs_public_key_free(server->public_key);
617 if (server->private_key)
618 silc_pkcs_private_key_free(server->private_key);
619 if (server->pending_commands)
620 silc_dlist_uninit(server->pending_commands);
621 if (server->id_entry) {
622 if (server->id_entry->data.sconn)
623 silc_schedule_task_del_by_context(server->schedule,
624 server->id_entry->data.sconn->sock);
625 silc_idlist_del_server(server->local_list, server->id_entry);
628 /* Delete all channels */
629 if (silc_idcache_get_all(server->local_list->channels, &list)) {
630 silc_list_start(list);
631 while ((cache = silc_list_get(list)))
632 silc_idlist_del_channel(server->local_list, cache->context);
634 if (silc_idcache_get_all(server->global_list->channels, &list)) {
635 silc_list_start(list);
636 while ((cache = silc_list_get(list)))
637 silc_idlist_del_channel(server->global_list, cache->context);
640 /* Delete all clients */
641 if (silc_idcache_get_all(server->local_list->clients, &list)) {
642 silc_list_start(list);
643 while ((cache = silc_list_get(list))) {
644 silc_schedule_task_del_by_context(server->schedule, cache->context);
645 silc_idlist_del_client(server->local_list, cache->context);
648 if (silc_idcache_get_all(server->global_list->clients, &list)) {
649 silc_list_start(list);
650 while ((cache = silc_list_get(list))) {
651 silc_schedule_task_del_by_context(server->schedule, cache->context);
652 silc_idlist_del_client(server->global_list, cache->context);
656 /* Delete all servers */
657 if (silc_idcache_get_all(server->local_list->servers, &list)) {
658 silc_list_start(list);
659 while ((cache = silc_list_get(list))) {
660 idata = (SilcIDListData)cache->context;
662 silc_schedule_task_del_by_context(server->schedule,
664 silc_idlist_del_server(server->local_list, cache->context);
667 if (silc_idcache_get_all(server->global_list->servers, &list)) {
668 while ((cache = silc_list_get(list))) {
669 idata = (SilcIDListData)cache->context;
671 silc_schedule_task_del_by_context(server->schedule,
673 silc_idlist_del_server(server->global_list, cache->context);
677 silc_schedule_task_del_by_context(server->schedule, server);
678 silc_schedule_uninit(server->schedule);
679 server->schedule = NULL;
681 silc_idcache_free(server->local_list->clients);
682 silc_idcache_free(server->local_list->servers);
683 silc_idcache_free(server->local_list->channels);
684 silc_idcache_free(server->global_list->clients);
685 silc_idcache_free(server->global_list->servers);
686 silc_idcache_free(server->global_list->channels);
687 silc_hash_table_free(server->watcher_list);
688 silc_hash_table_free(server->watcher_list_pk);
689 silc_hash_free(server->md5hash);
690 silc_hash_free(server->sha1hash);
692 silc_dlist_uninit(server->listeners);
693 silc_dlist_uninit(server->conns);
694 silc_dlist_uninit(server->expired_clients);
695 silc_skr_free(server->repository);
696 silc_packet_engine_stop(server->packet_engine);
698 silc_free(server->local_list);
699 silc_free(server->global_list);
700 silc_free(server->server_name);
703 silc_hmac_unregister_all();
704 silc_hash_unregister_all();
705 silc_cipher_unregister_all();
706 silc_pkcs_unregister_all();
709 /* Creates a new server listener. */
711 static SilcNetListener
712 silc_server_listen(SilcServer server, const char *server_ip, SilcUInt16 port)
714 SilcNetListener listener;
717 silc_net_tcp_create_listener(&server_ip, 1, port, TRUE,
718 server->config->require_reverse_lookup,
720 silc_server_accept_new_connection, server);
722 SILC_SERVER_LOG_ERROR(("Could not create server listener: %s on %hu",
730 /* Adds a secondary listener. */
732 SilcBool silc_server_init_secondary(SilcServer server)
734 SilcServerConfigServerInfoInterface *interface;
735 SilcNetListener listener;
737 for (interface = server->config->server_info->secondary; interface;
738 interface = interface->next) {
739 listener = silc_server_listen(server, interface->server_ip,
743 silc_dlist_add(server->listeners, listener);
749 /* Initializes the entire SILC server. This is called always before running
750 the server. This is called only once at the initialization of the program.
751 This binds the server to its listenning port. After this function returns
752 one should call silc_server_run to start the server. This returns TRUE
753 when everything is ok to run the server. Configuration file must be
754 read and parsed before calling this. */
756 SilcBool silc_server_init(SilcServer server)
759 SilcServerEntry id_entry;
760 SilcNetListener listener;
764 SILC_LOG_DEBUG(("Initializing server"));
766 server->starttime = time(NULL);
768 /* Take config object for us */
769 silc_server_config_ref(&server->config_ref, server->config,
773 /* Set debugging on if configured */
774 if (server->config->debug_string) {
775 silc_log_debug(TRUE);
776 silc_log_set_debug_string(server->config->debug_string);
778 #endif /* SILC_DEBUG */
780 /* Steal public and private key from the config object */
781 server->public_key = server->config->server_info->public_key;
782 server->private_key = server->config->server_info->private_key;
783 server->config->server_info->public_key = NULL;
784 server->config->server_info->private_key = NULL;
786 /* Register all configured ciphers, PKCS and hash functions. */
787 if (!silc_server_config_register_ciphers(server))
788 silc_cipher_register_default();
789 if (!silc_server_config_register_pkcs(server))
790 silc_pkcs_register_default();
791 if (!silc_server_config_register_hashfuncs(server))
792 silc_hash_register_default();
793 if (!silc_server_config_register_hmacs(server))
794 silc_hmac_register_default();
796 /* Initialize random number generator for the server. */
797 server->rng = silc_rng_alloc();
798 silc_rng_init(server->rng);
799 silc_rng_global_init(server->rng);
801 /* Initialize hash functions for server to use */
802 silc_hash_alloc("md5", &server->md5hash);
803 silc_hash_alloc("sha1", &server->sha1hash);
805 /* Initialize the scheduler */
806 server->schedule = silc_schedule_init(server->config->param.connections_max,
808 if (!server->schedule)
811 /* First, register log files configuration for error output */
812 silc_server_config_setlogfiles(server);
814 /* Initialize ID caches */
815 server->local_list->clients =
816 silc_idcache_alloc(0, SILC_ID_CLIENT, silc_idlist_client_destructor,
818 server->local_list->servers =
819 silc_idcache_alloc(0, SILC_ID_SERVER, silc_idlist_server_destructor,
821 server->local_list->channels =
822 silc_idcache_alloc(0, SILC_ID_CHANNEL, silc_idlist_channel_destructor,
825 /* These are allocated for normal server as well as these hold some
826 global information that the server has fetched from its router. For
827 router these are used as they are supposed to be used on router. */
828 server->global_list->clients =
829 silc_idcache_alloc(0, SILC_ID_CLIENT, silc_idlist_client_destructor,
831 server->global_list->servers =
832 silc_idcache_alloc(0, SILC_ID_SERVER, silc_idlist_server_destructor,
834 server->global_list->channels =
835 silc_idcache_alloc(0, SILC_ID_CHANNEL, silc_idlist_channel_destructor,
838 /* Init watcher lists */
839 server->watcher_list =
840 silc_hash_table_alloc(1, silc_hash_client_id_hash, NULL,
841 silc_hash_data_compare, (void *)CLIENTID_HASH_LEN,
843 if (!server->watcher_list)
845 server->watcher_list_pk =
846 silc_hash_table_alloc(1, silc_hash_public_key, NULL,
847 silc_hash_public_key_compare, NULL,
849 if (!server->watcher_list_pk)
852 /* Create TCP listener */
853 listener = silc_server_listen(
855 server->config->server_info->primary == NULL ? NULL :
856 server->config->server_info->primary->server_ip,
857 server->config->server_info->primary == NULL ? 0 :
858 server->config->server_info->primary->port);
861 silc_dlist_add(server->listeners, listener);
863 /* Create a Server ID for the server. */
864 port = silc_net_listener_get_port(listener, NULL);
865 ip = silc_net_listener_get_ip(listener, NULL);
866 silc_id_create_server_id(server->config->server_info->primary->public_ip ?
867 server->config->server_info->primary->public_ip :
868 ip[0], port[0], server->rng, &id);
877 server->server_name = server->config->server_info->server_name;
878 server->config->server_info->server_name = NULL;
879 silc_id_id2str(server->id, SILC_ID_SERVER, server->id_string,
880 sizeof(server->id_string), &server->id_string_len);
882 /* Add ourselves to the server list. We don't have a router yet
883 beacuse we haven't established a route yet. It will be done later.
884 For now, NULL is sent as router. This allocates new entry to
887 silc_idlist_add_server(server->local_list, strdup(server->server_name),
889 silc_id_dup(server->id, SILC_ID_SERVER),
892 SILC_LOG_ERROR(("Could not add local server to cache"));
895 id_entry->data.status |= SILC_IDLIST_STATUS_REGISTERED;
896 id_entry->data.conn_type = (server->server_type == SILC_SERVER ?
897 SILC_CONN_SERVER : SILC_CONN_ROUTER);
898 server->id_entry = id_entry;
900 /* Create secondary TCP listeners */
901 if (silc_server_init_secondary(server) == FALSE)
904 server->listenning = TRUE;
906 /* Create connections to configured routers. */
907 silc_server_create_connections(server);
909 /* If server connections has been configured then we must be router as
910 normal server cannot have server connections, only router connections. */
911 if (server->config->servers) {
912 SilcServerConfigServer *ptr = server->config->servers;
914 server->server_type = SILC_ROUTER;
916 if (ptr->backup_router) {
917 server->server_type = SILC_BACKUP_ROUTER;
918 server->backup_router = TRUE;
919 server->id_entry->server_type = SILC_BACKUP_ROUTER;
926 if (server->server_type != SILC_ROUTER) {
927 server->stat.servers = 1;
928 server->stat.cell_servers = 1;
930 server->stat.routers = 1;
933 /* If we are normal server we'll retrieve network statisticial information
934 once in a while from the router. */
935 if (server->server_type != SILC_ROUTER)
936 silc_schedule_task_add_timeout(server->schedule, silc_server_get_stats,
939 /* Start packet engine */
940 server->packet_engine =
941 silc_packet_engine_start(server->rng, server->server_type == SILC_ROUTER,
942 &silc_server_stream_cbs, server);
943 if (!server->packet_engine)
946 /* Register client entry expiration timeout */
947 silc_schedule_task_add_timeout(server->schedule,
948 silc_server_purge_expired_clients, server,
951 /* Initialize HTTP server */
952 silc_server_http_init(server);
954 SILC_LOG_DEBUG(("Server initialized"));
956 /* We are done here, return succesfully */
960 silc_server_config_unref(&server->config_ref);
964 /* Task callback to close a socket connection after rehash */
966 SILC_TASK_CALLBACK(silc_server_rehash_close_connection)
968 SilcServer server = app_context;
969 SilcPacketStream sock = context;
970 SilcIDListData idata = silc_packet_get_context(sock);
971 const char *hostname;
974 silc_socket_stream_get_info(silc_packet_stream_get_stream(sock),
975 NULL, &hostname, NULL, &port);
977 SILC_LOG_INFO(("Connection %s:%d [%s] is unconfigured",
978 hostname, port, SILC_CONNTYPE_STRING(idata->conn_type)));
979 silc_schedule_task_del_by_context(server->schedule, sock);
980 silc_server_disconnect_remote(server, sock,
981 SILC_STATUS_ERR_BANNED_FROM_SERVER,
982 "This connection is removed from "
984 silc_server_free_sock_user_data(server, sock, NULL);
987 /* This function basically reads the config file again and switches the config
988 object pointed by the server object. After that, we have to fix various
989 things such as the server_name and the listening ports.
990 Keep in mind that we no longer have the root privileges at this point. */
992 SilcBool silc_server_rehash(SilcServer server)
994 SilcServerConfig newconfig;
996 SILC_LOG_INFO(("Rehashing server"));
998 /* Reset the logging system */
999 silc_log_quick(TRUE);
1000 silc_log_flush_all();
1002 /* Start the main rehash phase (read again the config file) */
1003 newconfig = silc_server_config_alloc(server->config_file, server);
1005 SILC_LOG_ERROR(("Rehash FAILED."));
1009 /* Fix the server_name field */
1010 if (strcmp(server->server_name, newconfig->server_info->server_name)) {
1011 silc_free(server->server_name);
1013 /* Check server name */
1014 server->server_name =
1015 silc_identifier_check(newconfig->server_info->server_name,
1016 strlen(newconfig->server_info->server_name),
1017 SILC_STRING_LOCALE, 256, NULL);
1018 if (!server->server_name) {
1019 SILC_LOG_ERROR(("Malformed server name string '%s'",
1020 server->config->server_info->server_name));
1024 /* Update the idcache list with a fresh pointer */
1025 silc_free(server->id_entry->server_name);
1026 server->id_entry->server_name = strdup(server->server_name);
1027 silc_idcache_update_by_context(server->local_list->servers,
1028 server->id_entry, NULL,
1029 strdup(server->id_entry->server_name),
1034 silc_server_config_setlogfiles(server);
1036 /* Change new key pair if necessary */
1037 if (newconfig->server_info->public_key &&
1038 !silc_pkcs_public_key_compare(server->public_key,
1039 newconfig->server_info->public_key)) {
1040 silc_pkcs_public_key_free(server->public_key);
1041 silc_pkcs_private_key_free(server->private_key);
1042 server->public_key = newconfig->server_info->public_key;
1043 server->private_key = newconfig->server_info->private_key;
1044 newconfig->server_info->public_key = NULL;
1045 newconfig->server_info->private_key = NULL;
1048 /* Check for unconfigured server and router connections and close
1049 connections that were unconfigured. */
1051 if (server->config->routers) {
1052 SilcServerConfigRouter *ptr;
1053 SilcServerConfigRouter *newptr;
1056 for (ptr = server->config->routers; ptr; ptr = ptr->next) {
1059 /* Check whether new config has this one too */
1060 for (newptr = newconfig->routers; newptr; newptr = newptr->next) {
1061 if (silc_string_compare(newptr->host, ptr->host) &&
1062 newptr->port == ptr->port &&
1063 newptr->initiator == ptr->initiator) {
1069 if (!found && ptr->host) {
1070 /* Remove this connection */
1071 SilcPacketStream sock;
1072 sock = silc_server_find_socket_by_host(server, SILC_CONN_ROUTER,
1073 ptr->host, ptr->port);
1075 silc_schedule_task_add_timeout(server->schedule,
1076 silc_server_rehash_close_connection,
1082 if (server->config->servers) {
1083 SilcServerConfigServer *ptr;
1084 SilcServerConfigServer *newptr;
1087 for (ptr = server->config->servers; ptr; ptr = ptr->next) {
1090 /* Check whether new config has this one too */
1091 for (newptr = newconfig->servers; newptr; newptr = newptr->next) {
1092 if (silc_string_compare(newptr->host, ptr->host)) {
1098 if (!found && ptr->host) {
1099 /* Remove this connection */
1100 SilcPacketStream sock;
1101 sock = silc_server_find_socket_by_host(server, SILC_CONN_SERVER,
1104 silc_schedule_task_add_timeout(server->schedule,
1105 silc_server_rehash_close_connection,
1111 if (server->config->clients) {
1112 SilcServerConfigClient *ptr;
1113 SilcServerConfigClient *newptr;
1116 for (ptr = server->config->clients; ptr; ptr = ptr->next) {
1119 /* Check whether new config has this one too */
1120 for (newptr = newconfig->clients; newptr; newptr = newptr->next) {
1121 if (silc_string_compare(newptr->host, ptr->host)) {
1127 if (!found && ptr->host) {
1128 /* Remove this connection */
1129 SilcPacketStream sock;
1130 sock = silc_server_find_socket_by_host(server, SILC_CONN_CLIENT,
1133 silc_schedule_task_add_timeout(server->schedule,
1134 silc_server_rehash_close_connection,
1140 /* Create connections after rehash */
1141 silc_server_create_connections(server);
1143 /* Check whether our router status has changed */
1144 if (newconfig->servers) {
1145 SilcServerConfigServer *ptr = newconfig->servers;
1147 server->server_type = SILC_ROUTER;
1149 if (ptr->backup_router) {
1150 server->server_type = SILC_BACKUP_ROUTER;
1151 server->backup_router = TRUE;
1152 server->id_entry->server_type = SILC_BACKUP_ROUTER;
1159 /* Our old config is gone now. We'll unreference our reference made in
1160 silc_server_init and then destroy it since we are destroying it
1161 underneath the application (layer which called silc_server_init). */
1162 silc_server_config_unref(&server->config_ref);
1163 silc_server_config_destroy(server->config);
1165 /* Take new config context */
1166 server->config = newconfig;
1167 silc_server_config_ref(&server->config_ref, server->config, server->config);
1170 /* Set debugging on if configured */
1171 if (server->config->debug_string) {
1172 silc_log_debug(TRUE);
1173 silc_log_set_debug_string(server->config->debug_string);
1175 #endif /* SILC_DEBUG */
1177 SILC_LOG_DEBUG(("Server rehashed"));
1182 /* The heart of the server. This runs the scheduler thus runs the server.
1183 When this returns the server has been stopped and the program will
1186 void silc_server_run(SilcServer server)
1188 SILC_LOG_INFO(("SILC Server started"));
1190 /* Start the scheduler, the heart of the SILC server. When this returns
1191 the program will be terminated. */
1192 silc_schedule(server->schedule);
1195 /* Stops the SILC server. This function is used to shutdown the server.
1196 This is usually called after the scheduler has returned. After stopping
1197 the server one should call silc_server_free. */
1199 void silc_server_stop(SilcServer server)
1202 SilcPacketStream ps;
1203 SilcNetListener listener;
1205 SILC_LOG_INFO(("SILC Server shutting down"));
1207 server->server_shutdown = TRUE;
1209 /* Close all connections */
1210 if (server->packet_engine) {
1211 list = silc_packet_engine_get_streams(server->packet_engine);
1213 silc_dlist_start(list);
1214 while ((ps = silc_dlist_get(list))) {
1215 SilcIDListData idata = silc_packet_get_context(ps);
1217 if (!silc_packet_stream_is_valid(ps))
1221 idata->status &= ~SILC_IDLIST_STATUS_DISABLED;
1223 silc_server_disconnect_remote(server, ps, SILC_STATUS_OK,
1224 "Server is shutting down");
1225 silc_server_free_sock_user_data(server, ps,
1226 "Server is shutting down");
1228 silc_packet_engine_free_streams_list(list);
1231 /* We are not connected to network anymore */
1232 server->standalone = TRUE;
1234 silc_dlist_start(server->listeners);
1235 while ((listener = silc_dlist_get(server->listeners)))
1236 silc_net_close_listener(listener);
1238 silc_server_http_uninit(server);
1240 /* Cancel any possible retry timeouts */
1241 silc_schedule_task_del_by_callback(server->schedule,
1242 silc_server_connect_router);
1243 silc_schedule_task_del_by_callback(server->schedule,
1244 silc_server_connect_to_router_retry);
1245 silc_schedule_task_del_by_callback(server->schedule,
1246 silc_server_connect_to_router);
1248 silc_schedule_stop(server->schedule);
1250 SILC_LOG_DEBUG(("Server stopped"));
1253 /* Purge expired client entries from the server */
1255 SILC_TASK_CALLBACK(silc_server_purge_expired_clients)
1257 SilcServer server = context;
1258 SilcClientEntry client;
1260 SilcUInt64 curtime = silc_time();
1262 SILC_LOG_DEBUG(("Expire timeout"));
1264 silc_dlist_start(server->expired_clients);
1265 while ((client = silc_dlist_get(server->expired_clients))) {
1266 if (client->data.status & SILC_IDLIST_STATUS_REGISTERED)
1269 /* For unregistered clients the created timestamp is actually
1270 unregistered timestamp. Make sure client remains in history
1271 at least 500 seconds. */
1272 if (curtime - client->data.created < 500)
1275 id_list = (client->data.status & SILC_IDLIST_STATUS_LOCAL ?
1276 server->local_list : server->global_list);
1278 silc_idlist_del_data(client);
1279 silc_idlist_del_client(id_list, client);
1280 silc_dlist_del(server->expired_clients, client);
1283 silc_schedule_task_add_timeout(server->schedule,
1284 silc_server_purge_expired_clients, server,
1289 /******************************* Connecting *********************************/
1291 /* Free connection context */
1293 void silc_server_connection_free(SilcServerConnection sconn)
1295 SILC_LOG_DEBUG(("Free connection %p", sconn));
1296 silc_dlist_del(sconn->server->conns, sconn);
1297 silc_server_config_unref(&sconn->conn);
1298 silc_free(sconn->remote_host);
1299 silc_free(sconn->backup_replace_ip);
1303 /* Creates connection to a remote router. */
1305 void silc_server_create_connection(SilcServer server,
1308 const char *remote_host, SilcUInt32 port,
1309 SilcServerConnectCallback callback,
1312 SilcServerConnection sconn;
1314 /* Allocate connection object for hold connection specific stuff. */
1315 sconn = silc_calloc(1, sizeof(*sconn));
1318 sconn->remote_host = strdup(remote_host);
1319 sconn->remote_port = port;
1320 sconn->no_reconnect = reconnect == FALSE;
1321 sconn->callback = callback;
1322 sconn->callback_context = context;
1323 sconn->no_conf = dynamic;
1324 sconn->server = server;
1326 SILC_LOG_DEBUG(("Created connection %p", sconn));
1328 silc_schedule_task_add_timeout(server->schedule, silc_server_connect_router,
1332 /* Connection authentication completion callback */
1335 silc_server_ke_auth_compl(SilcConnAuth connauth, SilcBool success,
1338 SilcServerConnection sconn = context;
1339 SilcUnknownEntry entry = silc_packet_get_context(sconn->sock);
1340 SilcServer server = entry->server;
1341 SilcServerConfigServer *conn;
1342 SilcServerConfigConnParams *param;
1343 SilcIDListData idata;
1344 SilcServerEntry id_entry = NULL;
1345 unsigned char id[32];
1350 SILC_LOG_DEBUG(("Connection %p authentication completed, entry %p",
1355 if (success == FALSE) {
1356 /* Authentication failed */
1357 /* XXX retry connecting */
1359 silc_server_disconnect_remote(server, sconn->sock,
1360 SILC_STATUS_ERR_AUTH_FAILED, NULL);
1361 if (sconn->callback)
1362 (*sconn->callback)(server, NULL, sconn->callback_context);
1363 silc_server_free_sock_user_data(server, sconn->sock, NULL);
1364 silc_server_connection_free(sconn);
1368 /* XXX For now remote is router always */
1369 entry->data.conn_type = SILC_CONN_ROUTER;
1371 SILC_LOG_INFO(("Connected to %s %s",
1372 SILC_CONNTYPE_STRING(entry->data.conn_type),
1373 sconn->remote_host));
1375 /* Create the actual entry for remote entity */
1376 switch (entry->data.conn_type) {
1377 case SILC_CONN_SERVER:
1378 SILC_LOG_DEBUG(("Remote is SILC server"));
1380 /* Add new server. The server must register itself to us before it
1381 becomes registered to SILC network. */
1382 id_entry = silc_idlist_add_server(server->local_list,
1383 strdup(sconn->remote_host),
1384 SILC_SERVER, NULL, NULL, sconn->sock);
1386 silc_server_disconnect_remote(server, sconn->sock,
1387 SILC_STATUS_ERR_RESOURCE_LIMIT, NULL);
1388 if (sconn->callback)
1389 (*sconn->callback)(server, NULL, sconn->callback_context);
1390 silc_server_free_sock_user_data(server, sconn->sock, NULL);
1391 silc_server_connection_free(sconn);
1397 server->stat.my_servers++;
1398 if (server->server_type == SILC_ROUTER)
1399 server->stat.servers++;
1400 SILC_LOG_DEBUG(("my_servers %d", server->stat.my_servers));
1402 silc_idlist_add_data(id_entry, (SilcIDListData)entry);
1405 case SILC_CONN_ROUTER:
1406 SILC_LOG_DEBUG(("Remote is SILC router"));
1408 /* Register to network */
1409 silc_id_id2str(server->id, SILC_ID_SERVER, id, sizeof(id), &id_len);
1410 if (!silc_packet_send_va(sconn->sock, SILC_PACKET_NEW_SERVER, 0,
1411 SILC_STR_UI_SHORT(id_len),
1412 SILC_STR_DATA(id, id_len),
1413 SILC_STR_UI_SHORT(strlen(server->server_name)),
1414 SILC_STR_DATA(server->server_name,
1415 strlen(server->server_name)),
1417 silc_server_disconnect_remote(server, sconn->sock,
1418 SILC_STATUS_ERR_RESOURCE_LIMIT, NULL);
1419 if (sconn->callback)
1420 (*sconn->callback)(server, NULL, sconn->callback_context);
1421 silc_server_free_sock_user_data(server, sconn->sock, NULL);
1422 silc_server_connection_free(sconn);
1428 silc_packet_get_ids(sconn->sock, NULL, NULL, NULL, &remote_id);
1430 /* Check that we do not have this ID already */
1431 id_entry = silc_idlist_find_server_by_id(server->local_list,
1432 &remote_id.u.server_id,
1435 silc_idcache_del_by_context(server->local_list->servers, id_entry, NULL);
1437 id_entry = silc_idlist_find_server_by_id(server->global_list,
1438 &remote_id.u.server_id,
1441 silc_idcache_del_by_context(server->global_list->servers, id_entry,
1445 SILC_LOG_DEBUG(("New server id(%s)",
1446 silc_id_render(&remote_id.u.server_id, SILC_ID_SERVER)));
1448 /* Add the connected router to global server list. Router is sent
1449 as NULL since it's local to us. */
1450 id_entry = silc_idlist_add_server(server->global_list,
1451 strdup(sconn->remote_host),
1453 silc_id_dup(&remote_id.u.server_id,
1457 silc_server_disconnect_remote(server, sconn->sock,
1458 SILC_STATUS_ERR_RESOURCE_LIMIT, NULL);
1459 if (sconn->callback)
1460 (*sconn->callback)(server, NULL, sconn->callback_context);
1461 silc_server_free_sock_user_data(server, sconn->sock, NULL);
1462 silc_server_connection_free(sconn);
1468 silc_idlist_add_data(id_entry, (SilcIDListData)entry);
1469 idata = (SilcIDListData)id_entry;
1470 idata->status |= (SILC_IDLIST_STATUS_REGISTERED |
1471 SILC_IDLIST_STATUS_LOCAL);
1472 idata->sconn = sconn;
1475 server->stat.my_routers++;
1476 if (server->server_type == SILC_ROUTER)
1477 server->stat.routers++;
1478 SILC_LOG_DEBUG(("my_routers %d", server->stat.my_routers));
1480 if (!sconn->backup) {
1481 /* Mark this router our primary router if we're still standalone */
1482 if (server->standalone) {
1483 SILC_LOG_DEBUG(("This connection is our primary router"));
1484 server->id_entry->router = id_entry;
1485 server->router = id_entry;
1486 server->router->server_type = SILC_ROUTER;
1487 server->standalone = FALSE;
1488 server->backup_primary = FALSE;
1490 /* Announce data if we are not backup router (unless not as primary
1491 currently). Backup router announces later at the end of
1492 resuming protocol. */
1493 if (server->backup_router && server->server_type == SILC_ROUTER) {
1494 SILC_LOG_DEBUG(("Announce data after resume protocol"));
1496 /* If we are router then announce our possible servers. Backup
1497 router announces also global servers. */
1498 if (server->server_type == SILC_ROUTER)
1499 silc_server_announce_servers(server,
1500 server->backup_router ? TRUE : FALSE,
1501 0, SILC_PRIMARY_ROUTE(server));
1503 /* Announce our clients and channels to the router */
1504 silc_server_announce_clients(server, 0, SILC_PRIMARY_ROUTE(server));
1505 silc_server_announce_channels(server, 0, SILC_PRIMARY_ROUTE(server));
1508 /* If we are backup router then this primary router is whom we are
1510 if (server->server_type == SILC_BACKUP_ROUTER) {
1511 silc_socket_stream_get_info(silc_packet_stream_get_stream(sconn->
1513 NULL, NULL, &ip, NULL);
1514 silc_server_backup_add(server, server->id_entry, ip,
1515 sconn->remote_port, TRUE);
1519 /* We already have primary router. Disconnect this connection */
1520 SILC_LOG_DEBUG(("We already have primary router, disconnect"));
1521 silc_idlist_del_server(server->global_list, id_entry);
1522 silc_server_disconnect_remote(server, sconn->sock,
1523 SILC_STATUS_ERR_RESOURCE_LIMIT, NULL);
1524 if (sconn->callback)
1525 (*sconn->callback)(server, NULL, sconn->callback_context);
1526 silc_server_connection_free(sconn);
1532 /* Add this server to be our backup router */
1533 id_entry->server_type = SILC_BACKUP_ROUTER;
1534 silc_server_backup_add(server, id_entry, sconn->backup_replace_ip,
1535 sconn->backup_replace_port, FALSE);
1541 silc_server_disconnect_remote(server, sconn->sock,
1542 SILC_STATUS_ERR_AUTH_FAILED, NULL);
1543 if (sconn->callback)
1544 (*sconn->callback)(server, NULL, sconn->callback_context);
1545 silc_server_free_sock_user_data(server, sconn->sock, NULL);
1546 silc_server_connection_free(sconn);
1551 SILC_LOG_DEBUG(("Connection established, sock %p", sconn->sock));
1553 conn = sconn->conn.ref_ptr;
1554 param = &server->config->param;
1555 if (conn && conn->param)
1556 param = conn->param;
1558 /* Register rekey timeout */
1559 sconn->rekey_timeout = param->key_exchange_rekey;
1560 silc_schedule_task_add_timeout(server->schedule, silc_server_do_rekey,
1561 sconn->sock, sconn->rekey_timeout, 0);
1563 /* Set the entry as packet stream context */
1564 silc_packet_set_context(sconn->sock, id_entry);
1566 /* Call the completion callback to indicate that we've connected to
1568 if (sconn && sconn->callback)
1569 (*sconn->callback)(server, id_entry, sconn->callback_context);
1571 if (sconn == server->router_conn)
1572 server->router_conn = NULL;
1577 /* SKE completion callback */
1579 static void silc_server_ke_completed(SilcSKE ske, SilcSKEStatus status,
1580 SilcSKESecurityProperties prop,
1581 SilcSKEKeyMaterial keymat,
1582 SilcSKERekeyMaterial rekey,
1585 SilcPacketStream sock = context;
1586 SilcUnknownEntry entry = silc_packet_get_context(sock);
1587 SilcServerConnection sconn = silc_ske_get_context(ske);
1588 SilcServer server = entry->server;
1589 SilcServerConfigRouter *conn = sconn->conn.ref_ptr;
1590 SilcAuthMethod auth_meth = SILC_AUTH_NONE;
1591 void *auth_data = NULL;
1592 SilcUInt32 auth_data_len = 0;
1593 SilcConnAuth connauth;
1594 SilcCipher send_key, receive_key;
1595 SilcHmac hmac_send, hmac_receive;
1598 SILC_LOG_DEBUG(("Connection %p, SKE completed, entry %p", sconn, entry));
1602 if (status != SILC_SKE_STATUS_OK) {
1604 SILC_LOG_ERROR(("Error (%s) during Key Exchange protocol with %s (%s)",
1605 silc_ske_map_status(status), entry->hostname, entry->ip));
1607 /* XXX retry connecting */
1609 silc_server_disconnect_remote(server, sconn->sock,
1610 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED, NULL);
1611 if (sconn->callback)
1612 (*sconn->callback)(server, NULL, sconn->callback_context);
1613 silc_server_free_sock_user_data(server, sconn->sock, NULL);
1614 silc_server_connection_free(sconn);
1618 SILC_LOG_DEBUG(("Setting keys into use"));
1620 /* Set the keys into use. The data will be encrypted after this. */
1621 if (!silc_ske_set_keys(ske, keymat, prop, &send_key, &receive_key,
1622 &hmac_send, &hmac_receive, &hash)) {
1624 /* XXX retry connecting */
1626 /* Error setting keys */
1628 silc_server_disconnect_remote(server, sconn->sock,
1629 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED, NULL);
1630 if (sconn->callback)
1631 (*sconn->callback)(server, NULL, sconn->callback_context);
1632 silc_server_free_sock_user_data(server, sconn->sock, NULL);
1633 silc_server_connection_free(sconn);
1636 silc_packet_set_keys(sconn->sock, send_key, receive_key, hmac_send,
1637 hmac_receive, FALSE);
1639 SILC_LOG_DEBUG(("Starting connection authentication"));
1641 connauth = silc_connauth_alloc(server->schedule, ske,
1642 server->config->conn_auth_timeout);
1644 /* XXX retry connecting */
1646 /** Error allocating auth protocol */
1648 silc_server_disconnect_remote(server, sconn->sock,
1649 SILC_STATUS_ERR_RESOURCE_LIMIT, NULL);
1650 if (sconn->callback)
1651 (*sconn->callback)(server, NULL, sconn->callback_context);
1652 silc_server_free_sock_user_data(server, sconn->sock, NULL);
1653 silc_server_connection_free(sconn);
1657 /* Get authentication method */
1659 if (conn->passphrase) {
1660 if (conn->publickeys && !server->config->prefer_passphrase_auth) {
1661 auth_meth = SILC_AUTH_PUBLIC_KEY;
1662 auth_data = server->private_key;
1664 auth_meth = SILC_AUTH_PASSWORD;
1665 auth_data = conn->passphrase;
1666 auth_data_len = conn->passphrase_len;
1669 auth_meth = SILC_AUTH_PUBLIC_KEY;
1670 auth_data = server->private_key;
1674 entry->data.rekey = rekey;
1676 /* Start connection authentication */
1678 silc_connauth_initiator(connauth, server->server_type == SILC_SERVER ?
1679 SILC_CONN_SERVER : SILC_CONN_ROUTER, auth_meth,
1680 auth_data, auth_data_len,
1681 silc_server_ke_auth_compl, sconn);
1684 /* Function that is called when the network connection to a router has
1685 been established. This will continue with the key exchange protocol
1686 with the remote router. */
1688 void silc_server_start_key_exchange(SilcServerConnection sconn)
1690 SilcServer server = sconn->server;
1691 SilcServerConfigRouter *conn = sconn->conn.ref_ptr;
1692 SilcUnknownEntry entry;
1693 SilcSKEParamsStruct params;
1696 /* Cancel any possible retry timeouts */
1697 silc_schedule_task_del_by_context(server->schedule, sconn);
1699 /* Create packet stream */
1700 sconn->sock = silc_packet_stream_create(server->packet_engine,
1701 server->schedule, sconn->stream);
1703 SILC_LOG_ERROR(("Cannot connect: cannot create packet stream"));
1704 silc_stream_destroy(sconn->stream);
1705 if (sconn->callback)
1706 (*sconn->callback)(server, NULL, sconn->callback_context);
1707 silc_server_connection_free(sconn);
1710 server->stat.conn_num++;
1712 /* Set source ID to packet stream */
1713 if (!silc_packet_set_ids(sconn->sock, SILC_ID_SERVER, server->id,
1715 silc_packet_stream_destroy(sconn->sock);
1716 if (sconn->callback)
1717 (*sconn->callback)(server, NULL, sconn->callback_context);
1718 silc_server_connection_free(sconn);
1722 /* Create entry for remote entity */
1723 entry = silc_calloc(1, sizeof(*entry));
1725 silc_packet_stream_destroy(sconn->sock);
1726 silc_server_connection_free(sconn);
1729 entry->server = server;
1730 silc_packet_set_context(sconn->sock, entry);
1732 SILC_LOG_DEBUG(("Created unknown connection %p", entry));
1734 /* Set Key Exchange flags from configuration, but fall back to global
1736 memset(¶ms, 0, sizeof(params));
1737 SILC_GET_SKE_FLAGS(conn, params.flags);
1738 if (server->config->param.key_exchange_pfs)
1739 params.flags |= SILC_SKE_SP_FLAG_PFS;
1741 /* Start SILC Key Exchange protocol */
1742 SILC_LOG_DEBUG(("Starting key exchange protocol, connection %p", sconn));
1743 ske = silc_ske_alloc(server->rng, server->schedule, server->repository,
1744 server->public_key, server->private_key, sconn);
1747 silc_packet_stream_destroy(sconn->sock);
1748 if (sconn->callback)
1749 (*sconn->callback)(server, NULL, sconn->callback_context);
1750 silc_server_connection_free(sconn);
1753 silc_ske_set_callbacks(ske, silc_server_verify_key,
1754 silc_server_ke_completed, sconn->sock);
1756 /* Start key exchange protocol */
1757 params.version = silc_version_string;
1758 params.timeout_secs = server->config->key_exchange_timeout;
1759 entry->op = silc_ske_initiator(ske, sconn->sock, ¶ms, NULL);
1762 /* Timeout callback that will be called to retry connecting to remote
1763 router. This is used by both normal and router server. This will wait
1764 before retrying the connecting. The timeout is generated by exponential
1765 backoff algorithm. */
1767 SILC_TASK_CALLBACK(silc_server_connect_to_router_retry)
1769 SilcServerConnection sconn = context;
1770 SilcServer server = sconn->server;
1771 SilcServerConfigRouter *conn = sconn->conn.ref_ptr;
1772 SilcServerConfigConnParams *param =
1773 (conn->param ? conn->param : &server->config->param);
1775 SILC_LOG_INFO(("Retrying connecting to %s:%d", sconn->remote_host,
1776 sconn->remote_port));
1778 /* Calculate next timeout */
1779 if (sconn->retry_count >= 1) {
1780 sconn->retry_timeout = sconn->retry_timeout * SILC_SERVER_RETRY_MULTIPLIER;
1781 if (sconn->retry_timeout > param->reconnect_interval_max)
1782 sconn->retry_timeout = param->reconnect_interval_max;
1784 sconn->retry_timeout = param->reconnect_interval;
1786 sconn->retry_count++;
1787 sconn->retry_timeout = sconn->retry_timeout +
1788 (silc_rng_get_rn32(server->rng) % SILC_SERVER_RETRY_RANDOMIZER);
1790 /* If we've reached max retry count, give up. */
1791 if ((sconn->retry_count > param->reconnect_count) &&
1792 !param->reconnect_keep_trying) {
1793 SILC_LOG_ERROR(("Could not connect, giving up"));
1795 if (sconn->callback)
1796 (*sconn->callback)(server, NULL, sconn->callback_context);
1797 silc_server_connection_free(sconn);
1801 SILC_LOG_DEBUG(("Retrying connecting %d seconds", sconn->retry_timeout));
1803 /* We will lookup a fresh pointer later */
1804 silc_server_config_unref(&sconn->conn);
1806 /* Wait before retrying */
1807 silc_schedule_task_del_by_context(server->schedule, sconn);
1808 silc_schedule_task_add_timeout(server->schedule, silc_server_connect_router,
1809 sconn, sconn->retry_timeout, 0);
1812 /* Callback for async connection to remote router */
1814 static void silc_server_connection_established(SilcNetStatus status,
1818 SilcServerConnection sconn = context;
1819 SilcServer server = sconn->server;
1821 silc_schedule_task_del_by_context(server->schedule, sconn);
1826 SILC_LOG_DEBUG(("Connection %p to %s:%d established", sconn,
1827 sconn->remote_host, sconn->remote_port));
1829 /* Continue with key exchange protocol */
1830 sconn->stream = stream;
1831 silc_server_start_key_exchange(sconn);
1834 case SILC_NET_UNKNOWN_IP:
1835 case SILC_NET_UNKNOWN_HOST:
1836 SILC_LOG_ERROR(("Could not connect to %s:%d: %s",
1837 sconn->remote_host, sconn->remote_port,
1838 silc_net_get_error_string(status)));
1840 if (sconn->callback)
1841 (*sconn->callback)(server, NULL, sconn->callback_context);
1842 silc_server_connection_free(sconn);
1846 SILC_LOG_ERROR(("Could not connect to %s:%d: %s",
1847 sconn->remote_host, sconn->remote_port,
1848 silc_net_get_error_string(status)));
1849 if (!sconn->no_reconnect) {
1850 silc_schedule_task_add_timeout(sconn->server->schedule,
1851 silc_server_connect_to_router_retry,
1853 silc_dlist_del(server->conns, sconn);
1855 if (sconn->callback)
1856 (*sconn->callback)(server, NULL, sconn->callback_context);
1857 silc_server_connection_free(sconn);
1863 /* Generic routine to use connect to a router. */
1865 SILC_TASK_CALLBACK(silc_server_connect_router)
1867 SilcServerConnection sconn = context;
1868 SilcServer server = sconn->server;
1869 SilcServerConfigRouter *rconn;
1871 silc_schedule_task_del_by_context(server->schedule, sconn);
1873 /* Don't connect if we are shutting down. */
1874 if (server->server_shutdown) {
1875 if (sconn->callback)
1876 (*sconn->callback)(server, NULL, sconn->callback_context);
1877 silc_server_connection_free(sconn);
1881 SILC_LOG_INFO(("Connecting to the %s %s on port %d",
1882 (sconn->backup ? "backup router" : "router"),
1883 sconn->remote_host, sconn->remote_port));
1885 if (!sconn->no_conf) {
1886 /* Find connection configuration */
1887 rconn = silc_server_config_find_router_conn(server, sconn->remote_host,
1888 sconn->remote_port);
1890 SILC_LOG_INFO(("Unconfigured %s connection %s:%d, cannot connect",
1891 (sconn->backup ? "backup router" : "router"),
1892 sconn->remote_host, sconn->remote_port));
1893 silc_server_connection_free(sconn);
1896 silc_server_config_ref(&sconn->conn, server->config, (void *)rconn);
1899 /* Connect to remote host */
1901 silc_net_tcp_connect((!server->config->server_info->primary ? NULL :
1902 server->config->server_info->primary->server_ip),
1903 sconn->remote_host, sconn->remote_port,
1904 server->schedule, silc_server_connection_established,
1907 SILC_LOG_ERROR(("Could not connect to router %s:%d",
1908 sconn->remote_host, sconn->remote_port));
1909 silc_server_connection_free(sconn);
1913 /* Add to connection list */
1914 silc_dlist_add(server->conns, sconn);
1917 /* This function connects to our primary router or if we are a router this
1918 establishes all our primary routes. This is called at the start of the
1919 server to do authentication and key exchange with our router - called
1922 SILC_TASK_CALLBACK(silc_server_connect_to_router)
1924 SilcServer server = context;
1925 SilcServerConnection sconn;
1926 SilcServerConfigRouter *ptr;
1928 /* Don't connect if we are shutting down. */
1929 if (server->server_shutdown)
1932 SILC_LOG_DEBUG(("We are %s",
1933 (server->server_type == SILC_SERVER ?
1934 "normal server" : server->server_type == SILC_ROUTER ?
1935 "router" : "backup router/normal server")));
1937 if (!server->config->routers) {
1938 /* There wasn't a configured router, we will continue but we don't
1939 have a connection to outside world. We will be standalone server. */
1940 SILC_LOG_DEBUG(("No router(s), we are standalone"));
1941 server->standalone = TRUE;
1945 /* Cancel any possible retry timeouts */
1946 silc_schedule_task_del_by_callback(server->schedule,
1947 silc_server_connect_router);
1948 silc_schedule_task_del_by_callback(server->schedule,
1949 silc_server_connect_to_router_retry);
1951 /* Create the connections to all our routes */
1952 for (ptr = server->config->routers; ptr; ptr = ptr->next) {
1954 SILC_LOG_DEBUG(("%s connection [%s] %s:%d",
1955 ptr->backup_router ? "Backup router" : "Router",
1956 ptr->initiator ? "Initiator" : "Responder",
1957 ptr->host, ptr->port));
1959 if (server->server_type == SILC_ROUTER && ptr->backup_router &&
1960 ptr->initiator == FALSE && !server->backup_router &&
1961 !silc_server_config_get_backup_router(server))
1962 server->wait_backup = TRUE;
1964 if (!ptr->initiator)
1966 if (ptr->dynamic_connection)
1969 /* Check whether we are connecting or connected to this host already */
1970 if (silc_server_num_sockets_by_remote(server,
1971 silc_net_is_ip(ptr->host) ?
1973 silc_net_is_ip(ptr->host) ?
1974 NULL : ptr->host, ptr->port,
1975 SILC_CONN_ROUTER)) {
1976 SILC_LOG_DEBUG(("We are already connected to %s:%d",
1977 ptr->host, ptr->port));
1979 /* If we don't have primary router and this connection is our
1980 primary router we are in desync. Reconnect to the primary. */
1981 if (server->standalone && !server->router) {
1983 SilcPacketStream sock;
1984 SilcServerConfigRouter *primary =
1985 silc_server_config_get_primary_router(server);
1988 sock = silc_server_find_socket_by_host(server, SILC_CONN_ROUTER,
1989 ptr->host, ptr->port);
1992 server->backup_noswitch = TRUE;
1993 silc_server_free_sock_user_data(server, sock, NULL);
1994 silc_server_disconnect_remote(server, sock, 0, NULL);
1995 server->backup_noswitch = FALSE;
1996 SILC_LOG_DEBUG(("Reconnecting to primary router"));
2002 /* Allocate connection object for hold connection specific stuff. */
2003 sconn = silc_calloc(1, sizeof(*sconn));
2006 sconn->server = server;
2007 sconn->remote_host = strdup(ptr->host);
2008 sconn->remote_port = ptr->port;
2009 sconn->backup = ptr->backup_router;
2010 if (sconn->backup) {
2011 sconn->backup_replace_ip = strdup(ptr->backup_replace_ip);
2012 sconn->backup_replace_port = ptr->backup_replace_port;
2015 SILC_LOG_DEBUG(("Created connection %p", sconn));
2017 if (!server->router_conn && !sconn->backup)
2018 server->router_conn = sconn;
2021 silc_server_connect_router(server->schedule, server, SILC_TASK_EXPIRE,
2027 /************************ Accepting new connection **************************/
2029 /* After this is called, server don't wait for backup router anymore.
2030 This gets called automatically even after we have backup router
2031 connection established. */
2033 SILC_TASK_CALLBACK(silc_server_backup_router_wait)
2035 SilcServer server = context;
2036 server->wait_backup = FALSE;
2039 /* Authentication data callback */
2042 silc_server_accept_get_auth(SilcConnAuth connauth,
2043 SilcConnectionType conn_type,
2044 unsigned char **passphrase,
2045 SilcUInt32 *passphrase_len,
2046 SilcSKR *repository,
2049 SilcPacketStream sock = context;
2050 SilcUnknownEntry entry = silc_packet_get_context(sock);
2051 SilcServer server = entry->server;
2053 SILC_LOG_DEBUG(("Remote connection type %d", conn_type));
2055 /* Remote end is client */
2056 if (conn_type == SILC_CONN_CLIENT) {
2057 SilcServerConfigClient *cconfig = entry->cconfig.ref_ptr;
2061 *passphrase = cconfig->passphrase;
2062 *passphrase_len = cconfig->passphrase_len;
2063 if (cconfig->publickeys)
2064 *repository = server->repository;
2066 if (cconfig->publickeys) {
2067 if (server->config->prefer_passphrase_auth) {
2071 *passphrase_len = 0;
2075 entry->conn_type = conn_type;
2079 /* Remote end is server */
2080 if (conn_type == SILC_CONN_SERVER) {
2081 SilcServerConfigServer *sconfig;
2083 /* If we are normal server, don't accept the connection */
2084 if (server->server_type == SILC_SERVER)
2087 sconfig = entry->sconfig.ref_ptr;
2091 *passphrase = sconfig->passphrase;
2092 *passphrase_len = sconfig->passphrase_len;
2093 if (sconfig->publickeys)
2094 *repository = server->repository;
2096 if (sconfig->publickeys) {
2097 if (server->config->prefer_passphrase_auth) {
2101 *passphrase_len = 0;
2105 entry->conn_type = conn_type;
2109 /* Remote end is router */
2110 if (conn_type == SILC_CONN_ROUTER) {
2111 SilcServerConfigRouter *rconfig = entry->rconfig.ref_ptr;
2115 *passphrase = rconfig->passphrase;
2116 *passphrase_len = rconfig->passphrase_len;
2117 if (rconfig->publickeys)
2118 *repository = server->repository;
2120 if (rconfig->publickeys) {
2121 if (server->config->prefer_passphrase_auth) {
2125 *passphrase_len = 0;
2129 entry->conn_type = conn_type;
2136 /* Authentication completion callback. */
2139 silc_server_accept_auth_compl(SilcConnAuth connauth, SilcBool success,
2142 SilcPacketStream sock = context;
2143 SilcUnknownEntry entry = silc_packet_get_context(sock);
2144 SilcIDListData idata = (SilcIDListData)entry;
2145 SilcServer server = entry->server;
2146 SilcServerConfigConnParams *param = &server->config->param;
2147 SilcServerConnection sconn;
2149 const char *hostname, *ip;
2153 silc_socket_stream_get_info(silc_packet_stream_get_stream(sock),
2154 NULL, &hostname, &ip, &port);
2156 if (success == FALSE) {
2157 /* Authentication failed */
2158 SILC_LOG_INFO(("Authentication failed for %s (%s) [%s]", entry->hostname,
2159 entry->ip, SILC_CONNTYPE_STRING(entry->data.conn_type)));
2160 server->stat.auth_failures++;
2161 silc_server_disconnect_remote(server, sock,
2162 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED, NULL);
2163 silc_server_config_unref(&entry->cconfig);
2164 silc_server_config_unref(&entry->sconfig);
2165 silc_server_config_unref(&entry->rconfig);
2166 silc_server_free_sock_user_data(server, sock, NULL);
2170 SILC_LOG_DEBUG(("Checking whether connection is allowed"));
2172 switch (entry->conn_type) {
2173 case SILC_CONN_CLIENT:
2175 SilcClientEntry client;
2176 SilcServerConfigClient *conn = entry->cconfig.ref_ptr;
2178 /* Verify whether this connection is after all allowed to connect */
2179 if (!silc_server_connection_allowed(server, sock, entry->conn_type,
2180 &server->config->param,
2182 silc_connauth_get_ske(connauth))) {
2183 server->stat.auth_failures++;
2187 /* If we are primary router and we have backup router configured
2188 but it has not connected to use yet, do not accept any other
2190 if (server->wait_backup && server->server_type == SILC_ROUTER &&
2191 !server->backup_router) {
2192 SilcServerConfigRouter *router;
2193 router = silc_server_config_get_backup_router(server);
2194 if (router && strcmp(server->config->server_info->primary->server_ip,
2196 silc_server_find_socket_by_host(server,
2198 router->backup_replace_ip, 0)) {
2199 SILC_LOG_INFO(("Will not accept connections because we do "
2200 "not have backup router connection established"));
2201 silc_server_disconnect_remote(server, sock,
2202 SILC_STATUS_ERR_PERM_DENIED,
2203 "We do not have connection to backup "
2204 "router established, try later");
2205 silc_server_config_unref(&entry->cconfig);
2206 silc_server_config_unref(&entry->sconfig);
2207 silc_server_config_unref(&entry->rconfig);
2208 silc_server_free_sock_user_data(server, sock, NULL);
2209 server->stat.auth_failures++;
2211 /* From here on, wait 20 seconds for the backup router to appear. */
2212 silc_schedule_task_add_timeout(server->schedule,
2213 silc_server_backup_router_wait,
2214 (void *)server, 20, 0);
2219 SILC_LOG_DEBUG(("Remote host is client"));
2220 SILC_LOG_INFO(("Connection %s (%s) is client", entry->hostname,
2223 /* Add the client to the client ID cache. The nickname and Client ID
2224 and other information is created after we have received NEW_CLIENT
2225 packet from client. */
2226 client = silc_idlist_add_client(server->local_list,
2227 NULL, NULL, NULL, NULL, NULL, sock);
2229 SILC_LOG_ERROR(("Could not add new client to cache"));
2230 server->stat.auth_failures++;
2231 silc_server_disconnect_remote(server, sock,
2232 SILC_STATUS_ERR_AUTH_FAILED, NULL);
2233 silc_server_config_unref(&entry->cconfig);
2234 silc_server_config_unref(&entry->sconfig);
2235 silc_server_config_unref(&entry->rconfig);
2236 silc_server_free_sock_user_data(server, sock, NULL);
2239 entry->data.status |= SILC_IDLIST_STATUS_LOCAL;
2240 entry->data.conn_type = SILC_CONN_CLIENT;
2243 server->stat.my_clients++;
2244 server->stat.clients++;
2245 server->stat.cell_clients++;
2247 /* Get connection parameters */
2249 param = conn->param;
2251 if (!param->keepalive_secs)
2252 param->keepalive_secs = server->config->param.keepalive_secs;
2254 if (!param->qos && server->config->param.qos) {
2255 param->qos = server->config->param.qos;
2256 param->qos_rate_limit = server->config->param.qos_rate_limit;
2257 param->qos_bytes_limit = server->config->param.qos_bytes_limit;
2258 param->qos_limit_sec = server->config->param.qos_limit_sec;
2259 param->qos_limit_usec = server->config->param.qos_limit_usec;
2262 /* Check if to be anonymous connection */
2263 if (param->anonymous)
2264 client->mode |= SILC_UMODE_ANONYMOUS;
2267 /* Add public key to repository */
2268 SILC_LOG_DEBUG(("Add client public key to repository"));
2269 if (!silc_server_get_public_key_by_client(server, client, NULL))
2270 silc_skr_add_public_key_simple(server->repository,
2271 entry->data.public_key,
2272 SILC_SKR_USAGE_IDENTIFICATION, client,
2275 id_entry = (void *)client;
2279 case SILC_CONN_SERVER:
2280 case SILC_CONN_ROUTER:
2282 SilcServerEntry new_server;
2283 SilcBool initiator = FALSE;
2284 SilcBool backup_local = FALSE;
2285 SilcBool backup_router = FALSE;
2286 char *backup_replace_ip = NULL;
2287 SilcUInt16 backup_replace_port = 0;
2288 SilcServerConfigServer *srvconn = entry->sconfig.ref_ptr;
2289 SilcServerConfigRouter *rconn = entry->rconfig.ref_ptr;
2291 /* If we are backup router and this is incoming server connection
2292 and we do not have connection to primary router, do not allow
2294 if (server->server_type == SILC_BACKUP_ROUTER &&
2295 entry->conn_type == SILC_CONN_SERVER &&
2296 !SILC_PRIMARY_ROUTE(server)) {
2297 SILC_LOG_INFO(("Will not accept server connection because we do "
2298 "not have primary router connection established"));
2299 silc_server_disconnect_remote(server, sock,
2300 SILC_STATUS_ERR_PERM_DENIED,
2301 "We do not have connection to primary "
2302 "router established, try later");
2303 silc_server_config_unref(&entry->cconfig);
2304 silc_server_config_unref(&entry->sconfig);
2305 silc_server_config_unref(&entry->rconfig);
2306 silc_server_free_sock_user_data(server, sock, NULL);
2307 server->stat.auth_failures++;
2311 if (entry->conn_type == SILC_CONN_ROUTER) {
2312 /* Verify whether this connection is after all allowed to connect */
2313 if (!silc_server_connection_allowed(server, sock,
2315 &server->config->param,
2316 rconn ? rconn->param : NULL,
2317 silc_connauth_get_ske(connauth))) {
2318 silc_server_config_unref(&entry->cconfig);
2319 silc_server_config_unref(&entry->sconfig);
2320 silc_server_config_unref(&entry->rconfig);
2321 server->stat.auth_failures++;
2327 param = rconn->param;
2329 if (!param->keepalive_secs)
2330 param->keepalive_secs = server->config->param.keepalive_secs;
2332 if (!param->qos && server->config->param.qos) {
2333 param->qos = server->config->param.qos;
2334 param->qos_rate_limit = server->config->param.qos_rate_limit;
2335 param->qos_bytes_limit = server->config->param.qos_bytes_limit;
2336 param->qos_limit_sec = server->config->param.qos_limit_sec;
2337 param->qos_limit_usec = server->config->param.qos_limit_usec;
2341 initiator = rconn->initiator;
2342 backup_local = rconn->backup_local;
2343 backup_router = rconn->backup_router;
2344 backup_replace_ip = rconn->backup_replace_ip;
2345 backup_replace_port = rconn->backup_replace_port;
2349 if (entry->conn_type == SILC_CONN_SERVER) {
2350 /* Verify whether this connection is after all allowed to connect */
2351 if (!silc_server_connection_allowed(server, sock,
2353 &server->config->param,
2354 srvconn ? srvconn->param : NULL,
2355 silc_connauth_get_ske(connauth))) {
2356 server->stat.auth_failures++;
2360 if (srvconn->param) {
2361 param = srvconn->param;
2363 if (!param->keepalive_secs)
2364 param->keepalive_secs = server->config->param.keepalive_secs;
2366 if (!param->qos && server->config->param.qos) {
2367 param->qos = server->config->param.qos;
2368 param->qos_rate_limit = server->config->param.qos_rate_limit;
2369 param->qos_bytes_limit = server->config->param.qos_bytes_limit;
2370 param->qos_limit_sec = server->config->param.qos_limit_sec;
2371 param->qos_limit_usec = server->config->param.qos_limit_usec;
2375 backup_router = srvconn->backup_router;
2379 /* If we are primary router and we have backup router configured
2380 but it has not connected to use yet, do not accept any other
2382 if (server->wait_backup && server->server_type == SILC_ROUTER &&
2383 !server->backup_router && !backup_router) {
2384 SilcServerConfigRouter *router;
2385 router = silc_server_config_get_backup_router(server);
2386 if (router && strcmp(server->config->server_info->primary->server_ip,
2388 silc_server_find_socket_by_host(server,
2390 router->backup_replace_ip, 0)) {
2391 SILC_LOG_INFO(("Will not accept connections because we do "
2392 "not have backup router connection established"));
2393 silc_server_disconnect_remote(server, sock,
2394 SILC_STATUS_ERR_PERM_DENIED,
2395 "We do not have connection to backup "
2396 "router established, try later");
2397 silc_server_config_unref(&entry->cconfig);
2398 silc_server_config_unref(&entry->sconfig);
2399 silc_server_config_unref(&entry->rconfig);
2400 silc_server_free_sock_user_data(server, sock, NULL);
2401 server->stat.auth_failures++;
2403 /* From here on, wait 20 seconds for the backup router to appear. */
2404 silc_schedule_task_add_timeout(server->schedule,
2405 silc_server_backup_router_wait,
2406 (void *)server, 20, 0);
2411 SILC_LOG_DEBUG(("Remote host is %s",
2412 entry->conn_type == SILC_CONN_SERVER ?
2413 "server" : (backup_router ?
2414 "backup router" : "router")));
2415 SILC_LOG_INFO(("Connection %s (%s) is %s", entry->hostname,
2416 entry->ip, entry->conn_type == SILC_CONN_SERVER ?
2417 "server" : (backup_router ?
2418 "backup router" : "router")));
2420 /* Add the server into server cache. The server name and Server ID
2421 is updated after we have received NEW_SERVER packet from the
2422 server. We mark ourselves as router for this server if we really
2425 silc_idlist_add_server((entry->conn_type == SILC_CONN_SERVER ?
2426 server->local_list : (backup_router ?
2427 server->local_list :
2428 server->global_list)),
2430 (entry->conn_type == SILC_CONN_SERVER ?
2431 SILC_SERVER : SILC_ROUTER),
2433 (entry->conn_type == SILC_CONN_SERVER ?
2434 server->id_entry : (backup_router ?
2435 server->id_entry : NULL)),
2438 SILC_LOG_ERROR(("Could not add new server to cache"));
2439 silc_server_disconnect_remote(server, sock,
2440 SILC_STATUS_ERR_AUTH_FAILED, NULL);
2441 silc_server_config_unref(&entry->cconfig);
2442 silc_server_config_unref(&entry->sconfig);
2443 silc_server_config_unref(&entry->rconfig);
2444 silc_server_free_sock_user_data(server, sock, NULL);
2445 server->stat.auth_failures++;
2448 entry->data.status |= SILC_IDLIST_STATUS_LOCAL;
2449 entry->data.conn_type = entry->conn_type;
2451 id_entry = (void *)new_server;
2453 /* If the incoming connection is router and marked as backup router
2454 then add it to be one of our backups */
2455 if (entry->data.conn_type == SILC_CONN_ROUTER && backup_router) {
2456 /* Change it back to SERVER type since that's what it really is. */
2458 entry->data.conn_type = SILC_CONN_SERVER;
2459 new_server->server_type = SILC_BACKUP_ROUTER;
2461 SILC_SERVER_SEND_OPERS(server, FALSE, TRUE, SILC_NOTIFY_TYPE_NONE,
2462 ("Backup router %s is now online",
2465 /* Remove the backup waiting with timeout */
2466 silc_schedule_task_add_timeout(server->schedule,
2467 silc_server_backup_router_wait,
2468 (void *)server, 10, 0);
2472 if (entry->data.conn_type == SILC_CONN_SERVER) {
2473 server->stat.my_servers++;
2474 server->stat.servers++;
2475 SILC_LOG_DEBUG(("my_servers %d", server->stat.my_servers));
2477 server->stat.my_routers++;
2478 server->stat.routers++;
2479 SILC_LOG_DEBUG(("my_routers %d", server->stat.my_routers));
2482 /* Check whether this connection is to be our primary router connection
2483 if we do not already have the primary route. */
2484 if (!backup_router &&
2485 server->standalone && entry->data.conn_type == SILC_CONN_ROUTER) {
2486 if (silc_server_config_is_primary_route(server) && !initiator)
2489 SILC_LOG_DEBUG(("We are not standalone server anymore"));
2490 server->standalone = FALSE;
2491 if (!server->id_entry->router) {
2492 server->id_entry->router = id_entry;
2493 server->router = id_entry;
2505 /* Add connection to server->conns so that we know we have connection
2507 sconn = silc_calloc(1, sizeof(*sconn));
2508 sconn->server = server;
2510 sconn->remote_host = strdup(hostname);
2511 sconn->remote_port = port;
2512 silc_dlist_add(server->conns, sconn);
2513 idata->sconn = sconn;
2514 idata->last_receive = time(NULL);
2516 /* Add the common data structure to the ID entry. */
2517 silc_idlist_add_data(id_entry, (SilcIDListData)entry);
2518 silc_packet_set_context(sock, id_entry);
2520 /* Connection has been fully established now. Everything is ok. */
2521 SILC_LOG_DEBUG(("New connection %p authenticated", sconn));
2523 /* Perform Quality of Service */
2525 silc_socket_stream_set_qos(silc_packet_stream_get_stream(sock),
2526 param->qos_rate_limit, param->qos_bytes_limit,
2527 param->qos_limit_sec, param->qos_limit_usec);
2529 silc_server_config_unref(&entry->cconfig);
2530 silc_server_config_unref(&entry->sconfig);
2531 silc_server_config_unref(&entry->rconfig);
2535 silc_ske_free(silc_connauth_get_ske(connauth));
2536 silc_connauth_free(connauth);
2539 /* SKE completion callback. We set the new keys into use here. */
2542 silc_server_accept_completed(SilcSKE ske, SilcSKEStatus status,
2543 SilcSKESecurityProperties prop,
2544 SilcSKEKeyMaterial keymat,
2545 SilcSKERekeyMaterial rekey,
2548 SilcPacketStream sock = context;
2549 SilcUnknownEntry entry = silc_packet_get_context(sock);
2550 SilcIDListData idata = (SilcIDListData)entry;
2551 SilcServer server = entry->server;
2552 SilcConnAuth connauth;
2553 SilcCipher send_key, receive_key;
2554 SilcHmac hmac_send, hmac_receive;
2561 if (status != SILC_SKE_STATUS_OK) {
2563 SILC_LOG_ERROR(("Error (%s) during Key Exchange protocol with %s (%s)",
2564 silc_ske_map_status(status), entry->hostname, entry->ip));
2566 silc_server_disconnect_remote(server, sock,
2567 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED, NULL);
2568 silc_server_config_unref(&entry->cconfig);
2569 silc_server_config_unref(&entry->sconfig);
2570 silc_server_config_unref(&entry->rconfig);
2571 silc_server_free_sock_user_data(server, sock, NULL);
2575 SILC_LOG_DEBUG(("Setting keys into use"));
2577 /* Set the keys into use. The data will be encrypted after this. */
2578 if (!silc_ske_set_keys(ske, keymat, prop, &send_key, &receive_key,
2579 &hmac_send, &hmac_receive, &hash)) {
2580 /* Error setting keys */
2582 silc_server_disconnect_remote(server, sock,
2583 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED, NULL);
2584 silc_server_free_sock_user_data(server, sock, NULL);
2587 silc_packet_set_keys(sock, send_key, receive_key, hmac_send,
2588 hmac_receive, FALSE);
2590 idata->rekey = rekey;
2591 idata->public_key = silc_pkcs_public_key_copy(prop->public_key);
2592 pk = silc_pkcs_public_key_encode(idata->public_key, &pk_len);
2593 silc_hash_make(server->sha1hash, pk, pk_len, idata->fingerprint);
2595 silc_hash_alloc(silc_hash_get_name(prop->hash), &idata->hash);
2597 SILC_LOG_DEBUG(("Starting connection authentication"));
2598 server->stat.auth_attempts++;
2600 connauth = silc_connauth_alloc(server->schedule, ske,
2601 server->config->conn_auth_timeout);
2603 /** Error allocating auth protocol */
2605 silc_server_disconnect_remote(server, sock,
2606 SILC_STATUS_ERR_RESOURCE_LIMIT, NULL);
2607 silc_server_config_unref(&entry->cconfig);
2608 silc_server_config_unref(&entry->sconfig);
2609 silc_server_config_unref(&entry->rconfig);
2610 silc_server_free_sock_user_data(server, sock, NULL);
2614 /* Start connection authentication */
2616 silc_connauth_responder(connauth, silc_server_accept_get_auth,
2617 silc_server_accept_auth_compl, sock);
2620 /* Accept new TCP connection */
2622 static void silc_server_accept_new_connection(SilcNetStatus status,
2626 SilcServer server = context;
2627 SilcPacketStream packet_stream;
2628 SilcServerConfigClient *cconfig = NULL;
2629 SilcServerConfigServer *sconfig = NULL;
2630 SilcServerConfigRouter *rconfig = NULL;
2631 SilcServerConfigDeny *deny;
2632 SilcUnknownEntry entry;
2634 SilcSKEParamsStruct params;
2635 char *hostname, *ip;
2638 SILC_LOG_DEBUG(("Accepting new connection"));
2640 /* Check for maximum allowed connections */
2641 server->stat.conn_attempts++;
2642 if (silc_dlist_count(server->conns) >
2643 server->config->param.connections_max) {
2644 SILC_LOG_ERROR(("Refusing connection, server is full"));
2645 server->stat.conn_failures++;
2646 silc_stream_destroy(stream);
2650 /* Get hostname, IP and port */
2651 if (!silc_socket_stream_get_info(stream, NULL, (const char **)&hostname,
2652 (const char **)&ip, &port)) {
2653 /* Bad socket stream */
2654 server->stat.conn_failures++;
2655 silc_stream_destroy(stream);
2659 /* Create packet stream */
2660 packet_stream = silc_packet_stream_create(server->packet_engine,
2661 server->schedule, stream);
2662 if (!packet_stream) {
2663 SILC_LOG_ERROR(("Refusing connection, cannot create packet stream"));
2664 server->stat.conn_failures++;
2665 silc_stream_destroy(stream);
2668 server->stat.conn_num++;
2670 SILC_LOG_DEBUG(("Created packet stream %p", packet_stream));
2672 /* Set source ID to packet stream */
2673 if (!silc_packet_set_ids(packet_stream, SILC_ID_SERVER, server->id,
2676 server->stat.conn_failures++;
2677 silc_packet_stream_destroy(packet_stream);
2681 /* Check whether this connection is denied to connect to us. */
2682 deny = silc_server_config_find_denied(server, ip);
2684 deny = silc_server_config_find_denied(server, hostname);
2686 /* The connection is denied */
2687 SILC_LOG_INFO(("Connection %s (%s) is denied", hostname, ip));
2688 silc_server_disconnect_remote(server, packet_stream,
2689 SILC_STATUS_ERR_BANNED_FROM_SERVER,
2691 silc_server_free_sock_user_data(server, packet_stream, NULL);
2695 /* Check whether we have configured this sort of connection at all. We
2696 have to check all configurations since we don't know what type of
2697 connection this is. */
2698 if (!(cconfig = silc_server_config_find_client(server, ip)))
2699 cconfig = silc_server_config_find_client(server, hostname);
2700 if (!(sconfig = silc_server_config_find_server_conn(server, ip)))
2701 sconfig = silc_server_config_find_server_conn(server, hostname);
2702 if (server->server_type == SILC_ROUTER)
2703 if (!(rconfig = silc_server_config_find_router_conn(server, ip, port)))
2704 rconfig = silc_server_config_find_router_conn(server, hostname, port);
2705 if (!cconfig && !sconfig && !rconfig) {
2706 SILC_LOG_INFO(("Connection %s (%s) is not allowed", hostname, ip));
2707 server->stat.conn_failures++;
2708 silc_server_disconnect_remote(server, packet_stream,
2709 SILC_STATUS_ERR_BANNED_FROM_SERVER, NULL);
2710 silc_server_free_sock_user_data(server, packet_stream, NULL);
2714 /* The connection is allowed */
2715 entry = silc_calloc(1, sizeof(*entry));
2717 server->stat.conn_failures++;
2718 silc_server_disconnect_remote(server, packet_stream,
2719 SILC_STATUS_ERR_RESOURCE_LIMIT, NULL);
2720 silc_server_free_sock_user_data(server, packet_stream, NULL);
2723 entry->hostname = hostname;
2726 entry->server = server;
2727 entry->data.conn_type = SILC_CONN_UNKNOWN;
2728 silc_packet_set_context(packet_stream, entry);
2730 SILC_LOG_DEBUG(("Created unknown connection %p", entry));
2732 silc_server_config_ref(&entry->cconfig, server->config, cconfig);
2733 silc_server_config_ref(&entry->sconfig, server->config, sconfig);
2734 silc_server_config_ref(&entry->rconfig, server->config, rconfig);
2736 /* Take flags for key exchange. Since we do not know what type of connection
2737 this is, we go through all found configurations and use the global ones
2738 as well. This will result always into strictest key exchange flags. */
2739 memset(¶ms, 0, sizeof(params));
2740 SILC_GET_SKE_FLAGS(cconfig, params.flags);
2741 SILC_GET_SKE_FLAGS(sconfig, params.flags);
2742 SILC_GET_SKE_FLAGS(rconfig, params.flags);
2743 if (server->config->param.key_exchange_pfs)
2744 params.flags |= SILC_SKE_SP_FLAG_PFS;
2746 SILC_LOG_INFO(("Incoming connection %s (%s)", hostname, ip));
2747 server->stat.conn_attempts++;
2749 /* Start SILC Key Exchange protocol */
2750 SILC_LOG_DEBUG(("Starting key exchange protocol"));
2751 ske = silc_ske_alloc(server->rng, server->schedule, server->repository,
2752 server->public_key, server->private_key,
2755 server->stat.conn_failures++;
2756 silc_server_disconnect_remote(server, packet_stream,
2757 SILC_STATUS_ERR_RESOURCE_LIMIT, NULL);
2758 silc_server_free_sock_user_data(server, packet_stream, NULL);
2761 silc_ske_set_callbacks(ske, silc_server_verify_key,
2762 silc_server_accept_completed, packet_stream);
2764 /* Start key exchange protocol */
2765 params.version = silc_version_string;
2766 params.timeout_secs = server->config->key_exchange_timeout;
2767 entry->op = silc_ske_responder(ske, packet_stream, ¶ms);
2771 /********************************** Rekey ***********************************/
2773 /* Initiator rekey completion callback */
2775 static void silc_server_rekey_completion(SilcSKE ske,
2776 SilcSKEStatus status,
2777 const SilcSKESecurityProperties prop,
2778 const SilcSKEKeyMaterial keymat,
2779 SilcSKERekeyMaterial rekey,
2782 SilcPacketStream sock = context;
2783 SilcIDListData idata = silc_packet_get_context(sock);
2784 SilcServer server = idata->sconn->server;
2786 idata->sconn->op = NULL;
2787 if (status != SILC_SKE_STATUS_OK) {
2788 SILC_LOG_ERROR(("Error during rekey protocol with %s",
2789 idata->sconn->remote_host));
2793 SILC_LOG_DEBUG(("Rekey protocol completed with %s:%d [%s]",
2794 idata->sconn->remote_host, idata->sconn->remote_port,
2795 SILC_CONNTYPE_STRING(idata->conn_type)));
2797 /* Save rekey data for next rekey */
2798 idata->rekey = rekey;
2800 /* Register new rekey timeout */
2801 silc_schedule_task_add_timeout(server->schedule, silc_server_do_rekey,
2802 sock, idata->sconn->rekey_timeout, 0);
2805 /* Rekey callback. Start rekey as initiator */
2807 SILC_TASK_CALLBACK(silc_server_do_rekey)
2809 SilcServer server = app_context;
2810 SilcPacketStream sock = context;
2811 SilcIDListData idata = silc_packet_get_context(sock);
2814 SILC_LOG_DEBUG(("Perform rekey, sock %p", sock));
2816 /* Do not execute rekey with disabled connections */
2817 if (idata->status & SILC_IDLIST_STATUS_DISABLED)
2820 /* If another protocol is active do not start rekey */
2821 if (idata->sconn->op) {
2822 SILC_LOG_DEBUG(("Waiting for other protocol to finish before rekeying"));
2823 silc_schedule_task_add_timeout(server->schedule, silc_server_do_rekey,
2828 SILC_LOG_DEBUG(("Executing rekey protocol with %s:%d [%s]",
2829 idata->sconn->remote_host, idata->sconn->remote_port,
2830 SILC_CONNTYPE_STRING(idata->conn_type)));
2833 ske = silc_ske_alloc(server->rng, server->schedule, NULL,
2834 server->public_key, NULL, sock);
2838 /* Set SKE callbacks */
2839 silc_ske_set_callbacks(ske, NULL, silc_server_rekey_completion, sock);
2842 idata->sconn->op = silc_ske_rekey_initiator(ske, sock, idata->rekey);
2845 /* Responder rekey completion callback */
2848 silc_server_rekey_resp_completion(SilcSKE ske,
2849 SilcSKEStatus status,
2850 const SilcSKESecurityProperties prop,
2851 const SilcSKEKeyMaterial keymat,
2852 SilcSKERekeyMaterial rekey,
2855 SilcPacketStream sock = context;
2856 SilcIDListData idata = silc_packet_get_context(sock);
2858 idata->sconn->op = NULL;
2859 if (status != SILC_SKE_STATUS_OK) {
2860 SILC_LOG_ERROR(("Error during rekey protocol with %s",
2861 idata->sconn->remote_host));
2865 SILC_LOG_DEBUG(("Rekey protocol completed with %s:%d [%s]",
2866 idata->sconn->remote_host, idata->sconn->remote_port,
2867 SILC_CONNTYPE_STRING(idata->conn_type)));
2869 /* Save rekey data for next rekey */
2870 idata->rekey = rekey;
2873 /* Start rekey as responder */
2875 static void silc_server_rekey(SilcServer server, SilcPacketStream sock,
2878 SilcIDListData idata = silc_packet_get_context(sock);
2881 SILC_LOG_DEBUG(("Executing rekey protocol with %s:%d [%s], sock %p",
2882 idata->sconn->remote_host, idata->sconn->remote_port,
2883 SILC_CONNTYPE_STRING(idata->conn_type), sock));
2886 ske = silc_ske_alloc(server->rng, server->schedule, NULL,
2887 server->public_key, NULL, sock);
2889 silc_packet_free(packet);
2893 /* Set SKE callbacks */
2894 silc_ske_set_callbacks(ske, NULL, silc_server_rekey_resp_completion, sock);
2897 idata->sconn->op = silc_ske_rekey_responder(ske, sock, idata->rekey,
2902 /****************************** Disconnection *******************************/
2904 /* Destroys packet stream. */
2906 SILC_TASK_CALLBACK(silc_server_close_connection_final)
2908 silc_packet_stream_unref(context);
2911 /* Closes connection to socket connection */
2913 void silc_server_close_connection(SilcServer server,
2914 SilcPacketStream sock)
2916 SilcIDListData idata = silc_packet_get_context(sock);
2918 const char *hostname;
2921 if (!silc_packet_stream_is_valid(sock))
2924 memset(tmp, 0, sizeof(tmp));
2925 // silc_socket_get_error(sock, tmp, sizeof(tmp));
2926 silc_socket_stream_get_info(silc_packet_stream_get_stream(sock),
2927 NULL, &hostname, NULL, &port);
2928 SILC_LOG_INFO(("Closing connection %s:%d [%s] %s", hostname, port,
2929 idata ? SILC_CONNTYPE_STRING(idata->conn_type) : "",
2930 tmp[0] ? tmp : ""));
2932 // silc_socket_set_qos(sock, 0, 0, 0, 0, NULL);
2934 if (idata && idata->sconn) {
2935 silc_server_connection_free(idata->sconn);
2936 idata->sconn = NULL;
2939 /* Take a reference and then destroy the stream. The last reference
2940 is released later in a timeout callback. */
2941 silc_packet_stream_ref(sock);
2942 silc_packet_stream_destroy(sock);
2944 /* Close connection with timeout */
2945 server->stat.conn_num--;
2946 silc_schedule_task_del_by_all(server->schedule, 0,
2947 silc_server_close_connection_final, sock);
2948 silc_schedule_task_add_timeout(server->schedule,
2949 silc_server_close_connection_final,
2953 /* Sends disconnect message to remote connection and disconnects the
2956 void silc_server_disconnect_remote(SilcServer server,
2957 SilcPacketStream sock,
2958 SilcStatus status, ...)
2960 unsigned char buf[512];
2967 SILC_LOG_DEBUG(("Disconnecting remote host, sock %p", sock));
2969 va_start(ap, status);
2970 cp = va_arg(ap, char *);
2972 silc_vsnprintf(buf, sizeof(buf), cp, ap);
2975 /* Send SILC_PACKET_DISCONNECT */
2976 silc_packet_send_va(sock, SILC_PACKET_DISCONNECT, 0,
2977 SILC_STR_UI_CHAR(status),
2978 SILC_STR_UI8_STRING(cp ? buf : NULL),
2981 /* Close connection */
2982 silc_server_close_connection(server, sock);
2985 /* Frees client data and notifies about client's signoff. */
2987 void silc_server_free_client_data(SilcServer server,
2988 SilcPacketStream sock,
2989 SilcClientEntry client,
2991 const char *signoff)
2993 SILC_LOG_DEBUG(("Freeing client %p data", client));
2996 /* Check if anyone is watching this nickname */
2997 if (server->server_type == SILC_ROUTER)
2998 silc_server_check_watcher_list(server, client, NULL,
2999 SILC_NOTIFY_TYPE_SIGNOFF);
3001 /* Send SIGNOFF notify to routers. */
3003 silc_server_send_notify_signoff(server, SILC_PRIMARY_ROUTE(server),
3004 SILC_BROADCAST(server), client->id,
3008 /* Remove client from all channels */
3010 silc_server_remove_from_channels(server, NULL, client,
3011 TRUE, (char *)signoff, TRUE, FALSE);
3013 silc_server_remove_from_channels(server, NULL, client,
3014 FALSE, NULL, FALSE, FALSE);
3016 /* Remove this client from watcher list if it is */
3017 silc_server_del_from_watcher_list(server, client);
3019 /* Remove client's public key from repository, this will free it too. */
3020 if (client->data.public_key) {
3021 silc_skr_del_public_key(server->repository, client->data.public_key,
3023 client->data.public_key = NULL;
3026 /* Update statistics */
3027 server->stat.my_clients--;
3028 server->stat.clients--;
3029 if (server->stat.cell_clients)
3030 server->stat.cell_clients--;
3031 SILC_OPER_STATS_UPDATE(client, server, SILC_UMODE_SERVER_OPERATOR);
3032 SILC_OPER_STATS_UPDATE(client, router, SILC_UMODE_ROUTER_OPERATOR);
3033 silc_schedule_task_del_by_context(server->schedule, client);
3035 if (client->data.sconn) {
3036 silc_server_connection_free(client->data.sconn);
3037 client->data.sconn = NULL;
3040 /* We will not delete the client entry right away. We will take it
3041 into history (for WHOWAS command) for 5 minutes, unless we're
3042 shutting down server. */
3043 if (!server->server_shutdown) {
3044 client->data.status &= ~SILC_IDLIST_STATUS_REGISTERED;
3046 client->router = NULL;
3047 client->connection = NULL;
3048 client->data.created = silc_time();
3049 silc_dlist_add(server->expired_clients, client);
3051 /* Delete directly since we're shutting down server */
3052 SILC_LOG_DEBUG(("Delete client directly"));
3053 silc_idlist_del_data(client);
3054 silc_idlist_del_client(server->local_list, client);
3058 /* Frees user_data pointer from socket connection object. This also sends
3059 appropriate notify packets to the network to inform about leaving
3062 void silc_server_free_sock_user_data(SilcServer server,
3063 SilcPacketStream sock,
3064 const char *signoff_message)
3066 SilcIDListData idata = silc_packet_get_context(sock);
3070 SILC_LOG_DEBUG(("Start, sock %p", sock));
3075 silc_schedule_task_del_by_all(server->schedule, 0, silc_server_do_rekey,
3078 /* Cancel active protocols */
3080 if (idata->sconn && idata->sconn->op) {
3081 SILC_LOG_DEBUG(("Abort active protocol"));
3082 silc_async_abort(idata->sconn->op, NULL, NULL);
3084 if (idata->conn_type == SILC_CONN_UNKNOWN &&
3085 ((SilcUnknownEntry)idata)->op) {
3086 SILC_LOG_DEBUG(("Abort active protocol"));
3087 silc_async_abort(((SilcUnknownEntry)idata)->op, NULL, NULL);
3091 switch (idata->conn_type) {
3092 case SILC_CONN_CLIENT:
3094 SilcClientEntry client_entry = (SilcClientEntry)idata;
3095 silc_server_free_client_data(server, sock, client_entry, TRUE,
3097 silc_packet_set_context(sock, NULL);
3101 case SILC_CONN_SERVER:
3102 case SILC_CONN_ROUTER:
3104 SilcServerEntry user_data = (SilcServerEntry)idata;
3105 SilcServerEntry backup_router = NULL;
3107 SILC_LOG_DEBUG(("Freeing server %p data", user_data));
3110 backup_router = silc_server_backup_get(server, user_data->id);
3112 if (!server->backup_router && server->server_type == SILC_ROUTER &&
3113 backup_router == server->id_entry &&
3114 idata->conn_type != SILC_CONN_ROUTER)
3115 backup_router = NULL;
3117 if (server->server_shutdown || server->backup_noswitch)
3118 backup_router = NULL;
3120 silc_socket_stream_get_info(silc_packet_stream_get_stream(sock),
3121 NULL, NULL, &ip, &port);
3123 /* If this was our primary router connection then we're lost to
3124 the outside world. */
3125 if (server->router == user_data) {
3126 /* Check whether we have a backup router connection */
3127 if (!backup_router || backup_router == user_data) {
3128 if (!server->no_reconnect)
3129 silc_server_create_connections(server);
3130 server->id_entry->router = NULL;
3131 server->router = NULL;
3132 server->standalone = TRUE;
3133 server->backup_primary = FALSE;
3134 backup_router = NULL;
3136 if (server->id_entry != backup_router) {
3137 SILC_LOG_INFO(("New primary router is backup router %s",
3138 backup_router->server_name));
3139 server->id_entry->router = backup_router;
3140 server->router = backup_router;
3141 server->router_connect = time(0);
3142 server->backup_primary = TRUE;
3143 backup_router->data.status &= ~SILC_IDLIST_STATUS_DISABLED;
3145 /* Send START_USE to backup router to indicate we have switched */
3146 silc_server_backup_send_start_use(server,
3147 backup_router->connection,
3150 SILC_LOG_INFO(("We are now new primary router in this cell"));
3151 server->id_entry->router = NULL;
3152 server->router = NULL;
3153 server->standalone = TRUE;
3156 /* We stop here to take a breath */
3159 if (server->backup_router) {
3160 server->server_type = SILC_ROUTER;
3162 /* We'll need to constantly try to reconnect to the primary
3163 router so that we'll see when it comes back online. */
3164 silc_server_create_connection(server, FALSE, FALSE, ip, port,
3165 silc_server_backup_connected,
3169 /* Mark this connection as replaced */
3170 silc_server_backup_replaced_add(server, user_data->id,
3173 } else if (backup_router) {
3174 SILC_LOG_INFO(("Enabling the use of backup router %s",
3175 backup_router->server_name));
3177 /* Mark this connection as replaced */
3178 silc_server_backup_replaced_add(server, user_data->id,
3180 } else if (server->server_type == SILC_SERVER &&
3181 idata->conn_type == SILC_CONN_ROUTER) {
3182 /* Reconnect to the router (backup) */
3183 if (!server->no_reconnect)
3184 silc_server_create_connections(server);
3187 if (user_data->server_name)
3188 SILC_SERVER_SEND_OPERS(server, FALSE, TRUE, SILC_NOTIFY_TYPE_NONE,
3189 ("Server %s signoff", user_data->server_name));
3191 if (!backup_router) {
3192 /* Remove all servers that are originated from this server, and
3193 remove the clients of those servers too. */
3194 silc_server_remove_servers_by_server(server, user_data, TRUE);
3197 /* Remove the clients that this server owns as they will become
3198 invalid now too. For backup router the server is actually
3199 coming from the primary router, so mark that as the owner
3201 if (server->server_type == SILC_BACKUP_ROUTER &&
3202 sock->type == SILC_CONN_SERVER)
3203 silc_server_remove_clients_by_server(server, server->router,
3207 silc_server_remove_clients_by_server(server, user_data,
3210 /* Remove channels owned by this server */
3211 if (server->server_type == SILC_SERVER)
3212 silc_server_remove_channels_by_server(server, user_data);
3214 /* Enable local server connections that may be disabled */
3215 silc_server_local_servers_toggle_enabled(server, TRUE);
3217 /* Update the client entries of this server to the new backup
3218 router. If we are the backup router we also resolve the real
3219 servers for the clients. After updating is over this also
3220 removes the clients that this server explicitly owns. */
3221 silc_server_update_clients_by_server(server, user_data,
3222 backup_router, TRUE);
3224 /* If we are router and just lost our primary router (now standlaone)
3225 we remove everything that was behind it, since we don't know
3227 if (server->server_type == SILC_ROUTER && server->standalone)
3228 /* Remove all servers that are originated from this server, and
3229 remove the clients of those servers too. */
3230 silc_server_remove_servers_by_server(server, user_data, TRUE);
3232 /* Finally remove the clients that are explicitly owned by this
3233 server. They go down with the server. */
3234 silc_server_remove_clients_by_server(server, user_data,
3237 /* Update our server cache to use the new backup router too. */
3238 silc_server_update_servers_by_server(server, user_data, backup_router);
3239 if (server->server_type == SILC_SERVER)
3240 silc_server_update_channels_by_server(server, user_data,
3243 /* Send notify about primary router going down to local operators */
3244 if (server->backup_router)
3245 SILC_SERVER_SEND_OPERS(server, FALSE, TRUE,
3246 SILC_NOTIFY_TYPE_NONE,
3247 ("%s switched to backup router %s "
3248 "(we are primary router now)",
3249 server->server_name, server->server_name));
3250 else if (server->router)
3251 SILC_SERVER_SEND_OPERS(server, FALSE, TRUE,
3252 SILC_NOTIFY_TYPE_NONE,
3253 ("%s switched to backup router %s",
3254 server->server_name,
3255 server->router->server_name));
3257 server->backup_noswitch = FALSE;
3260 silc_server_connection_free(idata->sconn);
3263 if (idata->conn_type == SILC_CONN_SERVER) {
3264 server->stat.my_servers--;
3265 server->stat.servers--;
3266 SILC_LOG_DEBUG(("my_servers %d", server->stat.my_servers));
3267 } else if (idata->conn_type == SILC_CONN_ROUTER) {
3268 server->stat.my_routers--;
3269 server->stat.routers--;
3270 SILC_LOG_DEBUG(("my_routers %d", server->stat.my_routers));
3272 if (server->server_type == SILC_ROUTER)
3273 server->stat.cell_servers--;
3275 /* Free the server entry */
3276 silc_server_backup_del(server, user_data);
3277 silc_server_backup_replaced_del(server, user_data);
3278 silc_idlist_del_data(user_data);
3279 if (!silc_idlist_del_server(server->local_list, user_data))
3280 silc_idlist_del_server(server->global_list, user_data);
3282 if (backup_router && backup_router != server->id_entry) {
3283 /* Announce all of our stuff that was created about 5 minutes ago.
3284 The backup router knows all the other stuff already. */
3285 if (server->server_type == SILC_ROUTER)
3286 silc_server_announce_servers(server, FALSE, time(0) - 300,
3287 backup_router->connection);
3289 /* Announce our clients and channels to the router */
3290 silc_server_announce_clients(server, time(0) - 300,
3291 backup_router->connection);
3292 silc_server_announce_channels(server, time(0) - 300,
3293 backup_router->connection);
3296 silc_packet_set_context(sock, NULL);
3302 SilcUnknownEntry entry = (SilcUnknownEntry)idata;
3304 SILC_LOG_DEBUG(("Freeing unknown connection data %p", entry));
3307 silc_server_connection_free(idata->sconn);
3308 idata->sconn = NULL;
3310 silc_idlist_del_data(idata);
3312 silc_packet_set_context(sock, NULL);
3318 /* Removes client from all channels it has joined. This is used when client
3319 connection is disconnected. If the client on a channel is last, the
3320 channel is removed as well. This sends the SIGNOFF notify types. */
3322 void silc_server_remove_from_channels(SilcServer server,
3323 SilcPacketStream sock,
3324 SilcClientEntry client,
3326 const char *signoff_message,
3330 SilcChannelEntry channel;
3331 SilcChannelClientEntry chl;
3332 SilcHashTableList htl;
3333 SilcBuffer clidp = NULL;
3338 if (notify && !client->id)
3341 SILC_LOG_DEBUG(("Removing client %s from joined channels",
3342 notify ? silc_id_render(client->id, SILC_ID_CLIENT) : ""));
3345 clidp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
3350 /* Remove the client from all channels. The client is removed from
3351 the channels' user list. */
3352 silc_hash_table_list(client->channels, &htl);
3353 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
3354 channel = chl->channel;
3356 /* Remove channel if this is last client leaving the channel, unless
3357 the channel is permanent. */
3358 if (server->server_type != SILC_SERVER &&
3359 silc_hash_table_count(channel->user_list) < 2) {
3360 silc_server_channel_delete(server, channel);
3364 silc_hash_table_del(client->channels, channel);
3365 silc_hash_table_del(channel->user_list, client);
3366 channel->user_count--;
3368 /* If there is no global users on the channel anymore mark the channel
3369 as local channel. Do not check if the removed client is local client. */
3370 if (server->server_type == SILC_SERVER && channel->global_users &&
3371 chl->client->router && !silc_server_channel_has_global(channel))
3372 channel->global_users = FALSE;
3374 memset(chl, 'A', sizeof(*chl));
3377 /* Update statistics */
3378 if (SILC_IS_LOCAL(client))
3379 server->stat.my_chanclients--;
3380 if (server->server_type == SILC_ROUTER) {
3381 server->stat.cell_chanclients--;
3382 server->stat.chanclients--;
3385 /* If there is not at least one local user on the channel then we don't
3386 need the channel entry anymore, we can remove it safely, unless the
3387 channel is permanent channel */
3388 if (server->server_type == SILC_SERVER &&
3389 !silc_server_channel_has_local(channel)) {
3390 /* Notify about leaving client if this channel has global users. */
3391 if (notify && channel->global_users)
3392 silc_server_send_notify_to_channel(server, NULL, channel, FALSE, TRUE,
3393 SILC_NOTIFY_TYPE_SIGNOFF,
3394 signoff_message ? 2 : 1,
3395 clidp->data, silc_buffer_len(clidp),
3396 signoff_message, signoff_message ?
3397 strlen(signoff_message) : 0);
3399 silc_schedule_task_del_by_context(server->schedule, channel->rekey);
3400 silc_server_channel_delete(server, channel);
3404 /* Send notify to channel about client leaving SILC and channel too */
3406 silc_server_send_notify_to_channel(server, NULL, channel, FALSE, TRUE,
3407 SILC_NOTIFY_TYPE_SIGNOFF,
3408 signoff_message ? 2 : 1,
3409 clidp->data, silc_buffer_len(clidp),
3410 signoff_message, signoff_message ?
3411 strlen(signoff_message) : 0);
3413 if (killed && clidp) {
3414 /* Remove the client from channel's invite list */
3415 if (channel->invite_list &&
3416 silc_hash_table_count(channel->invite_list)) {
3418 SilcArgumentPayload iargs;
3419 ab = silc_argument_payload_encode_one(NULL, clidp->data,
3420 silc_buffer_len(clidp), 3);
3421 iargs = silc_argument_payload_parse(ab->data, silc_buffer_len(ab), 1);
3422 silc_server_inviteban_process(server, channel->invite_list, 1, iargs);
3423 silc_buffer_free(ab);
3424 silc_argument_payload_free(iargs);
3428 /* Don't create keys if we are shutting down */
3429 if (server->server_shutdown)
3432 /* Re-generate channel key if needed */
3433 if (keygen && !(channel->mode & SILC_CHANNEL_MODE_PRIVKEY)) {
3434 if (!silc_server_create_channel_key(server, channel, 0))
3437 /* Send the channel key to the channel. The key of course is not sent
3438 to the client who was removed from the channel. */
3439 silc_server_send_channel_key(server, client->connection, channel,
3440 server->server_type == SILC_ROUTER ?
3441 FALSE : !server->standalone);
3445 silc_hash_table_list_reset(&htl);
3447 silc_buffer_free(clidp);
3450 /* Removes client from one channel. This is used for example when client
3451 calls LEAVE command to remove itself from the channel. Returns TRUE
3452 if channel still exists and FALSE if the channel is removed when
3453 last client leaves the channel. If `notify' is FALSE notify messages
3456 SilcBool silc_server_remove_from_one_channel(SilcServer server,
3457 SilcPacketStream sock,
3458 SilcChannelEntry channel,
3459 SilcClientEntry client,
3462 SilcChannelClientEntry chl;
3465 SILC_LOG_DEBUG(("Removing %s from channel %s",
3466 silc_id_render(client->id, SILC_ID_CLIENT),
3467 channel->channel_name));
3469 /* Get the entry to the channel, if this client is not on the channel
3471 if (!silc_hash_table_find(client->channels, channel, NULL, (void *)&chl))
3474 /* Remove channel if this is last client leaving the channel, unless
3475 the channel is permanent. */
3476 if (server->server_type != SILC_SERVER &&
3477 silc_hash_table_count(channel->user_list) < 2) {
3478 silc_server_channel_delete(server, channel);
3482 silc_hash_table_del(client->channels, channel);
3483 silc_hash_table_del(channel->user_list, client);
3484 channel->user_count--;
3486 /* If there is no global users on the channel anymore mark the channel
3487 as local channel. Do not check if the client is local client. */
3488 if (server->server_type == SILC_SERVER && channel->global_users &&
3489 chl->client->router && !silc_server_channel_has_global(channel))
3490 channel->global_users = FALSE;
3492 memset(chl, 'O', sizeof(*chl));
3495 /* Update statistics */
3496 if (SILC_IS_LOCAL(client))
3497 server->stat.my_chanclients--;
3498 if (server->server_type == SILC_ROUTER) {
3499 server->stat.cell_chanclients--;
3500 server->stat.chanclients--;
3503 clidp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
3507 /* If there is not at least one local user on the channel then we don't
3508 need the channel entry anymore, we can remove it safely, unless the
3509 channel is permanent channel */
3510 if (server->server_type == SILC_SERVER &&
3511 !silc_server_channel_has_local(channel)) {
3512 /* Notify about leaving client if this channel has global users. */
3513 if (notify && channel->global_users)
3514 silc_server_send_notify_to_channel(server, NULL, channel, FALSE, TRUE,
3515 SILC_NOTIFY_TYPE_LEAVE, 1,
3516 clidp->data, silc_buffer_len(clidp));
3518 silc_schedule_task_del_by_context(server->schedule, channel->rekey);
3519 silc_server_channel_delete(server, channel);
3520 silc_buffer_free(clidp);
3524 /* Send notify to channel about client leaving the channel */
3526 silc_server_send_notify_to_channel(server, NULL, channel, FALSE, TRUE,
3527 SILC_NOTIFY_TYPE_LEAVE, 1,
3528 clidp->data, silc_buffer_len(clidp));
3530 silc_buffer_free(clidp);
3534 /* Creates new channel. Sends NEW_CHANNEL packet to primary route. This
3535 function may be used only by router. In real SILC network all channels
3536 are created by routers thus this function is never used by normal
3539 SilcChannelEntry silc_server_create_new_channel(SilcServer server,
3540 SilcServerID *router_id,
3546 SilcChannelID *channel_id;
3547 SilcChannelEntry entry;
3548 SilcCipher send_key, receive_key;
3551 SILC_LOG_DEBUG(("Creating new channel %s", channel_name));
3554 cipher = SILC_DEFAULT_CIPHER;
3556 hmac = SILC_DEFAULT_HMAC;
3558 /* Allocate cipher */
3559 if (!silc_cipher_alloc(cipher, &send_key))
3561 if (!silc_cipher_alloc(cipher, &receive_key)) {
3562 silc_cipher_free(send_key);
3567 if (!silc_hmac_alloc(hmac, NULL, &newhmac)) {
3568 silc_cipher_free(send_key);
3569 silc_cipher_free(receive_key);
3573 channel_name = strdup(channel_name);
3575 /* Create the channel ID */
3576 if (!silc_id_create_channel_id(server, router_id, server->rng,
3578 silc_free(channel_name);
3579 silc_cipher_free(send_key);
3580 silc_cipher_free(receive_key);
3581 silc_hmac_free(newhmac);
3585 /* Create the channel */
3586 entry = silc_idlist_add_channel(server->local_list, channel_name,
3587 SILC_CHANNEL_MODE_NONE, channel_id,
3588 NULL, send_key, receive_key, newhmac);
3590 silc_free(channel_name);
3591 silc_cipher_free(send_key);
3592 silc_cipher_free(receive_key);
3593 silc_hmac_free(newhmac);
3594 silc_free(channel_id);
3598 entry->cipher = strdup(cipher);
3599 entry->hmac_name = strdup(hmac);
3601 /* Now create the actual key material */
3602 if (!silc_server_create_channel_key(server, entry,
3603 silc_cipher_get_key_len(send_key) / 8)) {
3604 silc_idlist_del_channel(server->local_list, entry);
3608 /* Notify other routers about the new channel. We send the packet
3609 to our primary route. */
3611 silc_server_send_new_channel(server, SILC_PRIMARY_ROUTE(server), TRUE,
3612 channel_name, entry->id,
3613 silc_id_get_len(entry->id, SILC_ID_CHANNEL),
3616 /* Distribute to backup routers */
3617 if (broadcast && server->server_type == SILC_ROUTER) {
3619 unsigned char cid[32];
3620 SilcUInt32 name_len = strlen(channel_name);
3623 silc_id_id2str(entry->id, SILC_ID_CHANNEL, cid, sizeof(cid), &id_len);
3624 packet = silc_channel_payload_encode(channel_name, name_len,
3625 cid, id_len, entry->mode);
3626 silc_server_backup_send(server, NULL, SILC_PACKET_NEW_CHANNEL, 0,
3627 packet->data, silc_buffer_len(packet), FALSE,
3629 silc_buffer_free(packet);
3632 server->stat.my_channels++;
3633 if (server->server_type == SILC_ROUTER) {
3634 server->stat.channels++;
3635 server->stat.cell_channels++;
3636 entry->users_resolved = TRUE;
3642 /* Same as above but creates the channel with Channel ID `channel_id. */
3645 silc_server_create_new_channel_with_id(SilcServer server,
3649 SilcChannelID *channel_id,
3652 SilcChannelEntry entry;
3653 SilcCipher send_key, receive_key;
3656 SILC_LOG_DEBUG(("Creating new channel %s", channel_name));
3659 cipher = SILC_DEFAULT_CIPHER;
3661 hmac = SILC_DEFAULT_HMAC;
3663 /* Allocate cipher */
3664 if (!silc_cipher_alloc(cipher, &send_key))
3666 if (!silc_cipher_alloc(cipher, &receive_key)) {
3667 silc_cipher_free(send_key);
3672 if (!silc_hmac_alloc(hmac, NULL, &newhmac)) {
3673 silc_cipher_free(send_key);
3674 silc_cipher_free(receive_key);
3678 channel_name = strdup(channel_name);
3680 /* Create the channel */
3681 entry = silc_idlist_add_channel(server->local_list, channel_name,
3682 SILC_CHANNEL_MODE_NONE, channel_id,
3683 NULL, send_key, receive_key, newhmac);
3685 silc_cipher_free(send_key);
3686 silc_cipher_free(receive_key);
3687 silc_hmac_free(newhmac);
3688 silc_free(channel_name);
3692 /* Now create the actual key material */
3693 if (!silc_server_create_channel_key(server, entry,
3694 silc_cipher_get_key_len(send_key) / 8)) {
3695 silc_idlist_del_channel(server->local_list, entry);
3699 /* Notify other routers about the new channel. We send the packet
3700 to our primary route. */
3702 silc_server_send_new_channel(server, SILC_PRIMARY_ROUTE(server), TRUE,
3703 channel_name, entry->id,
3704 silc_id_get_len(entry->id, SILC_ID_CHANNEL),
3707 /* Distribute to backup routers */
3708 if (broadcast && server->server_type == SILC_ROUTER) {
3710 unsigned char cid[32];
3711 SilcUInt32 name_len = strlen(channel_name);
3714 silc_id_id2str(entry->id, SILC_ID_CHANNEL, cid, sizeof(cid), &id_len);
3715 packet = silc_channel_payload_encode(channel_name, name_len,
3716 cid, id_len, entry->mode);
3717 silc_server_backup_send(server, NULL, SILC_PACKET_NEW_CHANNEL, 0,
3718 packet->data, silc_buffer_len(packet), FALSE,
3720 silc_buffer_free(packet);
3723 server->stat.my_channels++;
3724 if (server->server_type == SILC_ROUTER) {
3725 server->stat.channels++;
3726 server->stat.cell_channels++;
3727 entry->users_resolved = TRUE;
3733 /* Channel's key re-key timeout callback. */
3735 SILC_TASK_CALLBACK(silc_server_channel_key_rekey)
3737 SilcServer server = app_context;
3738 SilcServerChannelRekey rekey = (SilcServerChannelRekey)context;
3742 /* Return now if we are shutting down */
3743 if (server->server_shutdown)
3746 if (!silc_server_create_channel_key(server, rekey->channel, rekey->key_len))
3749 silc_server_send_channel_key(server, NULL, rekey->channel, FALSE);
3752 /* Generates new channel key. This is used to create the initial channel key
3753 but also to re-generate new key for channel. If `key_len' is provided
3754 it is the bytes of the key length. */
3756 SilcBool silc_server_create_channel_key(SilcServer server,
3757 SilcChannelEntry channel,
3761 unsigned char channel_key[32], hash[SILC_HASH_MAXLEN];
3764 if (channel->mode & SILC_CHANNEL_MODE_PRIVKEY) {
3765 SILC_LOG_DEBUG(("Channel has private keys, will not generate new key"));
3769 SILC_LOG_DEBUG(("Generating channel %s key", channel->channel_name));
3771 if (!channel->send_key)
3772 if (!silc_cipher_alloc(SILC_DEFAULT_CIPHER, &channel->send_key)) {
3773 channel->send_key = NULL;
3776 if (!channel->receive_key)
3777 if (!silc_cipher_alloc(SILC_DEFAULT_CIPHER, &channel->receive_key)) {
3778 silc_cipher_free(channel->send_key);
3779 channel->send_key = channel->receive_key = NULL;
3785 else if (channel->key_len)
3786 len = channel->key_len / 8;
3788 len = silc_cipher_get_key_len(channel->send_key) / 8;
3790 /* Create channel key */
3791 for (i = 0; i < len; i++) channel_key[i] = silc_rng_get_byte(server->rng);
3794 silc_cipher_set_key(channel->send_key, channel_key, len * 8, TRUE);
3795 silc_cipher_set_key(channel->receive_key, channel_key, len * 8, FALSE);
3797 /* Remove old key if exists */
3799 memset(channel->key, 0, channel->key_len / 8);
3800 silc_free(channel->key);
3804 channel->key_len = len * 8;
3805 channel->key = silc_memdup(channel_key, len);
3806 memset(channel_key, 0, sizeof(channel_key));
3808 /* Generate HMAC key from the channel key data and set it */
3810 if (!silc_hmac_alloc(SILC_DEFAULT_HMAC, NULL, &channel->hmac)) {
3811 memset(channel->key, 0, channel->key_len / 8);
3812 silc_free(channel->key);
3813 silc_cipher_free(channel->send_key);
3814 silc_cipher_free(channel->receive_key);
3815 channel->send_key = channel->receive_key = NULL;
3818 silc_hash_make(silc_hmac_get_hash(channel->hmac), channel->key, len, hash);
3819 silc_hmac_set_key(channel->hmac, hash,
3820 silc_hash_len(silc_hmac_get_hash(channel->hmac)));
3821 memset(hash, 0, sizeof(hash));
3823 if (server->server_type == SILC_ROUTER) {
3824 if (!channel->rekey)
3825 channel->rekey = silc_calloc(1, sizeof(*channel->rekey));
3826 channel->rekey->channel = channel;
3827 channel->rekey->key_len = key_len;
3828 if (channel->rekey->task)
3829 silc_schedule_task_del(server->schedule, channel->rekey->task);
3831 channel->rekey->task =
3832 silc_schedule_task_add_timeout(server->schedule,
3833 silc_server_channel_key_rekey,
3834 (void *)channel->rekey,
3835 server->config->channel_rekey_secs, 0);
3841 /* Saves the channel key found in the encoded `key_payload' buffer. This
3842 function is used when we receive Channel Key Payload and also when we're
3843 processing JOIN command reply. Returns entry to the channel. */
3845 SilcChannelEntry silc_server_save_channel_key(SilcServer server,
3846 SilcBuffer key_payload,
3847 SilcChannelEntry channel)
3849 SilcChannelKeyPayload payload = NULL;
3851 unsigned char *tmp, hash[SILC_HASH_MAXLEN];
3855 /* Decode channel key payload */
3856 payload = silc_channel_key_payload_parse(key_payload->data,
3857 silc_buffer_len(key_payload));
3859 SILC_LOG_ERROR(("Bad channel key payload received, dropped"));
3864 /* Get the channel entry */
3867 /* Get channel ID */
3868 tmp = silc_channel_key_get_id(payload, &tmp_len);
3869 if (!silc_id_str2id(tmp, tmp_len, SILC_ID_CHANNEL, &id, sizeof(id))) {
3874 channel = silc_idlist_find_channel_by_id(server->local_list, &id, NULL);
3876 channel = silc_idlist_find_channel_by_id(server->global_list, &id, NULL);
3878 if (server->server_type == SILC_ROUTER)
3879 SILC_LOG_ERROR(("Received key for non-existent channel %s",
3880 silc_id_render(&id, SILC_ID_CHANNEL)));
3886 SILC_LOG_DEBUG(("Saving new channel %s key", channel->channel_name));
3888 tmp = silc_channel_key_get_key(payload, &tmp_len);
3894 cipher = silc_channel_key_get_cipher(payload, NULL);
3900 /* Remove old key if exists */
3902 memset(channel->key, 0, channel->key_len / 8);
3903 silc_free(channel->key);
3904 silc_cipher_free(channel->send_key);
3905 silc_cipher_free(channel->receive_key);
3908 /* Create new cipher */
3909 if (!silc_cipher_alloc(cipher, &channel->send_key)) {
3910 channel->send_key = NULL;
3914 if (!silc_cipher_alloc(cipher, &channel->receive_key)) {
3915 silc_cipher_free(channel->send_key);
3916 channel->send_key = channel->receive_key = NULL;
3921 if (channel->cipher)
3922 silc_free(channel->cipher);
3923 channel->cipher = strdup(cipher);
3926 channel->key_len = tmp_len * 8;
3927 channel->key = silc_memdup(tmp, tmp_len);
3928 silc_cipher_set_key(channel->send_key, tmp, channel->key_len, TRUE);
3929 silc_cipher_set_key(channel->receive_key, tmp, channel->key_len, FALSE);
3931 /* Generate HMAC key from the channel key data and set it */
3933 if (!silc_hmac_alloc(SILC_DEFAULT_HMAC, NULL, &channel->hmac)) {
3934 memset(channel->key, 0, channel->key_len / 8);
3935 silc_free(channel->key);
3936 silc_cipher_free(channel->send_key);
3937 silc_cipher_free(channel->receive_key);
3938 channel->send_key = channel->receive_key = NULL;
3941 silc_hash_make(silc_hmac_get_hash(channel->hmac), tmp, tmp_len, hash);
3942 silc_hmac_set_key(channel->hmac, hash,
3943 silc_hash_len(silc_hmac_get_hash(channel->hmac)));
3945 memset(hash, 0, sizeof(hash));
3946 memset(tmp, 0, tmp_len);
3948 if (server->server_type == SILC_ROUTER) {
3949 if (!channel->rekey)
3950 channel->rekey = silc_calloc(1, sizeof(*channel->rekey));
3951 channel->rekey->channel = channel;
3952 if (channel->rekey->task)
3953 silc_schedule_task_del(server->schedule, channel->rekey->task);
3955 channel->rekey->task =
3956 silc_schedule_task_add_timeout(server->schedule,
3957 silc_server_channel_key_rekey,
3958 (void *)channel->rekey,
3959 server->config->channel_rekey_secs, 0);
3964 silc_channel_key_payload_free(payload);
3969 /* Returns assembled of all servers in the given ID list. The packet's
3970 form is dictated by the New ID payload. */
3972 static void silc_server_announce_get_servers(SilcServer server,
3973 SilcServerEntry remote,
3975 SilcBuffer *servers,
3976 unsigned long creation_time)
3979 SilcIDCacheEntry id_cache;
3980 SilcServerEntry entry;
3983 /* Go through all clients in the list */
3984 if (silc_idcache_get_all(id_list->servers, &list)) {
3985 silc_list_start(list);
3986 while ((id_cache = silc_list_get(list))) {
3987 entry = (SilcServerEntry)id_cache->context;
3989 /* Do not announce the one we've sending our announcements and
3990 do not announce ourself. Also check the creation time if it's
3992 if ((entry == remote) || (entry == server->id_entry) ||
3993 (creation_time && entry->data.created < creation_time))
3996 idp = silc_id_payload_encode(entry->id, SILC_ID_SERVER);
3998 *servers = silc_buffer_realloc(*servers,
4000 silc_buffer_truelen((*servers)) +
4001 silc_buffer_len(idp) :
4002 silc_buffer_len(idp)));
4003 silc_buffer_pull_tail(*servers, ((*servers)->end - (*servers)->data));
4004 silc_buffer_put(*servers, idp->data, silc_buffer_len(idp));
4005 silc_buffer_pull(*servers, silc_buffer_len(idp));
4006 silc_buffer_free(idp);
4012 silc_server_announce_encode_notify(SilcNotifyType notify, SilcUInt32 argc, ...)
4018 p = silc_notify_payload_encode(notify, argc, ap);
4024 /* This function is used by router to announce existing servers to our
4025 primary router when we've connected to it. If `creation_time' is non-zero
4026 then only the servers that has been created after the `creation_time'
4027 will be announced. */
4029 void silc_server_announce_servers(SilcServer server, SilcBool global,
4030 unsigned long creation_time,
4031 SilcPacketStream remote)
4033 SilcBuffer servers = NULL;
4035 SILC_LOG_DEBUG(("Announcing servers"));
4037 /* Get servers in local list */
4038 silc_server_announce_get_servers(server, silc_packet_get_context(remote),
4039 server->local_list, &servers,
4043 /* Get servers in global list */
4044 silc_server_announce_get_servers(server, silc_packet_get_context(remote),
4045 server->global_list, &servers,
4049 silc_buffer_push(servers, servers->data - servers->head);
4050 SILC_LOG_HEXDUMP(("servers"), servers->data, silc_buffer_len(servers));
4052 /* Send the packet */
4053 silc_server_packet_send(server, remote,
4054 SILC_PACKET_NEW_ID, SILC_PACKET_FLAG_LIST,
4055 servers->data, silc_buffer_len(servers));
4057 silc_buffer_free(servers);
4061 /* Returns assembled packet of all clients in the given ID list. The
4062 packet's form is dictated by the New ID Payload. */
4064 static void silc_server_announce_get_clients(SilcServer server,
4066 SilcBuffer *clients,
4068 unsigned long creation_time)
4071 SilcIDCacheEntry id_cache;
4072 SilcClientEntry client;
4075 unsigned char mode[4];
4077 /* Go through all clients in the list */
4078 if (silc_idcache_get_all(id_list->clients, &list)) {
4079 silc_list_start(list);
4080 while ((id_cache = silc_list_get(list))) {
4081 client = (SilcClientEntry)id_cache->context;
4083 if (creation_time && client->data.created < creation_time)
4085 if (!(client->data.status & SILC_IDLIST_STATUS_REGISTERED))
4087 if (!client->connection && !client->router)
4090 SILC_LOG_DEBUG(("Announce Client ID %s",
4091 silc_id_render(client->id, SILC_ID_CLIENT)));
4093 idp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
4095 *clients = silc_buffer_realloc(*clients,
4097 silc_buffer_truelen((*clients)) +
4098 silc_buffer_len(idp) :
4099 silc_buffer_len(idp)));
4100 silc_buffer_pull_tail(*clients, ((*clients)->end - (*clients)->data));
4101 silc_buffer_put(*clients, idp->data, silc_buffer_len(idp));
4102 silc_buffer_pull(*clients, silc_buffer_len(idp));
4104 SILC_PUT32_MSB(client->mode, mode);
4106 silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_UMODE_CHANGE,
4107 2, idp->data, silc_buffer_len(idp),
4109 *umodes = silc_buffer_realloc(*umodes,
4111 silc_buffer_truelen((*umodes)) +
4112 silc_buffer_len(tmp) :
4113 silc_buffer_len(tmp)));
4114 silc_buffer_pull_tail(*umodes, ((*umodes)->end - (*umodes)->data));
4115 silc_buffer_put(*umodes, tmp->data, silc_buffer_len(tmp));
4116 silc_buffer_pull(*umodes, silc_buffer_len(tmp));
4117 silc_buffer_free(tmp);
4119 silc_buffer_free(idp);
4124 /* This function is used to announce our existing clients to our router
4125 when we've connected to it. If `creation_time' is non-zero then only
4126 the clients that has been created after the `creation_time' will be
4129 void silc_server_announce_clients(SilcServer server,
4130 unsigned long creation_time,
4131 SilcPacketStream remote)
4133 SilcBuffer clients = NULL;
4134 SilcBuffer umodes = NULL;
4136 SILC_LOG_DEBUG(("Announcing clients"));
4138 /* Get clients in local list */
4139 silc_server_announce_get_clients(server, server->local_list,
4140 &clients, &umodes, creation_time);
4142 /* As router we announce our global list as well */
4143 if (server->server_type == SILC_ROUTER)
4144 silc_server_announce_get_clients(server, server->global_list,
4145 &clients, &umodes, creation_time);
4148 silc_buffer_push(clients, clients->data - clients->head);
4149 SILC_LOG_HEXDUMP(("clients"), clients->data, silc_buffer_len(clients));
4151 /* Send the packet */
4152 silc_server_packet_send(server, remote,
4153 SILC_PACKET_NEW_ID, SILC_PACKET_FLAG_LIST,
4154 clients->data, silc_buffer_len(clients));
4156 silc_buffer_free(clients);
4160 silc_buffer_push(umodes, umodes->data - umodes->head);
4161 SILC_LOG_HEXDUMP(("umodes"), umodes->data, silc_buffer_len(umodes));
4163 /* Send the packet */
4164 silc_server_packet_send(server, remote,
4165 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
4166 umodes->data, silc_buffer_len(umodes));
4168 silc_buffer_free(umodes);
4172 /* Returns channel's topic for announcing it */
4174 void silc_server_announce_get_channel_topic(SilcServer server,
4175 SilcChannelEntry channel,
4180 if (channel->topic) {
4181 chidp = silc_id_payload_encode(channel->id, SILC_ID_CHANNEL);
4182 *topic = silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_TOPIC_SET, 2,
4184 silc_buffer_len(chidp),
4186 strlen(channel->topic));
4187 silc_buffer_free(chidp);
4191 /* Returns channel's invite and ban lists */
4193 void silc_server_announce_get_inviteban(SilcServer server,
4194 SilcChannelEntry channel,
4198 SilcBuffer list, idp, idp2, tmp2;
4201 SilcHashTableList htl;
4202 const unsigned char a[1] = { 0x03 };
4204 idp = silc_id_payload_encode((void *)channel->id, SILC_ID_CHANNEL);
4206 /* Encode invite list */
4207 if (channel->invite_list && silc_hash_table_count(channel->invite_list)) {
4208 list = silc_buffer_alloc_size(2);
4209 type = silc_hash_table_count(channel->invite_list);
4210 SILC_PUT16_MSB(type, list->data);
4211 silc_hash_table_list(channel->invite_list, &htl);
4212 while (silc_hash_table_get(&htl, (void *)&ptype, (void *)&tmp2))
4213 list = silc_argument_payload_encode_one(list, tmp2->data,
4214 silc_buffer_len(tmp2),
4215 SILC_PTR_TO_32(ptype));
4216 silc_hash_table_list_reset(&htl);
4218 idp2 = silc_id_payload_encode(server->id, SILC_ID_SERVER);
4220 silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_INVITE, 5,
4221 idp->data, silc_buffer_len(idp),
4222 channel->channel_name,
4223 strlen(channel->channel_name),
4224 idp2->data, silc_buffer_len(idp2),
4226 list->data, silc_buffer_len(list));
4227 silc_buffer_free(idp2);
4228 silc_buffer_free(list);
4231 /* Encode ban list */
4232 if (channel->ban_list && silc_hash_table_count(channel->ban_list)) {
4233 list = silc_buffer_alloc_size(2);
4234 type = silc_hash_table_count(channel->ban_list);
4235 SILC_PUT16_MSB(type, list->data);
4236 silc_hash_table_list(channel->ban_list, &htl);
4237 while (silc_hash_table_get(&htl, (void *)&ptype, (void *)&tmp2))
4238 list = silc_argument_payload_encode_one(list, tmp2->data,
4239 silc_buffer_len(tmp2),
4240 SILC_PTR_TO_32(ptype));
4241 silc_hash_table_list_reset(&htl);
4244 silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_BAN, 3,
4245 idp->data, silc_buffer_len(idp),
4247 list->data, silc_buffer_len(list));
4248 silc_buffer_free(list);
4251 silc_buffer_free(idp);
4254 /* Returns assembled packets for channel users of the `channel'. */
4256 void silc_server_announce_get_channel_users(SilcServer server,
4257 SilcChannelEntry channel,
4258 SilcBuffer *channel_modes,
4259 SilcBuffer *channel_users,
4260 SilcBuffer *channel_users_modes)
4262 SilcChannelClientEntry chl;
4263 SilcHashTableList htl;
4264 SilcBuffer chidp, clidp, csidp;
4265 SilcBuffer tmp, fkey = NULL, chpklist;
4267 unsigned char mode[4], ulimit[4];
4270 SILC_LOG_DEBUG(("Start"));
4272 chidp = silc_id_payload_encode(channel->id, SILC_ID_CHANNEL);
4273 csidp = silc_id_payload_encode(server->id, SILC_ID_SERVER);
4274 chpklist = silc_server_get_channel_pk_list(server, channel, TRUE, FALSE);
4277 SILC_PUT32_MSB(channel->mode, mode);
4278 if (channel->mode & SILC_CHANNEL_MODE_ULIMIT)
4279 SILC_PUT32_MSB(channel->user_limit, ulimit);
4280 hmac = channel->hmac ? (char *)silc_hmac_get_name(channel->hmac) : NULL;
4281 if (channel->founder_key)
4282 fkey = silc_public_key_payload_encode(channel->founder_key);
4284 silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_CMODE_CHANGE,
4286 silc_buffer_len(csidp),
4289 hmac, hmac ? strlen(hmac) : 0,
4290 channel->passphrase,
4291 channel->passphrase ?
4292 strlen(channel->passphrase) : 0,
4293 fkey ? fkey->data : NULL,
4294 fkey ? silc_buffer_len(fkey) : 0,
4295 chpklist ? chpklist->data : NULL,
4297 silc_buffer_len(chpklist) : 0,
4299 SILC_CHANNEL_MODE_ULIMIT ?
4302 SILC_CHANNEL_MODE_ULIMIT ?
4303 sizeof(ulimit) : 0));
4304 len = silc_buffer_len(tmp);
4306 silc_buffer_realloc(*channel_modes,
4308 silc_buffer_truelen((*channel_modes)) + len : len));
4309 silc_buffer_pull_tail(*channel_modes,
4310 ((*channel_modes)->end -
4311 (*channel_modes)->data));
4312 silc_buffer_put(*channel_modes, tmp->data, silc_buffer_len(tmp));
4313 silc_buffer_pull(*channel_modes, len);
4314 silc_buffer_free(tmp);
4315 silc_buffer_free(fkey);
4318 /* Now find all users on the channel */
4319 silc_hash_table_list(channel->user_list, &htl);
4320 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
4321 clidp = silc_id_payload_encode(chl->client->id, SILC_ID_CLIENT);
4323 SILC_LOG_DEBUG(("JOIN Client %s", silc_id_render(chl->client->id,
4327 tmp = silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_JOIN, 2,
4329 silc_buffer_len(clidp),
4331 silc_buffer_len(chidp));
4332 len = silc_buffer_len(tmp);
4334 silc_buffer_realloc(*channel_users,
4336 silc_buffer_truelen((*channel_users)) + len : len));
4337 silc_buffer_pull_tail(*channel_users,
4338 ((*channel_users)->end -
4339 (*channel_users)->data));
4341 silc_buffer_put(*channel_users, tmp->data, silc_buffer_len(tmp));
4342 silc_buffer_pull(*channel_users, len);
4343 silc_buffer_free(tmp);
4345 /* CUMODE notify for mode change on the channel */
4346 SILC_PUT32_MSB(chl->mode, mode);
4347 if (chl->mode & SILC_CHANNEL_UMODE_CHANFO && channel->founder_key)
4348 fkey = silc_public_key_payload_encode(channel->founder_key);
4349 tmp = silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_CUMODE_CHANGE,
4351 silc_buffer_len(csidp),
4354 silc_buffer_len(clidp),
4355 fkey ? fkey->data : NULL,
4356 fkey ? silc_buffer_len(fkey) : 0);
4357 len = silc_buffer_len(tmp);
4358 *channel_users_modes =
4359 silc_buffer_realloc(*channel_users_modes,
4360 (*channel_users_modes ?
4361 silc_buffer_truelen((*channel_users_modes)) +
4363 silc_buffer_pull_tail(*channel_users_modes,
4364 ((*channel_users_modes)->end -
4365 (*channel_users_modes)->data));
4367 silc_buffer_put(*channel_users_modes, tmp->data, silc_buffer_len(tmp));
4368 silc_buffer_pull(*channel_users_modes, len);
4369 silc_buffer_free(tmp);
4370 silc_buffer_free(fkey);
4372 silc_buffer_free(clidp);
4374 silc_hash_table_list_reset(&htl);
4375 silc_buffer_free(chidp);
4376 silc_buffer_free(csidp);
4379 /* Returns assembled packets for all channels and users on those channels
4380 from the given ID List. The packets are in the form dictated by the
4381 New Channel and New Channel User payloads. */
4383 void silc_server_announce_get_channels(SilcServer server,
4385 SilcBuffer *channels,
4386 SilcBuffer **channel_modes,
4387 SilcBuffer *channel_users,
4388 SilcBuffer **channel_users_modes,
4389 SilcUInt32 *channel_users_modes_c,
4390 SilcBuffer **channel_topics,
4391 SilcBuffer **channel_invites,
4392 SilcBuffer **channel_bans,
4393 SilcChannelID ***channel_ids,
4394 unsigned long creation_time)
4397 SilcIDCacheEntry id_cache;
4398 SilcChannelEntry channel;
4399 unsigned char cid[32];
4401 SilcUInt16 name_len;
4403 int i = *channel_users_modes_c;
4406 SILC_LOG_DEBUG(("Start"));
4408 /* Go through all channels in the list */
4409 if (silc_idcache_get_all(id_list->channels, &list)) {
4410 silc_list_start(list);
4411 while ((id_cache = silc_list_get(list))) {
4412 channel = (SilcChannelEntry)id_cache->context;
4414 if (creation_time && channel->created < creation_time)
4419 SILC_LOG_DEBUG(("Announce Channel ID %s",
4420 silc_id_render(channel->id, SILC_ID_CHANNEL)));
4422 silc_id_id2str(channel->id, SILC_ID_CHANNEL, cid, sizeof(cid), &id_len);
4423 name_len = strlen(channel->channel_name);
4426 len = 4 + name_len + id_len + 4;
4428 silc_buffer_realloc(*channels,
4430 silc_buffer_truelen((*channels)) +
4432 silc_buffer_pull_tail(*channels,
4433 ((*channels)->end - (*channels)->data));
4434 silc_buffer_format(*channels,
4435 SILC_STR_UI_SHORT(name_len),
4436 SILC_STR_UI_XNSTRING(channel->channel_name,
4438 SILC_STR_UI_SHORT(id_len),
4439 SILC_STR_UI_XNSTRING(cid, id_len),
4440 SILC_STR_UI_INT(channel->mode),
4442 silc_buffer_pull(*channels, len);
4445 if (creation_time && channel->updated < creation_time)
4451 /* Channel user modes */
4452 *channel_users_modes = silc_realloc(*channel_users_modes,
4453 sizeof(**channel_users_modes) *
4455 (*channel_users_modes)[i] = NULL;
4456 *channel_modes = silc_realloc(*channel_modes,
4457 sizeof(**channel_modes) * (i + 1));
4458 (*channel_modes)[i] = NULL;
4459 *channel_ids = silc_realloc(*channel_ids,
4460 sizeof(**channel_ids) * (i + 1));
4461 (*channel_ids)[i] = NULL;
4462 silc_server_announce_get_channel_users(server, channel,
4463 &(*channel_modes)[i],
4465 &(*channel_users_modes)[i]);
4466 (*channel_ids)[i] = channel->id;
4468 /* Channel's topic */
4469 *channel_topics = silc_realloc(*channel_topics,
4470 sizeof(**channel_topics) * (i + 1));
4471 (*channel_topics)[i] = NULL;
4472 silc_server_announce_get_channel_topic(server, channel,
4473 &(*channel_topics)[i]);
4475 /* Channel's invite and ban list */
4476 *channel_invites = silc_realloc(*channel_invites,
4477 sizeof(**channel_invites) * (i + 1));
4478 (*channel_invites)[i] = NULL;
4479 *channel_bans = silc_realloc(*channel_bans,
4480 sizeof(**channel_bans) * (i + 1));
4481 (*channel_bans)[i] = NULL;
4482 silc_server_announce_get_inviteban(server, channel,
4483 &(*channel_invites)[i],
4484 &(*channel_bans)[i]);
4486 (*channel_users_modes_c)++;
4494 /* This function is used to announce our existing channels to our router
4495 when we've connected to it. This also announces the users on the
4496 channels to the router. If the `creation_time' is non-zero only the
4497 channels that was created after the `creation_time' are announced.
4498 Note that the channel users are still announced even if the `creation_time'
4501 void silc_server_announce_channels(SilcServer server,
4502 unsigned long creation_time,
4503 SilcPacketStream remote)
4505 SilcBuffer channels = NULL, *channel_modes = NULL, channel_users = NULL;
4506 SilcBuffer *channel_users_modes = NULL;
4507 SilcBuffer *channel_topics = NULL;
4508 SilcBuffer *channel_invites = NULL;
4509 SilcBuffer *channel_bans = NULL;
4510 SilcUInt32 channel_users_modes_c = 0;
4511 SilcChannelID **channel_ids = NULL;
4513 SILC_LOG_DEBUG(("Announcing channels and channel users"));
4515 /* Get channels and channel users in local list */
4516 silc_server_announce_get_channels(server, server->local_list,
4517 &channels, &channel_modes,
4519 &channel_users_modes,
4520 &channel_users_modes_c,
4524 &channel_ids, creation_time);
4526 /* Get channels and channel users in global list */
4527 if (server->server_type != SILC_SERVER)
4528 silc_server_announce_get_channels(server, server->global_list,
4529 &channels, &channel_modes,
4531 &channel_users_modes,
4532 &channel_users_modes_c,
4536 &channel_ids, creation_time);
4539 silc_buffer_push(channels, channels->data - channels->head);
4540 SILC_LOG_HEXDUMP(("channels"), channels->data, silc_buffer_len(channels));
4542 /* Send the packet */
4543 silc_server_packet_send(server, remote,
4544 SILC_PACKET_NEW_CHANNEL, SILC_PACKET_FLAG_LIST,
4545 channels->data, silc_buffer_len(channels));
4547 silc_buffer_free(channels);
4550 if (channel_users) {
4551 silc_buffer_push(channel_users, channel_users->data - channel_users->head);
4552 SILC_LOG_HEXDUMP(("channel users"), channel_users->data,
4553 silc_buffer_len(channel_users));
4555 /* Send the packet */
4556 silc_server_packet_send(server, remote,
4557 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
4558 channel_users->data, silc_buffer_len(channel_users));
4560 silc_buffer_free(channel_users);
4563 if (channel_modes) {
4566 for (i = 0; i < channel_users_modes_c; i++) {
4567 if (!channel_modes[i])
4569 silc_buffer_push(channel_modes[i],
4570 channel_modes[i]->data -
4571 channel_modes[i]->head);
4572 SILC_LOG_HEXDUMP(("channel modes"), channel_modes[i]->data,
4573 silc_buffer_len(channel_modes[i]));
4574 silc_server_packet_send_dest(server, remote,
4575 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
4576 channel_ids[i], SILC_ID_CHANNEL,
4577 channel_modes[i]->data,
4578 silc_buffer_len(channel_modes[i]));
4579 silc_buffer_free(channel_modes[i]);
4581 silc_free(channel_modes);
4584 if (channel_users_modes) {
4587 for (i = 0; i < channel_users_modes_c; i++) {
4588 if (!channel_users_modes[i])
4590 silc_buffer_push(channel_users_modes[i],
4591 channel_users_modes[i]->data -
4592 channel_users_modes[i]->head);
4593 SILC_LOG_HEXDUMP(("channel users modes"), channel_users_modes[i]->data,
4594 silc_buffer_len(channel_users_modes[i]));
4595 silc_server_packet_send_dest(server, remote,
4596 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
4597 channel_ids[i], SILC_ID_CHANNEL,
4598 channel_users_modes[i]->data,
4599 silc_buffer_len(channel_users_modes[i]));
4600 silc_buffer_free(channel_users_modes[i]);
4602 silc_free(channel_users_modes);
4605 if (channel_topics) {
4608 for (i = 0; i < channel_users_modes_c; i++) {
4609 if (!channel_topics[i])
4612 silc_buffer_push(channel_topics[i],
4613 channel_topics[i]->data -
4614 channel_topics[i]->head);
4615 SILC_LOG_HEXDUMP(("channel topic"), channel_topics[i]->data,
4616 silc_buffer_len(channel_topics[i]));
4617 silc_server_packet_send_dest(server, remote,
4618 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
4619 channel_ids[i], SILC_ID_CHANNEL,
4620 channel_topics[i]->data,
4621 silc_buffer_len(channel_topics[i]));
4622 silc_buffer_free(channel_topics[i]);
4624 silc_free(channel_topics);
4627 if (channel_invites) {
4630 for (i = 0; i < channel_users_modes_c; i++) {
4631 if (!channel_invites[i])
4634 silc_buffer_push(channel_invites[i],
4635 channel_invites[i]->data -
4636 channel_invites[i]->head);
4637 SILC_LOG_HEXDUMP(("channel invite list"), channel_invites[i]->data,
4638 silc_buffer_len(channel_invites[i]));
4639 silc_server_packet_send_dest(server, remote,
4640 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
4641 channel_ids[i], SILC_ID_CHANNEL,
4642 channel_invites[i]->data,
4643 silc_buffer_len(channel_invites[i]));
4644 silc_buffer_free(channel_invites[i]);
4646 silc_free(channel_invites);
4652 for (i = 0; i < channel_users_modes_c; i++) {
4653 if (!channel_bans[i])
4656 silc_buffer_push(channel_bans[i],
4657 channel_bans[i]->data -
4658 channel_bans[i]->head);
4659 SILC_LOG_HEXDUMP(("channel ban list"), channel_bans[i]->data,
4660 silc_buffer_len(channel_bans[i]));
4661 silc_server_packet_send_dest(server, remote,
4662 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
4663 channel_ids[i], SILC_ID_CHANNEL,
4664 channel_bans[i]->data,
4665 silc_buffer_len(channel_bans[i]));
4666 silc_buffer_free(channel_bans[i]);
4668 silc_free(channel_bans);
4671 silc_free(channel_ids);
4674 /* Announces WATCH list. */
4676 void silc_server_announce_watches(SilcServer server,
4677 SilcPacketStream remote)
4679 SilcHashTableList htl;
4680 SilcBuffer buffer, idp, args, pkp;
4681 SilcClientEntry client;
4684 SILC_LOG_DEBUG(("Announcing watch list"));
4686 /* XXX because way we save the nicks (hash) we cannot announce them. */
4688 /* XXX we should send all public keys in one command if client is
4689 watching more than one key */
4690 silc_hash_table_list(server->watcher_list_pk, &htl);
4691 while (silc_hash_table_get(&htl, &key, (void *)&client)) {
4692 if (!client || !client->id)
4695 server->stat.commands_sent++;
4697 idp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
4698 args = silc_buffer_alloc_size(2);
4699 silc_buffer_format(args,
4700 SILC_STR_UI_SHORT(1),
4702 pkp = silc_public_key_payload_encode(key);
4703 args = silc_argument_payload_encode_one(args, pkp->data,
4704 silc_buffer_len(pkp), 0x00);
4705 buffer = silc_command_payload_encode_va(SILC_COMMAND_WATCH,
4706 ++server->cmd_ident, 2,
4707 1, idp->data, silc_buffer_len(idp),
4709 silc_buffer_len(args));
4712 silc_server_packet_send(server, remote, SILC_PACKET_COMMAND, 0,
4713 buffer->data, silc_buffer_len(buffer));
4715 silc_buffer_free(pkp);
4716 silc_buffer_free(args);
4717 silc_buffer_free(idp);
4718 silc_buffer_free(buffer);
4720 silc_hash_table_list_reset(&htl);
4723 /* Assembles user list and users mode list from the `channel'. */
4725 SilcBool silc_server_get_users_on_channel(SilcServer server,
4726 SilcChannelEntry channel,
4727 SilcBuffer *user_list,
4728 SilcBuffer *mode_list,
4729 SilcUInt32 *user_count)
4731 SilcChannelClientEntry chl;
4732 SilcHashTableList htl;
4733 SilcBuffer client_id_list;
4734 SilcBuffer client_mode_list;
4736 SilcUInt32 list_count = 0, len = 0;
4738 if (!silc_hash_table_count(channel->user_list))
4741 silc_hash_table_list(channel->user_list, &htl);
4742 while (silc_hash_table_get(&htl, NULL, (void *)&chl))
4743 len += (silc_id_get_len(chl->client->id, SILC_ID_CLIENT) + 4);
4744 silc_hash_table_list_reset(&htl);
4746 client_id_list = silc_buffer_alloc(len);
4748 silc_buffer_alloc(4 * silc_hash_table_count(channel->user_list));
4749 silc_buffer_pull_tail(client_id_list, silc_buffer_truelen(client_id_list));
4750 silc_buffer_pull_tail(client_mode_list,
4751 silc_buffer_truelen(client_mode_list));
4753 silc_hash_table_list(channel->user_list, &htl);
4754 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
4756 idp = silc_id_payload_encode(chl->client->id, SILC_ID_CLIENT);
4757 silc_buffer_put(client_id_list, idp->data, silc_buffer_len(idp));
4758 silc_buffer_pull(client_id_list, silc_buffer_len(idp));
4759 silc_buffer_free(idp);
4761 /* Client's mode on channel */
4762 SILC_PUT32_MSB(chl->mode, client_mode_list->data);
4763 silc_buffer_pull(client_mode_list, 4);
4767 silc_hash_table_list_reset(&htl);
4768 silc_buffer_push(client_id_list,
4769 client_id_list->data - client_id_list->head);
4770 silc_buffer_push(client_mode_list,
4771 client_mode_list->data - client_mode_list->head);
4773 *user_list = client_id_list;
4774 *mode_list = client_mode_list;
4775 *user_count = list_count;
4779 /* Saves users and their modes to the `channel'. */
4781 void silc_server_save_users_on_channel(SilcServer server,
4782 SilcPacketStream sock,
4783 SilcChannelEntry channel,
4784 SilcClientID *noadd,
4785 SilcBuffer user_list,
4786 SilcBuffer mode_list,
4787 SilcUInt32 user_count)
4793 SilcClientEntry client;
4794 SilcIDCacheEntry cache;
4795 SilcChannelClientEntry chl;
4797 SILC_LOG_DEBUG(("Saving %d users on %s channel", user_count,
4798 channel->channel_name));
4800 for (i = 0; i < user_count; i++) {
4802 SILC_GET16_MSB(idp_len, user_list->data + 2);
4804 if (!silc_id_payload_parse_id(user_list->data, idp_len, &id))
4806 silc_buffer_pull(user_list, idp_len);
4809 SILC_GET32_MSB(mode, mode_list->data);
4810 silc_buffer_pull(mode_list, 4);
4812 if (noadd && SILC_ID_CLIENT_COMPARE(&id.u.client_id, noadd))
4817 /* Check if we have this client cached already. */
4818 client = silc_idlist_find_client_by_id(server->local_list,
4820 server->server_type, &cache);
4822 client = silc_idlist_find_client_by_id(server->global_list,
4824 server->server_type, &cache);
4826 /* If router did not find such Client ID in its lists then this must
4827 be bogus client or some router in the net is buggy. */
4828 if (server->server_type != SILC_SERVER)
4831 /* We don't have that client anywhere, add it. The client is added
4832 to global list since server didn't have it in the lists so it must be
4834 client = silc_idlist_add_client(server->global_list, NULL, NULL, NULL,
4835 silc_id_dup(&id.u.client_id,
4837 silc_packet_get_context(sock),
4840 SILC_LOG_ERROR(("Could not add new client to the ID Cache"));
4844 client->data.status |= SILC_IDLIST_STATUS_REGISTERED;
4847 if (!(client->data.status & SILC_IDLIST_STATUS_REGISTERED)) {
4848 SILC_LOG_ERROR(("Attempting to add unregistered client to channel ",
4849 "%s", channel->channel_name));
4853 if (!silc_server_client_on_channel(client, channel, &chl)) {
4854 /* Client was not on the channel, add it. */
4855 chl = silc_calloc(1, sizeof(*chl));
4856 chl->client = client;
4858 chl->channel = channel;
4859 silc_hash_table_add(channel->user_list, chl->client, chl);
4860 silc_hash_table_add(client->channels, chl->channel, chl);
4861 channel->user_count++;
4869 /* Saves channels and channels user modes to the `client'. Removes
4870 the client from those channels that are not sent in the list but
4873 void silc_server_save_user_channels(SilcServer server,
4874 SilcPacketStream sock,
4875 SilcClientEntry client,
4876 SilcBuffer channels,
4877 SilcBuffer channels_user_modes)
4880 SilcUInt32 *chumodes;
4881 SilcChannelPayload entry;
4882 SilcChannelEntry channel;
4883 SilcChannelID channel_id;
4884 SilcChannelClientEntry chl;
4885 SilcHashTable ht = NULL;
4886 SilcHashTableList htl;
4890 if (!channels || !channels_user_modes ||
4891 !(client->data.status & SILC_IDLIST_STATUS_REGISTERED))
4894 ch = silc_channel_payload_parse_list(channels->data,
4895 silc_buffer_len(channels));
4896 if (ch && silc_get_mode_list(channels_user_modes, silc_dlist_count(ch),
4898 ht = silc_hash_table_alloc(0, silc_hash_ptr, NULL, NULL,
4899 NULL, NULL, NULL, TRUE);
4900 silc_dlist_start(ch);
4901 while ((entry = silc_dlist_get(ch)) != SILC_LIST_END) {
4902 /* Check if we have this channel, and add it if we don't have it.
4903 Also add the client on the channel unless it is there already. */
4904 if (!silc_channel_get_id_parse(entry, &channel_id))
4906 channel = silc_idlist_find_channel_by_id(server->local_list,
4909 channel = silc_idlist_find_channel_by_id(server->global_list,
4912 if (server->server_type != SILC_SERVER) {
4917 /* We don't have that channel anywhere, add it. */
4918 name = silc_channel_get_name(entry, NULL);
4919 channel = silc_idlist_add_channel(server->global_list, strdup(name), 0,
4920 silc_id_dup(&channel_id,
4922 server->router, NULL, NULL, 0);
4929 channel->mode = silc_channel_get_mode(entry);
4931 /* Add the client on the channel */
4932 if (!silc_server_client_on_channel(client, channel, &chl)) {
4933 chl = silc_calloc(1, sizeof(*chl));
4934 chl->client = client;
4935 chl->mode = chumodes[i++];
4936 chl->channel = channel;
4937 silc_hash_table_add(channel->user_list, chl->client, chl);
4938 silc_hash_table_add(client->channels, chl->channel, chl);
4939 channel->user_count++;
4942 chl->mode = chumodes[i++];
4945 silc_hash_table_add(ht, channel, channel);
4947 silc_channel_payload_list_free(ch);
4948 silc_free(chumodes);
4952 /* Go through the list again and remove client from channels that
4953 are no part of the list. */
4955 silc_hash_table_list(client->channels, &htl);
4956 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
4957 if (!silc_hash_table_find(ht, chl->channel, NULL, NULL)) {
4958 silc_hash_table_del(chl->channel->user_list, chl->client);
4959 silc_hash_table_del(chl->client->channels, chl->channel);
4963 silc_hash_table_list_reset(&htl);
4964 silc_hash_table_free(ht);
4966 silc_hash_table_list(client->channels, &htl);
4967 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
4968 silc_hash_table_del(chl->channel->user_list, chl->client);
4969 silc_hash_table_del(chl->client->channels, chl->channel);
4972 silc_hash_table_list_reset(&htl);
4976 /* Lookups route to the client indicated by the `id_data'. The connection
4977 object and internal data object is returned. Returns NULL if route
4978 could not be found to the client. If the `client_id' is specified then
4979 it is used and the `id_data' is ignored. */
4982 silc_server_get_client_route(SilcServer server,
4983 unsigned char *id_data,
4985 SilcClientID *client_id,
4986 SilcIDListData *idata,
4987 SilcClientEntry *client_entry)
4989 SilcClientID *id, clid;
4990 SilcClientEntry client;
4992 SILC_LOG_DEBUG(("Start"));
4995 *client_entry = NULL;
4997 /* Decode destination Client ID */
4999 if (!silc_id_str2id(id_data, id_len, SILC_ID_CLIENT, &clid, sizeof(clid)))
5001 id = silc_id_dup(&clid, SILC_ID_CLIENT);
5003 id = silc_id_dup(client_id, SILC_ID_CLIENT);
5006 /* If the destination belongs to our server we don't have to route
5007 the packet anywhere but to send it to the local destination. */
5008 client = silc_idlist_find_client_by_id(server->local_list, id, TRUE, NULL);
5012 /* If we are router and the client has router then the client is in
5013 our cell but not directly connected to us. */
5014 if (server->server_type == SILC_ROUTER && client->router) {
5015 /* We are of course in this case the client's router thus the route
5016 to the client is the server who owns the client. So, we will send
5017 the packet to that server. */
5019 *idata = (SilcIDListData)client->router;
5020 return client->router->connection;
5023 /* Seems that client really is directly connected to us */
5025 *idata = (SilcIDListData)client;
5027 *client_entry = client;
5028 return client->connection;
5031 /* Destination belongs to someone not in this server. If we are normal
5032 server our action is to send the packet to our router. */
5033 if (server->server_type != SILC_ROUTER && !server->standalone) {
5036 *idata = (SilcIDListData)server->router;
5037 return SILC_PRIMARY_ROUTE(server);
5040 /* We are router and we will perform route lookup for the destination
5041 and send the packet to fastest route. */
5042 if (server->server_type == SILC_ROUTER && !server->standalone) {
5043 /* Check first that the ID is valid */
5044 client = silc_idlist_find_client_by_id(server->global_list, id,
5047 SilcPacketStream dst_sock;
5049 dst_sock = silc_server_route_get(server, id, SILC_ID_CLIENT);
5052 if (idata && dst_sock)
5053 *idata = silc_packet_get_context(dst_sock);
5062 /* Encodes and returns channel list of channels the `client' has joined.
5063 Secret channels are not put to the list. */
5065 SilcBuffer silc_server_get_client_channel_list(SilcServer server,
5066 SilcClientEntry client,
5067 SilcBool get_private,
5068 SilcBool get_secret,
5069 SilcBuffer *user_mode_list)
5071 SilcBuffer buffer = NULL;
5072 SilcChannelEntry channel;
5073 SilcChannelClientEntry chl;
5074 SilcHashTableList htl;
5075 unsigned char cid[32];
5077 SilcUInt16 name_len;
5081 *user_mode_list = NULL;
5083 silc_hash_table_list(client->channels, &htl);
5084 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
5085 channel = chl->channel;
5087 if (channel->mode & SILC_CHANNEL_MODE_SECRET && !get_secret)
5089 if (channel->mode & SILC_CHANNEL_MODE_PRIVATE && !get_private)
5092 silc_id_id2str(channel->id, SILC_ID_CHANNEL, cid, sizeof(cid), &id_len);
5093 name_len = strlen(channel->channel_name);
5095 len = 4 + name_len + id_len + 4;
5096 buffer = silc_buffer_realloc(buffer,
5098 silc_buffer_truelen(buffer) + len : len));
5099 silc_buffer_pull_tail(buffer, (buffer->end - buffer->data));
5100 silc_buffer_format(buffer,
5101 SILC_STR_UI_SHORT(name_len),
5102 SILC_STR_DATA(channel->channel_name, name_len),
5103 SILC_STR_UI_SHORT(id_len),
5104 SILC_STR_DATA(cid, id_len),
5105 SILC_STR_UI_INT(chl->channel->mode),
5107 silc_buffer_pull(buffer, len);
5109 if (user_mode_list) {
5111 silc_buffer_realloc(*user_mode_list,
5113 silc_buffer_truelen((*user_mode_list)) + 4 : 4));
5114 silc_buffer_pull_tail(*user_mode_list, ((*user_mode_list)->end -
5115 (*user_mode_list)->data));
5116 SILC_PUT32_MSB(chl->mode, (*user_mode_list)->data);
5117 silc_buffer_pull(*user_mode_list, 4);
5120 silc_hash_table_list_reset(&htl);
5123 silc_buffer_push(buffer, buffer->data - buffer->head);
5124 if (user_mode_list && *user_mode_list)
5125 silc_buffer_push(*user_mode_list, ((*user_mode_list)->data -
5126 (*user_mode_list)->head));
5131 /* Task callback used to retrieve network statistical information from
5132 router server once in a while. */
5134 SILC_TASK_CALLBACK(silc_server_get_stats)
5136 SilcServer server = (SilcServer)context;
5137 SilcBuffer idp, packet;
5139 if (!server->standalone) {
5140 SILC_LOG_DEBUG(("Retrieving stats from router"));
5141 server->stat.commands_sent++;
5142 idp = silc_id_payload_encode(server->router->id, SILC_ID_SERVER);
5144 packet = silc_command_payload_encode_va(SILC_COMMAND_STATS,
5145 ++server->cmd_ident, 1,
5147 silc_buffer_len(idp));
5148 silc_server_packet_send(server, SILC_PRIMARY_ROUTE(server),
5149 SILC_PACKET_COMMAND, 0, packet->data,
5150 silc_buffer_len(packet));
5151 silc_buffer_free(packet);
5152 silc_buffer_free(idp);
5156 silc_schedule_task_add_timeout(server->schedule, silc_server_get_stats,