5 Author: Pekka Riikonen <priikone@silcnet.org>
7 Copyright (C) 1997 - 2002 Pekka Riikonen
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
21 * This is the actual SILC server than handles everything relating to
22 * servicing the SILC connections. This is also a SILC router as a router
23 * is also normal server.
27 #include "serverincludes.h"
28 #include "server_internal.h"
30 /* Static prototypes */
31 SILC_TASK_CALLBACK(silc_server_connect_to_router_retry);
32 SILC_TASK_CALLBACK(silc_server_connect_router);
33 SILC_TASK_CALLBACK(silc_server_connect_to_router);
34 SILC_TASK_CALLBACK(silc_server_connect_to_router_second);
35 SILC_TASK_CALLBACK(silc_server_connect_to_router_final);
36 SILC_TASK_CALLBACK(silc_server_accept_new_connection);
37 SILC_TASK_CALLBACK(silc_server_accept_new_connection_second);
38 SILC_TASK_CALLBACK(silc_server_accept_new_connection_final);
39 SILC_TASK_CALLBACK(silc_server_packet_process);
40 SILC_TASK_CALLBACK(silc_server_packet_parse_real);
41 SILC_TASK_CALLBACK(silc_server_close_connection_final);
42 SILC_TASK_CALLBACK(silc_server_free_client_data_timeout);
43 SILC_TASK_CALLBACK(silc_server_timeout_remote);
44 SILC_TASK_CALLBACK(silc_server_channel_key_rekey);
45 SILC_TASK_CALLBACK(silc_server_failure_callback);
46 SILC_TASK_CALLBACK(silc_server_rekey_callback);
47 SILC_TASK_CALLBACK(silc_server_get_stats);
49 /* Allocates a new SILC server object. This has to be done before the server
50 can be used. After allocation one must call silc_server_init to initialize
51 the server. The new allocated server object is returned to the new_server
54 int silc_server_alloc(SilcServer *new_server)
58 SILC_LOG_DEBUG(("Allocating new server object"));
60 server = silc_calloc(1, sizeof(*server));
61 server->server_type = SILC_SERVER;
62 server->standalone = TRUE;
63 server->local_list = silc_calloc(1, sizeof(*server->local_list));
64 server->global_list = silc_calloc(1, sizeof(*server->global_list));
65 server->pending_commands = silc_dlist_init();
67 server->sim = silc_dlist_init();
75 /* Free's the SILC server object. This is called at the very end before
78 void silc_server_free(SilcServer server)
84 while ((sim = silc_dlist_get(server->sim)) != SILC_LIST_END) {
85 silc_dlist_del(server->sim, sim);
88 silc_dlist_uninit(server->sim);
91 silc_server_config_unref(&server->config_ref);
93 silc_rng_free(server->rng);
95 silc_pkcs_free(server->pkcs);
96 if (server->public_key)
97 silc_pkcs_public_key_free(server->public_key);
98 if (server->private_key)
99 silc_pkcs_private_key_free(server->private_key);
100 if (server->pending_commands)
101 silc_dlist_uninit(server->pending_commands);
102 if (server->id_entry)
103 silc_idlist_del_server(server->local_list, server->id_entry);
105 silc_idcache_free(server->local_list->clients);
106 silc_idcache_free(server->local_list->servers);
107 silc_idcache_free(server->local_list->channels);
108 silc_idcache_free(server->global_list->clients);
109 silc_idcache_free(server->global_list->servers);
110 silc_idcache_free(server->global_list->channels);
111 silc_hash_table_free(server->watcher_list);
113 silc_free(server->sockets);
118 /* Opens a listening port.
119 XXX This function will become more general and will support multiple
122 static bool silc_server_listen(SilcServer server, const char *server_ip,
123 SilcUInt16 port, int *sock)
125 *sock = silc_net_create_server(port, server_ip);
127 SILC_LOG_ERROR(("Could not create server listener: %s on %hu",
134 /* Adds a secondary listener. */
135 bool silc_server_init_secondary(SilcServer server)
137 int sock=0, sock_list[server->config->param.connections_max];
138 SilcSocketConnection newsocket = NULL;
139 SilcServerConfigServerInfoInterface *interface;
141 for (interface = server->config->server_info->secondary; interface;
142 interface = interface->next, sock++) {
144 if (!silc_server_listen(server,
145 interface->server_ip, interface->port, &sock_list[sock]))
148 /* Set socket to non-blocking mode */
149 silc_net_set_socket_nonblock(sock_list[sock]);
151 /* Add ourselves also to the socket table. The entry allocated above
152 is sent as argument for fast referencing in the future. */
153 silc_socket_alloc(sock_list[sock],
154 SILC_SOCKET_TYPE_SERVER, NULL, &newsocket);
155 server->sockets[sock_list[sock]] = newsocket;
157 /* Perform name and address lookups to resolve the listenning address
159 if (!silc_net_check_local_by_sock(sock_list[sock], &newsocket->hostname,
161 if ((server->config->require_reverse_lookup && !newsocket->hostname) ||
163 SILC_LOG_ERROR(("IP/DNS lookup failed for local host %s",
164 newsocket->hostname ? newsocket->hostname :
165 newsocket->ip ? newsocket->ip : ""));
166 server->stat.conn_failures++;
169 if (!newsocket->hostname)
170 newsocket->hostname = strdup(newsocket->ip);
172 newsocket->port = silc_net_get_local_port(sock);
174 newsocket->user_data = (void *)server->id_entry;
175 silc_schedule_task_add(server->schedule, sock_list[sock],
176 silc_server_accept_new_connection,
177 (void *)server, 0, 0,
179 SILC_TASK_PRI_NORMAL);
187 do silc_net_close_server(sock_list[sock--]); while (sock >= 0);
192 /* Initializes the entire SILC server. This is called always before running
193 the server. This is called only once at the initialization of the program.
194 This binds the server to its listenning port. After this function returns
195 one should call silc_server_run to start the server. This returns TRUE
196 when everything is ok to run the server. Configuration file must be
197 read and parsed before calling this. */
199 bool silc_server_init(SilcServer server)
203 SilcServerEntry id_entry;
204 SilcIDListPurge purge;
205 SilcSocketConnection newsocket = NULL;
207 SILC_LOG_DEBUG(("Initializing server"));
209 server->starttime = time(NULL);
211 /* Take config object for us */
212 silc_server_config_ref(&server->config_ref, server->config,
215 /* Steal public and private key from the config object */
216 server->public_key = server->config->server_info->public_key;
217 server->private_key = server->config->server_info->private_key;
218 server->config->server_info->public_key = NULL;
219 server->config->server_info->private_key = NULL;
221 /* Register all configured ciphers, PKCS and hash functions. */
222 if (!silc_server_config_register_ciphers(server))
223 silc_cipher_register_default();
224 if (!silc_server_config_register_pkcs(server))
225 silc_pkcs_register_default();
226 if (!silc_server_config_register_hashfuncs(server))
227 silc_hash_register_default();
228 if (!silc_server_config_register_hmacs(server))
229 silc_hmac_register_default();
231 /* Initialize random number generator for the server. */
232 server->rng = silc_rng_alloc();
233 silc_rng_init(server->rng);
234 silc_rng_global_init(server->rng);
236 /* Initialize hash functions for server to use */
237 silc_hash_alloc("md5", &server->md5hash);
238 silc_hash_alloc("sha1", &server->sha1hash);
240 /* Allocate PKCS context for local public and private keys */
241 if (!silc_pkcs_alloc(server->public_key->name, &server->pkcs))
243 silc_pkcs_public_key_set(server->pkcs, server->public_key);
244 silc_pkcs_private_key_set(server->pkcs, server->private_key);
246 /* Initialize the scheduler */
247 server->schedule = silc_schedule_init(server->config->param.connections_max);
248 if (!server->schedule)
251 /* First, register log files configuration for error output */
252 silc_server_config_setlogfiles(server);
254 /* Initialize ID caches */
255 server->local_list->clients =
256 silc_idcache_alloc(0, SILC_ID_CLIENT, silc_idlist_client_destructor);
257 server->local_list->servers = silc_idcache_alloc(0, SILC_ID_SERVER, NULL);
258 server->local_list->channels = silc_idcache_alloc(0, SILC_ID_CHANNEL, NULL);
260 /* These are allocated for normal server as well as these hold some
261 global information that the server has fetched from its router. For
262 router these are used as they are supposed to be used on router. */
263 server->global_list->clients =
264 silc_idcache_alloc(0, SILC_ID_CLIENT, silc_idlist_client_destructor);
265 server->global_list->servers = silc_idcache_alloc(0, SILC_ID_SERVER, NULL);
266 server->global_list->channels = silc_idcache_alloc(0, SILC_ID_CHANNEL, NULL);
268 /* Init watcher list */
269 server->watcher_list =
270 silc_hash_table_alloc(1, silc_hash_client_id_hash, NULL,
271 silc_hash_data_compare, (void *)CLIENTID_HASH_LEN,
273 if (!server->watcher_list)
276 /* Create a listening server */
277 if (!silc_server_listen(server,
278 server->config->server_info->primary == NULL ? NULL :
279 server->config->server_info->primary->server_ip,
280 server->config->server_info->primary == NULL ? 0 :
281 server->config->server_info->primary->port,
285 /* Set socket to non-blocking mode */
286 silc_net_set_socket_nonblock(sock);
289 /* Allocate the entire socket list that is used in server. Eventually
290 all connections will have entry in this table (it is a table of
291 pointers to the actual object that is allocated individually
293 server->sockets = silc_calloc(server->config->param.connections_max,
294 sizeof(*server->sockets));
295 if (!server->sockets)
298 /* Add ourselves also to the socket table. The entry allocated above
299 is sent as argument for fast referencing in the future. */
300 silc_socket_alloc(sock, SILC_SOCKET_TYPE_SERVER, NULL, &newsocket);
301 server->sockets[sock] = newsocket;
303 /* Perform name and address lookups to resolve the listenning address
305 if (!silc_net_check_local_by_sock(sock, &newsocket->hostname,
307 if ((server->config->require_reverse_lookup && !newsocket->hostname) ||
309 SILC_LOG_ERROR(("IP/DNS lookup failed for local host %s",
310 newsocket->hostname ? newsocket->hostname :
311 newsocket->ip ? newsocket->ip : ""));
312 server->stat.conn_failures++;
315 if (!newsocket->hostname)
316 newsocket->hostname = strdup(newsocket->ip);
318 newsocket->port = silc_net_get_local_port(sock);
320 /* Create a Server ID for the server. */
321 silc_id_create_server_id(newsocket->ip, newsocket->port, server->rng, &id);
326 server->id_string = silc_id_id2str(id, SILC_ID_SERVER);
327 server->id_string_len = silc_id_get_len(id, SILC_ID_SERVER);
328 server->id_type = SILC_ID_SERVER;
329 server->server_name = server->config->server_info->server_name;
330 server->config->server_info->server_name = NULL;
332 /* Add ourselves to the server list. We don't have a router yet
333 beacuse we haven't established a route yet. It will be done later.
334 For now, NULL is sent as router. This allocates new entry to
337 silc_idlist_add_server(server->local_list, strdup(server->server_name),
338 server->server_type, server->id, NULL, NULL);
340 SILC_LOG_ERROR(("Could not add ourselves to cache"));
343 id_entry->data.status |= SILC_IDLIST_STATUS_REGISTERED;
345 /* Put the allocated socket pointer also to the entry allocated above
346 for fast back-referencing to the socket list. */
347 newsocket->user_data = (void *)id_entry;
348 id_entry->connection = (void *)newsocket;
349 server->id_entry = id_entry;
351 /* Register protocols */
352 silc_server_protocols_register();
354 /* Add the first task to the scheduler. This is task that is executed by
355 timeout. It expires as soon as the caller calls silc_server_run. This
356 task performs authentication protocol and key exchange with our
358 silc_schedule_task_add(server->schedule, 0,
359 silc_server_connect_to_router,
360 (void *)server, 0, 1,
362 SILC_TASK_PRI_NORMAL);
364 /* Add listener task to the scheduler. This task receives new connections
365 to the server. This task remains on the queue until the end of the
367 silc_schedule_task_add(server->schedule, sock,
368 silc_server_accept_new_connection,
369 (void *)server, 0, 0,
371 SILC_TASK_PRI_NORMAL);
373 if (silc_server_init_secondary(server) == FALSE)
376 server->listenning = TRUE;
378 /* If server connections has been configured then we must be router as
379 normal server cannot have server connections, only router connections. */
380 if (server->config->servers) {
381 SilcServerConfigServer *ptr = server->config->servers;
383 server->server_type = SILC_ROUTER;
385 if (ptr->backup_router) {
386 server->server_type = SILC_BACKUP_ROUTER;
387 server->backup_router = TRUE;
388 server->id_entry->server_type = SILC_BACKUP_ROUTER;
395 /* Register the ID Cache purge task. This periodically purges the ID cache
396 and removes the expired cache entries. */
398 /* Clients local list */
399 purge = silc_calloc(1, sizeof(*purge));
400 purge->cache = server->local_list->clients;
401 purge->schedule = server->schedule;
402 purge->timeout = 600;
403 silc_schedule_task_add(purge->schedule, 0,
405 (void *)purge, purge->timeout, 0,
406 SILC_TASK_TIMEOUT, SILC_TASK_PRI_LOW);
408 /* Clients global list */
409 purge = silc_calloc(1, sizeof(*purge));
410 purge->cache = server->global_list->clients;
411 purge->schedule = server->schedule;
412 purge->timeout = 300;
413 silc_schedule_task_add(purge->schedule, 0,
415 (void *)purge, purge->timeout, 0,
416 SILC_TASK_TIMEOUT, SILC_TASK_PRI_LOW);
418 /* If we are normal server we'll retrieve network statisticial information
419 once in a while from the router. */
420 if (server->server_type == SILC_SERVER)
421 silc_schedule_task_add(purge->schedule, 0, silc_server_get_stats,
422 server, 10, 0, SILC_TASK_TIMEOUT,
425 SILC_LOG_DEBUG(("Server initialized"));
427 /* We are done here, return succesfully */
431 silc_server_config_unref(&server->config_ref);
432 silc_net_close_server(sock);
436 /* This function basically reads the config file again and switches the config
437 object pointed by the server object. After that, we have to fix various
438 things such as the server_name and the listening ports.
439 Keep in mind that we no longer have the root privileges at this point. */
441 bool silc_server_rehash(SilcServer server)
443 SilcServerConfig newconfig;
445 SILC_LOG_INFO(("Rehashing server"));
447 /* Reset the logging system */
448 silc_log_quick = TRUE;
449 silc_log_flush_all();
451 /* Start the main rehash phase (read again the config file) */
452 newconfig = silc_server_config_alloc(server->config_file);
454 SILC_LOG_ERROR(("Rehash FAILED."));
458 /* Reinit scheduler if necessary */
459 if (newconfig->param.connections_max > server->config->param.connections_max)
460 if (!silc_schedule_reinit(server->schedule,
461 newconfig->param.connections_max))
464 /* Fix the server_name field */
465 if (strcmp(server->server_name, newconfig->server_info->server_name)) {
466 silc_free(server->server_name);
467 server->server_name = newconfig->server_info->server_name;
468 newconfig->server_info->server_name = NULL;
470 /* Update the idcache list with a fresh pointer */
471 silc_free(server->id_entry->server_name);
472 server->id_entry->server_name = strdup(server->server_name);
473 if (!silc_idcache_del_by_context(server->local_list->servers,
476 if (!silc_idcache_add(server->local_list->servers,
477 server->id_entry->server_name,
478 server->id_entry->id, server->id_entry, 0, NULL))
483 silc_server_config_setlogfiles(server);
485 /* Change new key pair if necessary */
486 if (newconfig->server_info->public_key &&
487 !silc_pkcs_public_key_compare(server->public_key,
488 newconfig->server_info->public_key)) {
489 silc_pkcs_public_key_free(server->public_key);
490 silc_pkcs_private_key_free(server->private_key);
491 server->public_key = newconfig->server_info->public_key;
492 server->private_key = newconfig->server_info->private_key;
493 newconfig->server_info->public_key = NULL;
494 newconfig->server_info->private_key = NULL;
496 /* Allocate PKCS context for local public and private keys */
497 silc_pkcs_free(server->pkcs);
498 if (!silc_pkcs_alloc(server->public_key->name, &server->pkcs))
500 silc_pkcs_public_key_set(server->pkcs, server->public_key);
501 silc_pkcs_private_key_set(server->pkcs, server->private_key);
504 /* Go through all configured routers after rehash */
505 silc_schedule_task_add(server->schedule, 0,
506 silc_server_connect_to_router,
507 (void *)server, 0, 1,
509 SILC_TASK_PRI_NORMAL);
511 /* Check whether our router status has changed */
512 if (newconfig->servers) {
513 SilcServerConfigServer *ptr = newconfig->servers;
515 server->server_type = SILC_ROUTER;
517 if (ptr->backup_router) {
518 server->server_type = SILC_BACKUP_ROUTER;
519 server->backup_router = TRUE;
520 server->id_entry->server_type = SILC_BACKUP_ROUTER;
527 /* Our old config is gone now. We'll unreference our reference made in
528 silc_server_init and then destroy it since we are destroying it
529 underneath the application (layer which called silc_server_init). */
530 silc_server_config_unref(&server->config_ref);
531 silc_server_config_destroy(server->config);
533 /* Take new config context */
534 server->config = newconfig;
535 silc_server_config_ref(&server->config_ref, server->config, server->config);
537 SILC_LOG_DEBUG(("Server rehashed"));
542 /* The heart of the server. This runs the scheduler thus runs the server.
543 When this returns the server has been stopped and the program will
546 void silc_server_run(SilcServer server)
548 SILC_LOG_INFO(("SILC Server started"));
550 /* Start the scheduler, the heart of the SILC server. When this returns
551 the program will be terminated. */
552 silc_schedule(server->schedule);
555 /* Stops the SILC server. This function is used to shutdown the server.
556 This is usually called after the scheduler has returned. After stopping
557 the server one should call silc_server_free. */
559 void silc_server_stop(SilcServer server)
561 SILC_LOG_DEBUG(("Stopping server"));
563 if (server->schedule) {
564 silc_schedule_stop(server->schedule);
565 silc_schedule_uninit(server->schedule);
566 server->schedule = NULL;
569 silc_server_protocols_unregister();
571 SILC_LOG_DEBUG(("Server stopped"));
574 /* Function that is called when the network connection to a router has
575 been established. This will continue with the key exchange protocol
576 with the remote router. */
578 void silc_server_start_key_exchange(SilcServer server,
579 SilcServerConnection sconn,
582 SilcSocketConnection newsocket;
583 SilcProtocol protocol;
584 SilcServerKEInternalContext *proto_ctx;
585 SilcServerConfigRouter *conn =
586 (SilcServerConfigRouter *) sconn->conn.ref_ptr;
589 /* Cancel any possible retry timeouts */
590 silc_schedule_task_del_by_callback(server->schedule,
591 silc_server_connect_router);
593 /* Set socket options */
594 silc_net_set_socket_nonblock(sock);
595 silc_net_set_socket_opt(sock, SOL_SOCKET, SO_REUSEADDR, 1);
597 /* Create socket connection for the connection. Even though we
598 know that we are connecting to a router we will mark the socket
599 to be unknown connection until we have executed authentication
601 silc_socket_alloc(sock, SILC_SOCKET_TYPE_UNKNOWN, NULL, &newsocket);
602 server->sockets[sock] = newsocket;
603 newsocket->hostname = strdup(sconn->remote_host);
604 newsocket->ip = strdup(sconn->remote_host);
605 newsocket->port = sconn->remote_port;
606 sconn->sock = newsocket;
608 /* Allocate internal protocol context. This is sent as context
610 proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
611 proto_ctx->server = (void *)server;
612 proto_ctx->context = (void *)sconn;
613 proto_ctx->sock = newsocket;
614 proto_ctx->rng = server->rng;
615 proto_ctx->responder = FALSE;
617 /* Set Key Exchange flags from configuration, but fall back to global
619 SILC_GET_SKE_FLAGS(conn, proto_ctx);
620 if (server->config->param.key_exchange_pfs)
621 proto_ctx->flags |= SILC_SKE_SP_FLAG_PFS;
623 /* Perform key exchange protocol. silc_server_connect_to_router_second
624 will be called after the protocol is finished. */
625 silc_protocol_alloc(SILC_PROTOCOL_SERVER_KEY_EXCHANGE,
626 &protocol, proto_ctx,
627 silc_server_connect_to_router_second);
628 newsocket->protocol = protocol;
630 /* Register a timeout task that will be executed if the protocol
631 is not executed within set limit. */
632 proto_ctx->timeout_task =
633 silc_schedule_task_add(server->schedule, sock,
634 silc_server_timeout_remote,
635 server, server->config->key_exchange_timeout, 0,
639 /* Register the connection for network input and output. This sets
640 that scheduler will listen for incoming packets for this connection
641 and sets that outgoing packets may be sent to this connection as
642 well. However, this doesn't set the scheduler for outgoing traffic,
643 it will be set separately by calling SILC_SET_CONNECTION_FOR_OUTPUT,
644 later when outgoing data is available. */
645 context = (void *)server;
646 SILC_REGISTER_CONNECTION_FOR_IO(sock);
648 /* Run the protocol */
649 silc_protocol_execute(protocol, server->schedule, 0, 0);
652 /* Timeout callback that will be called to retry connecting to remote
653 router. This is used by both normal and router server. This will wait
654 before retrying the connecting. The timeout is generated by exponential
655 backoff algorithm. */
657 SILC_TASK_CALLBACK(silc_server_connect_to_router_retry)
659 SilcServerConnection sconn = (SilcServerConnection)context;
660 SilcServer server = sconn->server;
661 SilcServerConfigRouter *conn = sconn->conn.ref_ptr;
662 SilcServerConfigConnParams *param =
663 (conn->param ? conn->param : &server->config->param);
665 SILC_LOG_INFO(("Retrying connecting to a router"));
667 /* Calculate next timeout */
668 if (sconn->retry_count >= 1) {
669 sconn->retry_timeout = sconn->retry_timeout * SILC_SERVER_RETRY_MULTIPLIER;
670 if (sconn->retry_timeout > param->reconnect_interval_max)
671 sconn->retry_timeout = param->reconnect_interval_max;
673 sconn->retry_timeout = param->reconnect_interval;
675 sconn->retry_count++;
676 sconn->retry_timeout = sconn->retry_timeout +
677 silc_rng_get_rn32(server->rng) % SILC_SERVER_RETRY_RANDOMIZER;
679 /* If we've reached max retry count, give up. */
680 if ((sconn->retry_count > param->reconnect_count) &&
681 !param->reconnect_keep_trying) {
682 SILC_LOG_ERROR(("Could not connect to router, giving up"));
683 silc_server_config_unref(&sconn->conn);
684 silc_free(sconn->remote_host);
685 silc_free(sconn->backup_replace_ip);
690 /* We will lookup a fresh pointer later */
691 silc_server_config_unref(&sconn->conn);
693 /* Wait one before retrying */
694 silc_schedule_task_add(server->schedule, 0, silc_server_connect_router,
695 context, sconn->retry_timeout, 0,
696 SILC_TASK_TIMEOUT, SILC_TASK_PRI_NORMAL);
699 /* Generic routine to use connect to a router. */
701 SILC_TASK_CALLBACK(silc_server_connect_router)
703 SilcServerConnection sconn = (SilcServerConnection)context;
704 SilcServer server = sconn->server;
705 SilcServerConfigRouter *rconn;
708 SILC_LOG_INFO(("Connecting to the %s %s on port %d",
709 (sconn->backup ? "backup router" : "router"),
710 sconn->remote_host, sconn->remote_port));
712 server->router_connect = time(NULL);
713 rconn = silc_server_config_find_router_conn(server, sconn->remote_host,
716 SILC_LOG_INFO(("Unconfigured %s connection %s:%d, cannot connect",
717 (sconn->backup ? "backup router" : "router"),
718 sconn->remote_host, sconn->remote_port));
719 silc_free(sconn->remote_host);
720 silc_free(sconn->backup_replace_ip);
724 silc_server_config_ref(&sconn->conn, server->config, (void *)rconn);
726 /* Connect to remote host */
727 sock = silc_net_create_connection(server->config->server_info->primary == NULL ? NULL :
728 server->config->server_info->primary->server_ip,
732 SILC_LOG_ERROR(("Could not connect to router %s:%d",
733 sconn->remote_host, sconn->remote_port));
734 if (!sconn->no_reconnect)
735 silc_schedule_task_add(server->schedule, 0,
736 silc_server_connect_to_router_retry,
737 context, 0, 1, SILC_TASK_TIMEOUT,
738 SILC_TASK_PRI_NORMAL);
740 silc_server_config_unref(&sconn->conn);
744 /* Continue with key exchange protocol */
745 silc_server_start_key_exchange(server, sconn, sock);
748 /* This function connects to our primary router or if we are a router this
749 establishes all our primary routes. This is called at the start of the
750 server to do authentication and key exchange with our router - called
753 SILC_TASK_CALLBACK(silc_server_connect_to_router)
755 SilcServer server = (SilcServer)context;
756 SilcServerConnection sconn;
757 SilcServerConfigRouter *ptr;
759 SILC_LOG_DEBUG(("Connecting to router(s)"));
761 if (server->server_type == SILC_SERVER) {
762 SILC_LOG_DEBUG(("We are normal server"));
763 } else if (server->server_type == SILC_ROUTER) {
764 SILC_LOG_DEBUG(("We are router"));
766 SILC_LOG_DEBUG(("We are backup router/normal server"));
769 if (!server->config->routers) {
770 /* There wasn't a configured router, we will continue but we don't
771 have a connection to outside world. We will be standalone server. */
772 SILC_LOG_DEBUG(("No router(s), server will be standalone"));
773 server->standalone = TRUE;
777 /* Cancel any possible retry timeouts */
778 silc_schedule_task_del_by_callback(server->schedule,
779 silc_server_connect_router);
780 silc_schedule_task_del_by_callback(server->schedule,
781 silc_server_connect_to_router_retry);
783 /* Create the connections to all our routes */
784 for (ptr = server->config->routers; ptr; ptr = ptr->next) {
786 SILC_LOG_DEBUG(("%s connection [%s] %s:%d",
787 ptr->backup_router ? "Backup router" : "Router",
788 ptr->initiator ? "Initiator" : "Responder",
789 ptr->host, ptr->port));
791 if (ptr->initiator) {
792 /* Check whether we are connected to this host already */
793 if (silc_server_num_sockets_by_remote(server,
794 silc_net_is_ip(ptr->host) ?
796 silc_net_is_ip(ptr->host) ?
797 NULL : ptr->host, ptr->port,
798 SILC_SOCKET_TYPE_ROUTER)) {
799 SILC_LOG_DEBUG(("We are already connected to this router"));
803 /* Allocate connection object for hold connection specific stuff. */
804 sconn = silc_calloc(1, sizeof(*sconn));
805 sconn->server = server;
806 sconn->remote_host = strdup(ptr->host);
807 sconn->remote_port = ptr->port;
808 sconn->backup = ptr->backup_router;
810 sconn->backup_replace_ip = strdup(ptr->backup_replace_ip);
811 sconn->backup_replace_port = ptr->backup_replace_port;
814 if (!server->router_conn && !sconn->backup)
815 server->router_conn = sconn;
817 silc_schedule_task_add(server->schedule, 0,
818 silc_server_connect_router,
819 (void *)sconn, 0, 1, SILC_TASK_TIMEOUT,
820 SILC_TASK_PRI_NORMAL);
825 /* Second part of connecting to router(s). Key exchange protocol has been
826 executed and now we will execute authentication protocol. */
828 SILC_TASK_CALLBACK(silc_server_connect_to_router_second)
830 SilcProtocol protocol = (SilcProtocol)context;
831 SilcServerKEInternalContext *ctx =
832 (SilcServerKEInternalContext *)protocol->context;
833 SilcServer server = (SilcServer)ctx->server;
834 SilcServerConnection sconn = (SilcServerConnection)ctx->context;
835 SilcSocketConnection sock = ctx->sock;
836 SilcServerConnAuthInternalContext *proto_ctx;
837 SilcServerConfigRouter *conn = NULL;
839 SILC_LOG_DEBUG(("Start"));
841 if (protocol->state == SILC_PROTOCOL_STATE_ERROR ||
842 protocol->state == SILC_PROTOCOL_STATE_FAILURE) {
843 /* Error occured during protocol */
844 silc_protocol_free(protocol);
845 sock->protocol = NULL;
846 silc_ske_free_key_material(ctx->keymat);
848 silc_packet_context_free(ctx->packet);
850 silc_ske_free(ctx->ske);
851 silc_free(ctx->dest_id);
853 silc_server_config_unref(&sconn->conn);
854 silc_free(sconn->remote_host);
855 silc_free(sconn->backup_replace_ip);
857 silc_schedule_task_del_by_callback(server->schedule,
858 silc_server_failure_callback);
859 silc_server_disconnect_remote(server, sock,
860 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED, NULL);
864 /* We now have the key material as the result of the key exchange
865 protocol. Take the key material into use. Free the raw key material
866 as soon as we've set them into use. */
867 if (!silc_server_protocol_ke_set_keys(server, ctx->ske,
868 ctx->sock, ctx->keymat,
869 ctx->ske->prop->cipher,
870 ctx->ske->prop->pkcs,
871 ctx->ske->prop->hash,
872 ctx->ske->prop->hmac,
873 ctx->ske->prop->group,
875 silc_protocol_free(protocol);
876 sock->protocol = NULL;
877 silc_ske_free_key_material(ctx->keymat);
879 silc_packet_context_free(ctx->packet);
881 silc_ske_free(ctx->ske);
882 silc_free(ctx->dest_id);
884 silc_server_config_unref(&sconn->conn);
885 silc_free(sconn->remote_host);
886 silc_free(sconn->backup_replace_ip);
888 silc_schedule_task_del_by_callback(server->schedule,
889 silc_server_failure_callback);
890 silc_server_disconnect_remote(server, sock,
891 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED, NULL);
894 silc_ske_free_key_material(ctx->keymat);
896 /* Allocate internal context for the authentication protocol. This
897 is sent as context for the protocol. */
898 proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
899 proto_ctx->server = (void *)server;
900 proto_ctx->context = (void *)sconn;
901 proto_ctx->sock = sock;
902 proto_ctx->ske = ctx->ske; /* Save SKE object from previous protocol */
903 proto_ctx->dest_id_type = ctx->dest_id_type;
904 proto_ctx->dest_id = ctx->dest_id;
906 /* Resolve the authentication method used in this connection. Check if
907 we find a match from user configured connections */
908 if (!sconn->conn.ref_ptr)
909 conn = silc_server_config_find_router_conn(server, sock->hostname,
912 conn = sconn->conn.ref_ptr;
915 /* Match found. Use the configured authentication method. Take only
916 the passphrase, since for public key auth we automatically use
917 our local key pair. */
918 if (conn->passphrase) {
919 if (conn->publickeys && !server->config->prefer_passphrase_auth) {
920 proto_ctx->auth_meth = SILC_AUTH_PUBLIC_KEY;
922 proto_ctx->auth_data = strdup(conn->passphrase);
923 proto_ctx->auth_data_len = strlen(conn->passphrase);
924 proto_ctx->auth_meth = SILC_AUTH_PASSWORD;
926 } else if (conn->publickeys) {
927 proto_ctx->auth_meth = SILC_AUTH_PUBLIC_KEY;
929 proto_ctx->auth_meth = SILC_AUTH_NONE;
932 SILC_LOG_ERROR(("Could not find connection data for %s (%s) on port",
933 sock->hostname, sock->ip, sock->port));
934 silc_protocol_free(protocol);
935 sock->protocol = NULL;
937 silc_packet_context_free(ctx->packet);
939 silc_ske_free(ctx->ske);
940 silc_free(ctx->dest_id);
942 silc_server_config_unref(&sconn->conn);
943 silc_free(sconn->remote_host);
944 silc_free(sconn->backup_replace_ip);
946 silc_schedule_task_del_by_callback(server->schedule,
947 silc_server_failure_callback);
948 silc_server_disconnect_remote(server, sock,
949 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED, NULL);
953 /* Free old protocol as it is finished now */
954 silc_protocol_free(protocol);
956 silc_packet_context_free(ctx->packet);
958 sock->protocol = NULL;
960 /* Allocate the authentication protocol. This is allocated here
961 but we won't start it yet. We will be receiving party of this
962 protocol thus we will wait that connecting party will make
964 silc_protocol_alloc(SILC_PROTOCOL_SERVER_CONNECTION_AUTH,
965 &sock->protocol, proto_ctx,
966 silc_server_connect_to_router_final);
968 /* Register timeout task. If the protocol is not executed inside
969 this timelimit the connection will be terminated. */
970 proto_ctx->timeout_task =
971 silc_schedule_task_add(server->schedule, sock->sock,
972 silc_server_timeout_remote,
974 server->config->conn_auth_timeout, 0,
978 /* Run the protocol */
979 silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
982 /* Finalizes the connection to router. Registers a server task to the
983 queue so that we can accept new connections. */
985 SILC_TASK_CALLBACK(silc_server_connect_to_router_final)
987 SilcProtocol protocol = (SilcProtocol)context;
988 SilcServerConnAuthInternalContext *ctx =
989 (SilcServerConnAuthInternalContext *)protocol->context;
990 SilcServer server = (SilcServer)ctx->server;
991 SilcServerConnection sconn = (SilcServerConnection)ctx->context;
992 SilcSocketConnection sock = ctx->sock;
993 SilcServerEntry id_entry;
995 SilcServerHBContext hb_context;
996 unsigned char *id_string;
998 SilcIDListData idata;
999 SilcServerConfigRouter *conn = NULL;
1000 SilcServerConfigConnParams *param = NULL;
1002 SILC_LOG_DEBUG(("Start"));
1004 if (protocol->state == SILC_PROTOCOL_STATE_ERROR ||
1005 protocol->state == SILC_PROTOCOL_STATE_FAILURE) {
1006 /* Error occured during protocol */
1007 silc_free(ctx->dest_id);
1008 silc_server_disconnect_remote(server, sock, SILC_STATUS_ERR_AUTH_FAILED,
1013 /* Add a task to the queue. This task receives new connections to the
1014 server. This task remains on the queue until the end of the program. */
1015 if (!server->listenning && !sconn->backup) {
1016 silc_schedule_task_add(server->schedule, server->sock,
1017 silc_server_accept_new_connection,
1018 (void *)server, 0, 0,
1020 SILC_TASK_PRI_NORMAL);
1021 server->listenning = TRUE;
1024 /* Send NEW_SERVER packet to the router. We will become registered
1025 to the SILC network after sending this packet. */
1026 id_string = silc_id_id2str(server->id, SILC_ID_SERVER);
1027 id_len = silc_id_get_len(server->id, SILC_ID_SERVER);
1028 packet = silc_buffer_alloc(2 + 2 + id_len + strlen(server->server_name));
1029 silc_buffer_pull_tail(packet, SILC_BUFFER_END(packet));
1030 silc_buffer_format(packet,
1031 SILC_STR_UI_SHORT(id_len),
1032 SILC_STR_UI_XNSTRING(id_string, id_len),
1033 SILC_STR_UI_SHORT(strlen(server->server_name)),
1034 SILC_STR_UI_XNSTRING(server->server_name,
1035 strlen(server->server_name)),
1038 /* Send the packet */
1039 silc_server_packet_send(server, ctx->sock, SILC_PACKET_NEW_SERVER, 0,
1040 packet->data, packet->len, TRUE);
1041 silc_buffer_free(packet);
1042 silc_free(id_string);
1044 SILC_LOG_INFO(("Connected to router %s", sock->hostname));
1046 /* Check that we do not have this ID already */
1047 id_entry = silc_idlist_find_server_by_id(server->local_list,
1048 ctx->dest_id, TRUE, NULL);
1050 silc_idcache_del_by_context(server->local_list->servers, id_entry);
1052 id_entry = silc_idlist_find_server_by_id(server->global_list,
1053 ctx->dest_id, TRUE, NULL);
1055 silc_idcache_del_by_context(server->global_list->servers, id_entry);
1058 SILC_LOG_DEBUG(("New server id(%s)",
1059 silc_id_render(ctx->dest_id, SILC_ID_SERVER)));
1061 /* Add the connected router to global server list */
1062 id_entry = silc_idlist_add_server(server->global_list,
1063 strdup(sock->hostname),
1064 SILC_ROUTER, ctx->dest_id, NULL, sock);
1066 silc_free(ctx->dest_id);
1067 SILC_LOG_ERROR(("Cannot add new server entry to cache"));
1068 silc_server_disconnect_remote(server, sock, SILC_STATUS_ERR_AUTH_FAILED,
1073 silc_idlist_add_data(id_entry, (SilcIDListData)sock->user_data);
1074 silc_free(sock->user_data);
1075 sock->user_data = (void *)id_entry;
1076 sock->type = SILC_SOCKET_TYPE_ROUTER;
1077 idata = (SilcIDListData)sock->user_data;
1078 idata->status |= SILC_IDLIST_STATUS_REGISTERED;
1080 conn = sconn->conn.ref_ptr;
1081 param = &server->config->param;
1082 if (conn && conn->param)
1083 param = conn->param;
1085 /* Perform keepalive. The `hb_context' will be freed automatically
1086 when finally calling the silc_socket_free function. */
1087 hb_context = silc_calloc(1, sizeof(*hb_context));
1088 hb_context->server = server;
1089 silc_socket_set_heartbeat(sock, param->keepalive_secs, hb_context,
1090 silc_server_perform_heartbeat,
1093 /* Register re-key timeout */
1094 idata->rekey->timeout = param->key_exchange_rekey;
1095 idata->rekey->context = (void *)server;
1096 silc_schedule_task_add(server->schedule, sock->sock,
1097 silc_server_rekey_callback,
1098 (void *)sock, idata->rekey->timeout, 0,
1099 SILC_TASK_TIMEOUT, SILC_TASK_PRI_NORMAL);
1101 if (!sconn->backup) {
1102 /* Mark this router our primary router if we're still standalone */
1103 if (server->standalone) {
1104 server->id_entry->router = id_entry;
1105 server->router = id_entry;
1106 server->standalone = FALSE;
1108 /* If we are router then announce our possible servers. */
1109 if (server->server_type == SILC_ROUTER)
1110 silc_server_announce_servers(server, FALSE, 0,
1111 server->router->connection);
1113 /* Announce our clients and channels to the router */
1114 silc_server_announce_clients(server, 0, server->router->connection);
1115 silc_server_announce_channels(server, 0, server->router->connection);
1118 /* Add this server to be our backup router */
1119 silc_server_backup_add(server, id_entry, sconn->backup_replace_ip,
1120 sconn->backup_replace_port, FALSE);
1123 sock->protocol = NULL;
1125 /* Call the completion callback to indicate that we've connected to
1127 if (sconn->callback)
1128 (*sconn->callback)(server, id_entry, sconn->callback_context);
1131 /* Free the temporary connection data context */
1133 silc_server_config_unref(&sconn->conn);
1134 silc_free(sconn->remote_host);
1135 silc_free(sconn->backup_replace_ip);
1138 if (sconn == server->router_conn)
1139 server->router_conn = NULL;
1141 /* Free the protocol object */
1142 if (sock->protocol == protocol)
1143 sock->protocol = NULL;
1144 silc_protocol_free(protocol);
1146 silc_packet_context_free(ctx->packet);
1148 silc_ske_free(ctx->ske);
1149 if (ctx->auth_meth == SILC_AUTH_PASSWORD)
1150 silc_free(ctx->auth_data);
1154 /* Host lookup callback that is called after the incoming connection's
1155 IP and FQDN lookup is performed. This will actually check the acceptance
1156 of the incoming connection and will register the key exchange protocol
1157 for this connection. */
1160 silc_server_accept_new_connection_lookup(SilcSocketConnection sock,
1163 SilcServerKEInternalContext *proto_ctx = (SilcServerKEInternalContext *)context;
1164 SilcServer server = (SilcServer)proto_ctx->server;
1165 SilcServerConfigClient *cconfig = NULL;
1166 SilcServerConfigServer *sconfig = NULL;
1167 SilcServerConfigRouter *rconfig = NULL;
1168 SilcServerConfigDeny *deny;
1171 context = (void *)server;
1173 SILC_LOG_DEBUG(("Start"));
1175 /* Check whether we could resolve both IP and FQDN. */
1176 if (!sock->ip || (!strcmp(sock->ip, sock->hostname) &&
1177 server->config->require_reverse_lookup)) {
1178 SILC_LOG_ERROR(("IP/DNS lookup failed %s",
1179 sock->hostname ? sock->hostname :
1180 sock->ip ? sock->ip : ""));
1181 server->stat.conn_failures++;
1182 silc_server_disconnect_remote(server, sock,
1183 SILC_STATUS_ERR_INCOMPLETE_INFORMATION,
1184 "Unknown host or IP");
1185 silc_free(proto_ctx);
1189 /* Register the connection for network input and output. This sets
1190 that scheduler will listen for incoming packets for this connection
1191 and sets that outgoing packets may be sent to this connection as well.
1192 However, this doesn't set the scheduler for outgoing traffic, it
1193 will be set separately by calling SILC_SET_CONNECTION_FOR_OUTPUT,
1194 later when outgoing data is available. */
1195 SILC_REGISTER_CONNECTION_FOR_IO(sock->sock);
1197 SILC_LOG_INFO(("Incoming connection %s (%s)", sock->hostname,
1200 port = server->sockets[(SilcUInt32)proto_ctx->context]->port; /* Listenning port */
1202 /* Check whether this connection is denied to connect to us. */
1203 deny = silc_server_config_find_denied(server, sock->ip);
1205 deny = silc_server_config_find_denied(server, sock->hostname);
1207 /* The connection is denied */
1208 SILC_LOG_INFO(("Connection %s (%s) is denied",
1209 sock->hostname, sock->ip));
1210 silc_server_disconnect_remote(server, sock,
1211 SILC_STATUS_ERR_BANNED_FROM_SERVER,
1213 server->stat.conn_failures++;
1214 silc_free(proto_ctx);
1218 /* Check whether we have configured this sort of connection at all. We
1219 have to check all configurations since we don't know what type of
1220 connection this is. */
1221 if (!(cconfig = silc_server_config_find_client(server, sock->ip)))
1222 cconfig = silc_server_config_find_client(server, sock->hostname);
1223 if (!(sconfig = silc_server_config_find_server_conn(server, sock->ip)))
1224 sconfig = silc_server_config_find_server_conn(server, sock->hostname);
1225 if (server->server_type == SILC_ROUTER) {
1226 if (!(rconfig = silc_server_config_find_router_conn(server,
1227 sock->ip, sock->port)))
1228 rconfig = silc_server_config_find_router_conn(server, sock->hostname,
1231 if (!cconfig && !sconfig && !rconfig) {
1232 SILC_LOG_INFO(("Connection %s (%s) is not allowed", sock->hostname,
1234 silc_server_disconnect_remote(server, sock,
1235 SILC_STATUS_ERR_BANNED_FROM_SERVER);
1236 server->stat.conn_failures++;
1237 silc_free(proto_ctx);
1241 /* The connection is allowed */
1243 /* Set internal context for key exchange protocol. This is
1244 sent as context for the protocol. */
1245 proto_ctx->sock = sock;
1246 proto_ctx->rng = server->rng;
1247 proto_ctx->responder = TRUE;
1248 silc_server_config_ref(&proto_ctx->cconfig, server->config, cconfig);
1249 silc_server_config_ref(&proto_ctx->sconfig, server->config, sconfig);
1250 silc_server_config_ref(&proto_ctx->rconfig, server->config, rconfig);
1252 /* Take flags for key exchange. Since we do not know what type of connection
1253 this is, we go through all found configurations and use the global ones
1254 as well. This will result always into strictest key exchange flags. */
1255 SILC_GET_SKE_FLAGS(cconfig, proto_ctx);
1256 SILC_GET_SKE_FLAGS(sconfig, proto_ctx);
1257 SILC_GET_SKE_FLAGS(rconfig, proto_ctx);
1258 if (server->config->param.key_exchange_pfs)
1259 proto_ctx->flags |= SILC_SKE_SP_FLAG_PFS;
1261 /* Prepare the connection for key exchange protocol. We allocate the
1262 protocol but will not start it yet. The connector will be the
1263 initiator of the protocol thus we will wait for initiation from
1264 there before we start the protocol. */
1265 server->stat.auth_attempts++;
1266 silc_protocol_alloc(SILC_PROTOCOL_SERVER_KEY_EXCHANGE,
1267 &sock->protocol, proto_ctx,
1268 silc_server_accept_new_connection_second);
1270 /* Register a timeout task that will be executed if the connector
1271 will not start the key exchange protocol within specified timeout
1272 and the connection will be closed. */
1273 proto_ctx->timeout_task =
1274 silc_schedule_task_add(server->schedule, sock->sock,
1275 silc_server_timeout_remote,
1277 server->config->key_exchange_timeout, 0,
1282 /* Accepts new connections to the server. Accepting new connections are
1283 done in three parts to make it async. */
1285 SILC_TASK_CALLBACK(silc_server_accept_new_connection)
1287 SilcServer server = (SilcServer)context;
1288 SilcSocketConnection newsocket;
1289 SilcServerKEInternalContext *proto_ctx;
1292 SILC_LOG_DEBUG(("Accepting new connection"));
1294 server->stat.conn_attempts++;
1296 sock = silc_net_accept_connection(fd);
1298 SILC_LOG_ERROR(("Could not accept new connection: %s", strerror(errno)));
1299 server->stat.conn_failures++;
1303 /* Check for maximum allowed connections */
1304 if (sock > server->config->param.connections_max) {
1305 SILC_LOG_ERROR(("Refusing connection, server is full"));
1306 server->stat.conn_failures++;
1307 silc_net_close_connection(sock);
1311 /* Set socket options */
1312 silc_net_set_socket_nonblock(sock);
1313 silc_net_set_socket_opt(sock, SOL_SOCKET, SO_REUSEADDR, 1);
1315 /* We don't create a ID yet, since we don't know what type of connection
1316 this is yet. But, we do add the connection to the socket table. */
1317 silc_socket_alloc(sock, SILC_SOCKET_TYPE_UNKNOWN, NULL, &newsocket);
1318 server->sockets[sock] = newsocket;
1320 /* Perform asynchronous host lookup. This will lookup the IP and the
1321 FQDN of the remote connection. After the lookup is done the connection
1322 is accepted further. */
1323 proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
1324 proto_ctx->server = server;
1325 proto_ctx->context = (void *)fd;
1326 silc_socket_host_lookup(newsocket, TRUE,
1327 silc_server_accept_new_connection_lookup,
1328 (void *)proto_ctx, server->schedule);
1331 /* Second part of accepting new connection. Key exchange protocol has been
1332 performed and now it is time to do little connection authentication
1333 protocol to figure out whether this connection is client or server
1334 and whether it has right to access this server (especially server
1335 connections needs to be authenticated). */
1337 SILC_TASK_CALLBACK(silc_server_accept_new_connection_second)
1339 SilcProtocol protocol = (SilcProtocol)context;
1340 SilcServerKEInternalContext *ctx =
1341 (SilcServerKEInternalContext *)protocol->context;
1342 SilcServer server = (SilcServer)ctx->server;
1343 SilcSocketConnection sock = ctx->sock;
1344 SilcServerConnAuthInternalContext *proto_ctx;
1346 SILC_LOG_DEBUG(("Start"));
1348 if ((protocol->state == SILC_PROTOCOL_STATE_ERROR) ||
1349 (protocol->state == SILC_PROTOCOL_STATE_FAILURE)) {
1350 /* Error occured during protocol */
1351 silc_protocol_free(protocol);
1352 sock->protocol = NULL;
1353 silc_ske_free_key_material(ctx->keymat);
1355 silc_packet_context_free(ctx->packet);
1357 silc_ske_free(ctx->ske);
1358 silc_free(ctx->dest_id);
1359 silc_server_config_unref(&ctx->cconfig);
1360 silc_server_config_unref(&ctx->sconfig);
1361 silc_server_config_unref(&ctx->rconfig);
1363 silc_schedule_task_del_by_callback(server->schedule,
1364 silc_server_failure_callback);
1365 silc_server_disconnect_remote(server, sock,
1366 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED,
1368 server->stat.auth_failures++;
1372 /* We now have the key material as the result of the key exchange
1373 protocol. Take the key material into use. Free the raw key material
1374 as soon as we've set them into use. */
1375 if (!silc_server_protocol_ke_set_keys(server, ctx->ske,
1376 ctx->sock, ctx->keymat,
1377 ctx->ske->prop->cipher,
1378 ctx->ske->prop->pkcs,
1379 ctx->ske->prop->hash,
1380 ctx->ske->prop->hmac,
1381 ctx->ske->prop->group,
1383 silc_protocol_free(protocol);
1384 sock->protocol = NULL;
1385 silc_ske_free_key_material(ctx->keymat);
1387 silc_packet_context_free(ctx->packet);
1389 silc_ske_free(ctx->ske);
1390 silc_free(ctx->dest_id);
1391 silc_server_config_unref(&ctx->cconfig);
1392 silc_server_config_unref(&ctx->sconfig);
1393 silc_server_config_unref(&ctx->rconfig);
1395 silc_schedule_task_del_by_callback(server->schedule,
1396 silc_server_failure_callback);
1397 silc_server_disconnect_remote(server, sock,
1398 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED, NULL);
1399 server->stat.auth_failures++;
1402 silc_ske_free_key_material(ctx->keymat);
1404 /* Allocate internal context for the authentication protocol. This
1405 is sent as context for the protocol. */
1406 proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
1407 proto_ctx->server = (void *)server;
1408 proto_ctx->sock = sock;
1409 proto_ctx->ske = ctx->ske; /* Save SKE object from previous protocol */
1410 proto_ctx->responder = TRUE;
1411 proto_ctx->dest_id_type = ctx->dest_id_type;
1412 proto_ctx->dest_id = ctx->dest_id;
1413 proto_ctx->cconfig = ctx->cconfig;
1414 proto_ctx->sconfig = ctx->sconfig;
1415 proto_ctx->rconfig = ctx->rconfig;
1417 /* Free old protocol as it is finished now */
1418 silc_protocol_free(protocol);
1420 silc_packet_context_free(ctx->packet);
1422 sock->protocol = NULL;
1424 /* Allocate the authentication protocol. This is allocated here
1425 but we won't start it yet. We will be receiving party of this
1426 protocol thus we will wait that connecting party will make
1427 their first move. */
1428 silc_protocol_alloc(SILC_PROTOCOL_SERVER_CONNECTION_AUTH,
1429 &sock->protocol, proto_ctx,
1430 silc_server_accept_new_connection_final);
1432 /* Register timeout task. If the protocol is not executed inside
1433 this timelimit the connection will be terminated. */
1434 proto_ctx->timeout_task =
1435 silc_schedule_task_add(server->schedule, sock->sock,
1436 silc_server_timeout_remote,
1438 server->config->conn_auth_timeout, 0,
1443 /* Final part of accepting new connection. The connection has now
1444 been authenticated and keys has been exchanged. We also know whether
1445 this is client or server connection. */
1447 SILC_TASK_CALLBACK(silc_server_accept_new_connection_final)
1449 SilcProtocol protocol = (SilcProtocol)context;
1450 SilcServerConnAuthInternalContext *ctx =
1451 (SilcServerConnAuthInternalContext *)protocol->context;
1452 SilcServer server = (SilcServer)ctx->server;
1453 SilcSocketConnection sock = ctx->sock;
1454 SilcServerHBContext hb_context;
1455 SilcUnknownEntry entry = (SilcUnknownEntry)sock->user_data;
1457 SilcUInt32 hearbeat_timeout = server->config->param.keepalive_secs;
1459 SILC_LOG_DEBUG(("Start"));
1461 if (protocol->state == SILC_PROTOCOL_STATE_ERROR ||
1462 protocol->state == SILC_PROTOCOL_STATE_FAILURE) {
1463 /* Error occured during protocol */
1464 silc_protocol_free(protocol);
1465 sock->protocol = NULL;
1467 silc_packet_context_free(ctx->packet);
1469 silc_ske_free(ctx->ske);
1470 silc_free(ctx->dest_id);
1471 silc_server_config_unref(&ctx->cconfig);
1472 silc_server_config_unref(&ctx->sconfig);
1473 silc_server_config_unref(&ctx->rconfig);
1475 silc_schedule_task_del_by_callback(server->schedule,
1476 silc_server_failure_callback);
1477 silc_server_disconnect_remote(server, sock, SILC_STATUS_ERR_AUTH_FAILED,
1479 server->stat.auth_failures++;
1483 entry->data.last_receive = time(NULL);
1485 switch (ctx->conn_type) {
1486 case SILC_SOCKET_TYPE_CLIENT:
1488 SilcClientEntry client;
1489 SilcServerConfigClient *conn = ctx->cconfig.ref_ptr;
1491 /* Verify whether this connection is after all allowed to connect */
1492 if (!silc_server_connection_allowed(server, sock, ctx->conn_type,
1493 &server->config->param,
1494 conn->param, ctx->ske)) {
1495 server->stat.auth_failures++;
1499 SILC_LOG_DEBUG(("Remote host is client"));
1500 SILC_LOG_INFO(("Connection %s (%s) is client", sock->hostname,
1503 /* Add the client to the client ID cache. The nickname and Client ID
1504 and other information is created after we have received NEW_CLIENT
1505 packet from client. */
1506 client = silc_idlist_add_client(server->local_list,
1507 NULL, NULL, NULL, NULL, NULL, sock, 0);
1509 SILC_LOG_ERROR(("Could not add new client to cache"));
1510 silc_free(sock->user_data);
1511 silc_server_disconnect_remote(server, sock,
1512 SILC_STATUS_ERR_AUTH_FAILED, NULL);
1513 server->stat.auth_failures++;
1518 server->stat.my_clients++;
1519 server->stat.clients++;
1520 server->stat.cell_clients++;
1522 /* Get connection parameters */
1524 if (conn->param->keepalive_secs)
1525 hearbeat_timeout = conn->param->keepalive_secs;
1528 id_entry = (void *)client;
1531 case SILC_SOCKET_TYPE_SERVER:
1532 case SILC_SOCKET_TYPE_ROUTER:
1534 SilcServerEntry new_server;
1535 bool initiator = FALSE;
1536 bool backup_local = FALSE;
1537 bool backup_router = FALSE;
1538 char *backup_replace_ip = NULL;
1539 SilcUInt16 backup_replace_port = 0;
1540 SilcServerConfigServer *sconn = ctx->sconfig.ref_ptr;
1541 SilcServerConfigRouter *rconn = ctx->rconfig.ref_ptr;
1543 if (ctx->conn_type == SILC_SOCKET_TYPE_ROUTER) {
1544 /* Verify whether this connection is after all allowed to connect */
1545 if (!silc_server_connection_allowed(server, sock, ctx->conn_type,
1546 &server->config->param,
1547 rconn ? rconn->param : NULL,
1549 server->stat.auth_failures++;
1555 if (rconn->param->keepalive_secs)
1556 hearbeat_timeout = rconn->param->keepalive_secs;
1559 initiator = rconn->initiator;
1560 backup_local = rconn->backup_local;
1561 backup_router = rconn->backup_router;
1562 backup_replace_ip = rconn->backup_replace_ip;
1563 backup_replace_port = rconn->backup_replace_port;
1567 if (ctx->conn_type == SILC_SOCKET_TYPE_SERVER) {
1568 /* Verify whether this connection is after all allowed to connect */
1569 if (!silc_server_connection_allowed(server, sock, ctx->conn_type,
1570 &server->config->param,
1571 sconn ? sconn->param : NULL,
1573 server->stat.auth_failures++;
1578 if (sconn->param->keepalive_secs)
1579 hearbeat_timeout = sconn->param->keepalive_secs;
1582 backup_router = sconn->backup_router;
1586 SILC_LOG_DEBUG(("Remote host is %s",
1587 ctx->conn_type == SILC_SOCKET_TYPE_SERVER ?
1588 "server" : (backup_router ?
1589 "backup router" : "router")));
1590 SILC_LOG_INFO(("Connection %s (%s) is %s", sock->hostname,
1591 sock->ip, ctx->conn_type == SILC_SOCKET_TYPE_SERVER ?
1592 "server" : (backup_router ?
1593 "backup router" : "router")));
1595 /* Add the server into server cache. The server name and Server ID
1596 is updated after we have received NEW_SERVER packet from the
1597 server. We mark ourselves as router for this server if we really
1600 silc_idlist_add_server((ctx->conn_type == SILC_SOCKET_TYPE_SERVER ?
1601 server->local_list : (backup_router ?
1602 server->local_list :
1603 server->global_list)),
1605 (ctx->conn_type == SILC_SOCKET_TYPE_SERVER ?
1606 SILC_SERVER : SILC_ROUTER),
1608 (ctx->conn_type == SILC_SOCKET_TYPE_SERVER ?
1609 server->id_entry : (backup_router ?
1610 server->id_entry : NULL)),
1613 SILC_LOG_ERROR(("Could not add new server to cache"));
1614 silc_free(sock->user_data);
1615 silc_server_disconnect_remote(server, sock,
1616 SILC_STATUS_ERR_AUTH_FAILED, NULL);
1617 server->stat.auth_failures++;
1622 if (ctx->conn_type == SILC_SOCKET_TYPE_SERVER)
1623 server->stat.my_servers++;
1625 server->stat.my_routers++;
1626 server->stat.servers++;
1628 id_entry = (void *)new_server;
1630 /* If the incoming connection is router and marked as backup router
1631 then add it to be one of our backups */
1632 if (ctx->conn_type == SILC_SOCKET_TYPE_ROUTER && backup_router) {
1633 silc_server_backup_add(server, new_server, backup_replace_ip,
1634 backup_replace_port, backup_local);
1636 /* Change it back to SERVER type since that's what it really is. */
1638 ctx->conn_type = SILC_SOCKET_TYPE_SERVER;
1640 new_server->server_type = SILC_BACKUP_ROUTER;
1643 /* Check whether this connection is to be our primary router connection
1644 if we do not already have the primary route. */
1645 if (server->standalone && ctx->conn_type == SILC_SOCKET_TYPE_ROUTER) {
1646 if (silc_server_config_is_primary_route(server) && !initiator)
1649 SILC_LOG_DEBUG(("We are not standalone server anymore"));
1650 server->standalone = FALSE;
1651 if (!server->id_entry->router) {
1652 server->id_entry->router = id_entry;
1653 server->router = id_entry;
1664 sock->type = ctx->conn_type;
1666 /* Add the common data structure to the ID entry. */
1667 silc_idlist_add_data(id_entry, (SilcIDListData)sock->user_data);
1669 /* Add to sockets internal pointer for fast referencing */
1670 silc_free(sock->user_data);
1671 sock->user_data = id_entry;
1673 /* Connection has been fully established now. Everything is ok. */
1674 SILC_LOG_DEBUG(("New connection authenticated"));
1676 /* Perform keepalive. The `hb_context' will be freed automatically
1677 when finally calling the silc_socket_free function. */
1678 hb_context = silc_calloc(1, sizeof(*hb_context));
1679 hb_context->server = server;
1680 silc_socket_set_heartbeat(sock, hearbeat_timeout, hb_context,
1681 silc_server_perform_heartbeat,
1685 silc_schedule_task_del_by_callback(server->schedule,
1686 silc_server_failure_callback);
1687 silc_protocol_free(protocol);
1689 silc_packet_context_free(ctx->packet);
1691 silc_ske_free(ctx->ske);
1692 silc_free(ctx->dest_id);
1693 silc_server_config_unref(&ctx->cconfig);
1694 silc_server_config_unref(&ctx->sconfig);
1695 silc_server_config_unref(&ctx->rconfig);
1697 sock->protocol = NULL;
1700 /* This function is used to read packets from network and send packets to
1701 network. This is usually a generic task. */
1703 SILC_TASK_CALLBACK(silc_server_packet_process)
1705 SilcServer server = (SilcServer)context;
1706 SilcSocketConnection sock = server->sockets[fd];
1707 SilcIDListData idata;
1708 SilcCipher cipher = NULL;
1709 SilcHmac hmac = NULL;
1710 SilcUInt32 sequence = 0;
1716 SILC_LOG_DEBUG(("Processing packet"));
1718 /* Packet sending */
1720 if (type == SILC_TASK_WRITE) {
1721 /* Do not send data to disconnected connection */
1722 if (SILC_IS_DISCONNECTED(sock))
1725 server->stat.packets_sent++;
1727 /* Send the packet */
1728 ret = silc_packet_send(sock, TRUE);
1730 /* If returned -2 could not write to connection now, will do
1736 SILC_LOG_ERROR(("Error sending packet to connection "
1737 "%s:%d [%s]", sock->hostname, sock->port,
1738 (sock->type == SILC_SOCKET_TYPE_UNKNOWN ? "Unknown" :
1739 sock->type == SILC_SOCKET_TYPE_CLIENT ? "Client" :
1740 sock->type == SILC_SOCKET_TYPE_SERVER ? "Server" :
1745 /* The packet has been sent and now it is time to set the connection
1746 back to only for input. When there is again some outgoing data
1747 available for this connection it will be set for output as well.
1748 This call clears the output setting and sets it only for input. */
1749 SILC_SET_CONNECTION_FOR_INPUT(server->schedule, fd);
1750 SILC_UNSET_OUTBUF_PENDING(sock);
1752 silc_buffer_clear(sock->outbuf);
1756 /* Packet receiving */
1758 /* Read some data from connection */
1759 ret = silc_packet_receive(sock);
1763 SILC_LOG_ERROR(("Error receiving packet from connection "
1764 "%s:%d [%s] %s", sock->hostname, sock->port,
1765 (sock->type == SILC_SOCKET_TYPE_UNKNOWN ? "Unknown" :
1766 sock->type == SILC_SOCKET_TYPE_CLIENT ? "Client" :
1767 sock->type == SILC_SOCKET_TYPE_SERVER ? "Server" :
1768 "Router"), strerror(errno)));
1774 SILC_LOG_DEBUG(("Read EOF"));
1776 /* If connection is disconnecting already we will finally
1777 close the connection */
1778 if (SILC_IS_DISCONNECTING(sock)) {
1779 if (sock->user_data)
1780 silc_server_free_sock_user_data(server, sock, NULL);
1781 silc_server_close_connection(server, sock);
1785 SILC_LOG_DEBUG(("Premature EOF from connection %d", sock->sock));
1786 SILC_SET_DISCONNECTING(sock);
1788 if (sock->user_data) {
1790 if (silc_socket_get_error(sock, tmp, sizeof(tmp) - 1))
1791 silc_server_free_sock_user_data(server, sock, tmp);
1793 silc_server_free_sock_user_data(server, sock, NULL);
1794 } else if (server->router_conn && server->router_conn->sock == sock &&
1795 !server->router && server->standalone)
1796 silc_schedule_task_add(server->schedule, 0,
1797 silc_server_connect_to_router,
1800 SILC_TASK_PRI_NORMAL);
1802 silc_server_close_connection(server, sock);
1806 /* If connection is disconnecting or disconnected we will ignore
1808 if (SILC_IS_DISCONNECTING(sock) || SILC_IS_DISCONNECTED(sock)) {
1809 SILC_LOG_DEBUG(("Ignoring read data from disconnected connection"));
1813 server->stat.packets_received++;
1815 /* Get keys and stuff from ID entry */
1816 idata = (SilcIDListData)sock->user_data;
1818 cipher = idata->receive_key;
1819 hmac = idata->hmac_receive;
1820 sequence = idata->psn_receive;
1823 /* Process the packet. This will call the parser that will then
1824 decrypt and parse the packet. */
1825 ret = silc_packet_receive_process(sock, server->server_type == SILC_ROUTER ?
1826 TRUE : FALSE, cipher, hmac, sequence,
1827 silc_server_packet_parse, server);
1829 /* If this socket connection is not authenticated yet and the packet
1830 processing failed we will drop the connection since it can be
1831 a malicious flooder. */
1832 if (sock->type == SILC_SOCKET_TYPE_UNKNOWN && ret == FALSE &&
1833 (!sock->protocol || sock->protocol->protocol->type ==
1834 SILC_PROTOCOL_SERVER_KEY_EXCHANGE)) {
1835 SILC_LOG_DEBUG(("Bad data sent from unknown connection %d", sock->sock));
1836 SILC_SET_DISCONNECTING(sock);
1838 if (sock->user_data)
1839 silc_server_free_sock_user_data(server, sock, NULL);
1840 silc_server_close_connection(server, sock);
1844 /* Parses whole packet, received earlier. */
1846 SILC_TASK_CALLBACK(silc_server_packet_parse_real)
1848 SilcPacketParserContext *parse_ctx = (SilcPacketParserContext *)context;
1849 SilcServer server = (SilcServer)parse_ctx->context;
1850 SilcSocketConnection sock = parse_ctx->sock;
1851 SilcPacketContext *packet = parse_ctx->packet;
1852 SilcIDListData idata = (SilcIDListData)sock->user_data;
1855 SILC_LOG_DEBUG(("Start"));
1857 /* Parse the packet */
1858 if (parse_ctx->normal)
1859 ret = silc_packet_parse(packet, idata ? idata->receive_key : NULL);
1861 ret = silc_packet_parse_special(packet, idata ? idata->receive_key : NULL);
1863 /* If entry is disabled ignore what we got. */
1864 if (ret != SILC_PACKET_RESUME_ROUTER &&
1865 idata && idata->status & SILC_IDLIST_STATUS_DISABLED) {
1866 SILC_LOG_DEBUG(("Connection is disabled"));
1870 if (ret == SILC_PACKET_NONE)
1873 /* Check that the the current client ID is same as in the client's packet. */
1874 if (sock->type == SILC_SOCKET_TYPE_CLIENT) {
1875 SilcClientEntry client = (SilcClientEntry)sock->user_data;
1876 if (client && client->id) {
1877 void *id = silc_id_str2id(packet->src_id, packet->src_id_len,
1878 packet->src_id_type);
1879 if (!id || !SILC_ID_CLIENT_COMPARE(client->id, id)) {
1887 if (server->server_type == SILC_ROUTER) {
1888 /* Route the packet if it is not destined to us. Other ID types but
1889 server are handled separately after processing them. */
1890 if (!(packet->flags & SILC_PACKET_FLAG_BROADCAST) &&
1891 packet->dst_id_type == SILC_ID_SERVER &&
1892 sock->type != SILC_SOCKET_TYPE_CLIENT &&
1893 memcmp(packet->dst_id, server->id_string, server->id_string_len)) {
1895 /* Route the packet to fastest route for the destination ID */
1896 void *id = silc_id_str2id(packet->dst_id, packet->dst_id_len,
1897 packet->dst_id_type);
1900 silc_server_packet_route(server,
1901 silc_server_route_get(server, id,
1902 packet->dst_id_type),
1909 /* Parse the incoming packet type */
1910 silc_server_packet_parse_type(server, sock, packet);
1912 if (server->server_type == SILC_ROUTER) {
1913 /* Broadcast packet if it is marked as broadcast packet and it is
1914 originated from router and we are router. */
1915 if (sock->type == SILC_SOCKET_TYPE_ROUTER &&
1916 packet->flags & SILC_PACKET_FLAG_BROADCAST &&
1917 !server->standalone) {
1918 /* Broadcast to our primary route */
1919 silc_server_packet_broadcast(server, server->router->connection, packet);
1921 /* If we have backup routers then we need to feed all broadcast
1922 data to those servers. */
1923 silc_server_backup_broadcast(server, sock, packet);
1928 silc_packet_context_free(packet);
1929 silc_free(parse_ctx);
1932 /* Parser callback called by silc_packet_receive_process. This merely
1933 registers timeout that will handle the actual parsing when appropriate. */
1935 bool silc_server_packet_parse(SilcPacketParserContext *parser_context,
1938 SilcServer server = (SilcServer)context;
1939 SilcSocketConnection sock = parser_context->sock;
1940 SilcIDListData idata = (SilcIDListData)sock->user_data;
1943 idata->psn_receive = parser_context->packet->sequence + 1;
1945 /* If protocol for this connection is key exchange or rekey then we'll
1946 process all packets synchronously, since there might be packets in
1947 queue that we are not able to decrypt without first processing the
1948 packets before them. */
1949 if ((parser_context->packet->type == SILC_PACKET_REKEY ||
1950 parser_context->packet->type == SILC_PACKET_REKEY_DONE) ||
1951 (sock->protocol && sock->protocol->protocol &&
1952 (sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_KEY_EXCHANGE ||
1953 sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY))) {
1954 silc_server_packet_parse_real(server->schedule, 0, sock->sock,
1957 /* Reprocess data since we'll return FALSE here. This is because
1958 the idata->receive_key might have become valid in the last packet
1959 and we want to call this processor with valid cipher. */
1961 silc_packet_receive_process(sock, server->server_type == SILC_ROUTER ?
1962 TRUE : FALSE, idata->receive_key,
1963 idata->hmac_receive, idata->psn_receive,
1964 silc_server_packet_parse, server);
1966 silc_packet_receive_process(sock, server->server_type == SILC_ROUTER ?
1967 TRUE : FALSE, NULL, NULL, 0,
1968 silc_server_packet_parse, server);
1972 switch (sock->type) {
1973 case SILC_SOCKET_TYPE_UNKNOWN:
1974 case SILC_SOCKET_TYPE_CLIENT:
1975 /* Parse the packet with timeout */
1976 silc_schedule_task_add(server->schedule, sock->sock,
1977 silc_server_packet_parse_real,
1978 (void *)parser_context, 0, 100000,
1980 SILC_TASK_PRI_NORMAL);
1982 case SILC_SOCKET_TYPE_SERVER:
1983 case SILC_SOCKET_TYPE_ROUTER:
1984 /* Packets from servers are parsed immediately */
1985 silc_server_packet_parse_real(server->schedule, 0, sock->sock,
1995 /* Parses the packet type and calls what ever routines the packet type
1996 requires. This is done for all incoming packets. */
1998 void silc_server_packet_parse_type(SilcServer server,
1999 SilcSocketConnection sock,
2000 SilcPacketContext *packet)
2002 SilcPacketType type = packet->type;
2003 SilcIDListData idata = (SilcIDListData)sock->user_data;
2005 SILC_LOG_DEBUG(("Parsing packet type %d", type));
2007 /* Parse the packet type */
2009 case SILC_PACKET_DISCONNECT:
2012 char *message = NULL;
2014 SILC_LOG_DEBUG(("Disconnect packet"));
2016 if (packet->flags & SILC_PACKET_FLAG_LIST)
2018 if (packet->buffer->len < 1)
2021 status = (SilcStatus)packet->buffer->data[0];
2022 if (packet->buffer->len > 1 &&
2023 silc_utf8_valid(packet->buffer->data + 1, packet->buffer->len - 1))
2024 message = silc_memdup(packet->buffer->data, packet->buffer->len);
2026 SILC_LOG_ERROR(("Disconnected by %s (%s): %s (%d) %s",
2027 sock->ip, sock->hostname,
2028 silc_get_status_message(status), status,
2029 message ? message : ""));
2034 case SILC_PACKET_SUCCESS:
2036 * Success received for something. For now we can have only
2037 * one protocol for connection executing at once hence this
2038 * success message is for whatever protocol is executing currently.
2040 SILC_LOG_DEBUG(("Success packet"));
2041 if (packet->flags & SILC_PACKET_FLAG_LIST)
2044 silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
2047 case SILC_PACKET_FAILURE:
2049 * Failure received for something. For now we can have only
2050 * one protocol for connection executing at once hence this
2051 * failure message is for whatever protocol is executing currently.
2053 SILC_LOG_DEBUG(("Failure packet"));
2054 if (packet->flags & SILC_PACKET_FLAG_LIST)
2056 if (sock->protocol) {
2057 SilcServerFailureContext f;
2058 f = silc_calloc(1, sizeof(*f));
2062 /* We will wait 5 seconds to process this failure packet */
2063 silc_schedule_task_add(server->schedule, sock->sock,
2064 silc_server_failure_callback, (void *)f, 5, 0,
2065 SILC_TASK_TIMEOUT, SILC_TASK_PRI_NORMAL);
2069 case SILC_PACKET_REJECT:
2070 SILC_LOG_DEBUG(("Reject packet"));
2071 if (packet->flags & SILC_PACKET_FLAG_LIST)
2076 case SILC_PACKET_NOTIFY:
2078 * Received notify packet. Server can receive notify packets from
2079 * router. Server then relays the notify messages to clients if needed.
2081 SILC_LOG_DEBUG(("Notify packet"));
2082 if (packet->flags & SILC_PACKET_FLAG_LIST)
2083 silc_server_notify_list(server, sock, packet);
2085 silc_server_notify(server, sock, packet);
2091 case SILC_PACKET_CHANNEL_MESSAGE:
2093 * Received channel message. Channel messages are special packets
2094 * (although probably most common ones) thus they are handled
2097 SILC_LOG_DEBUG(("Channel Message packet"));
2098 if (packet->flags & SILC_PACKET_FLAG_LIST)
2100 idata->last_receive = time(NULL);
2101 silc_server_channel_message(server, sock, packet);
2104 case SILC_PACKET_CHANNEL_KEY:
2106 * Received key for channel. As channels are created by the router
2107 * the keys are as well. We will distribute the key to all of our
2108 * locally connected clients on the particular channel. Router
2109 * never receives this channel and thus is ignored.
2111 SILC_LOG_DEBUG(("Channel Key packet"));
2112 if (packet->flags & SILC_PACKET_FLAG_LIST)
2114 silc_server_channel_key(server, sock, packet);
2120 case SILC_PACKET_COMMAND:
2122 * Recived command. Processes the command request and allocates the
2123 * command context and calls the command.
2125 SILC_LOG_DEBUG(("Command packet"));
2126 if (packet->flags & SILC_PACKET_FLAG_LIST)
2128 silc_server_command_process(server, sock, packet);
2131 case SILC_PACKET_COMMAND_REPLY:
2133 * Received command reply packet. Received command reply to command. It
2134 * may be reply to command sent by us or reply to command sent by client
2135 * that we've routed further.
2137 SILC_LOG_DEBUG(("Command Reply packet"));
2138 if (packet->flags & SILC_PACKET_FLAG_LIST)
2140 silc_server_command_reply(server, sock, packet);
2144 * Private Message packets
2146 case SILC_PACKET_PRIVATE_MESSAGE:
2148 * Received private message packet. The packet is coming from either
2151 SILC_LOG_DEBUG(("Private Message packet"));
2152 if (packet->flags & SILC_PACKET_FLAG_LIST)
2154 idata->last_receive = time(NULL);
2155 silc_server_private_message(server, sock, packet);
2158 case SILC_PACKET_PRIVATE_MESSAGE_KEY:
2160 * Private message key packet.
2162 if (packet->flags & SILC_PACKET_FLAG_LIST)
2164 silc_server_private_message_key(server, sock, packet);
2168 * Key Exchange protocol packets
2170 case SILC_PACKET_KEY_EXCHANGE:
2171 SILC_LOG_DEBUG(("KE packet"));
2172 if (packet->flags & SILC_PACKET_FLAG_LIST)
2175 if (sock->protocol && sock->protocol->protocol &&
2176 sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_KEY_EXCHANGE) {
2177 SilcServerKEInternalContext *proto_ctx =
2178 (SilcServerKEInternalContext *)sock->protocol->context;
2180 proto_ctx->packet = silc_packet_context_dup(packet);
2182 /* Let the protocol handle the packet */
2183 silc_protocol_execute(sock->protocol, server->schedule, 0, 100000);
2185 SILC_LOG_ERROR(("Received Key Exchange packet but no key exchange "
2186 "protocol active, packet dropped."));
2190 case SILC_PACKET_KEY_EXCHANGE_1:
2191 SILC_LOG_DEBUG(("KE 1 packet"));
2192 if (packet->flags & SILC_PACKET_FLAG_LIST)
2195 if (sock->protocol && sock->protocol->protocol &&
2196 (sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_KEY_EXCHANGE ||
2197 sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY)) {
2199 if (sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY) {
2200 SilcServerRekeyInternalContext *proto_ctx =
2201 (SilcServerRekeyInternalContext *)sock->protocol->context;
2203 if (proto_ctx->packet)
2204 silc_packet_context_free(proto_ctx->packet);
2206 proto_ctx->packet = silc_packet_context_dup(packet);
2208 /* Let the protocol handle the packet */
2209 silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
2211 SilcServerKEInternalContext *proto_ctx =
2212 (SilcServerKEInternalContext *)sock->protocol->context;
2214 if (proto_ctx->packet)
2215 silc_packet_context_free(proto_ctx->packet);
2217 proto_ctx->packet = silc_packet_context_dup(packet);
2218 proto_ctx->dest_id_type = packet->src_id_type;
2219 proto_ctx->dest_id = silc_id_str2id(packet->src_id, packet->src_id_len,
2220 packet->src_id_type);
2221 if (!proto_ctx->dest_id)
2224 /* Let the protocol handle the packet */
2225 silc_protocol_execute(sock->protocol, server->schedule,
2229 SILC_LOG_ERROR(("Received Key Exchange 1 packet but no key exchange "
2230 "protocol active, packet dropped."));
2234 case SILC_PACKET_KEY_EXCHANGE_2:
2235 SILC_LOG_DEBUG(("KE 2 packet"));
2236 if (packet->flags & SILC_PACKET_FLAG_LIST)
2239 if (sock->protocol && sock->protocol->protocol &&
2240 (sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_KEY_EXCHANGE ||
2241 sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY)) {
2243 if (sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY) {
2244 SilcServerRekeyInternalContext *proto_ctx =
2245 (SilcServerRekeyInternalContext *)sock->protocol->context;
2247 if (proto_ctx->packet)
2248 silc_packet_context_free(proto_ctx->packet);
2250 proto_ctx->packet = silc_packet_context_dup(packet);
2252 /* Let the protocol handle the packet */
2253 silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
2255 SilcServerKEInternalContext *proto_ctx =
2256 (SilcServerKEInternalContext *)sock->protocol->context;
2258 if (proto_ctx->packet)
2259 silc_packet_context_free(proto_ctx->packet);
2261 proto_ctx->packet = silc_packet_context_dup(packet);
2262 proto_ctx->dest_id_type = packet->src_id_type;
2263 proto_ctx->dest_id = silc_id_str2id(packet->src_id, packet->src_id_len,
2264 packet->src_id_type);
2265 if (!proto_ctx->dest_id)
2268 /* Let the protocol handle the packet */
2269 silc_protocol_execute(sock->protocol, server->schedule,
2273 SILC_LOG_ERROR(("Received Key Exchange 2 packet but no key exchange "
2274 "protocol active, packet dropped."));
2278 case SILC_PACKET_CONNECTION_AUTH_REQUEST:
2280 * Connection authentication request packet. When we receive this packet
2281 * we will send to the other end information about our mandatory
2282 * authentication method for the connection. This packet maybe received
2285 SILC_LOG_DEBUG(("Connection authentication request packet"));
2286 if (packet->flags & SILC_PACKET_FLAG_LIST)
2288 silc_server_connection_auth_request(server, sock, packet);
2292 * Connection Authentication protocol packets
2294 case SILC_PACKET_CONNECTION_AUTH:
2295 /* Start of the authentication protocol. We receive here the
2296 authentication data and will verify it. */
2297 SILC_LOG_DEBUG(("Connection auth packet"));
2298 if (packet->flags & SILC_PACKET_FLAG_LIST)
2301 if (sock->protocol && sock->protocol->protocol->type
2302 == SILC_PROTOCOL_SERVER_CONNECTION_AUTH) {
2304 SilcServerConnAuthInternalContext *proto_ctx =
2305 (SilcServerConnAuthInternalContext *)sock->protocol->context;
2307 proto_ctx->packet = silc_packet_context_dup(packet);
2309 /* Let the protocol handle the packet */
2310 silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
2312 SILC_LOG_ERROR(("Received Connection Auth packet but no authentication "
2313 "protocol active, packet dropped."));
2317 case SILC_PACKET_NEW_ID:
2319 * Received New ID packet. This includes some new ID that has been
2320 * created. It may be for client, server or channel. This is the way
2321 * to distribute information about new registered entities in the
2324 SILC_LOG_DEBUG(("New ID packet"));
2325 if (packet->flags & SILC_PACKET_FLAG_LIST)
2326 silc_server_new_id_list(server, sock, packet);
2328 silc_server_new_id(server, sock, packet);
2331 case SILC_PACKET_NEW_CLIENT:
2333 * Received new client packet. This includes client information that
2334 * we will use to create initial client ID. After creating new
2335 * ID we will send it to the client.
2337 SILC_LOG_DEBUG(("New Client packet"));
2338 if (packet->flags & SILC_PACKET_FLAG_LIST)
2340 silc_server_new_client(server, sock, packet);
2343 case SILC_PACKET_NEW_SERVER:
2345 * Received new server packet. This includes Server ID and some other
2346 * information that we may save. This is received after server has
2349 SILC_LOG_DEBUG(("New Server packet"));
2350 if (packet->flags & SILC_PACKET_FLAG_LIST)
2352 silc_server_new_server(server, sock, packet);
2355 case SILC_PACKET_NEW_CHANNEL:
2357 * Received new channel packet. Information about new channel in the
2358 * network are distributed using this packet.
2360 SILC_LOG_DEBUG(("New Channel packet"));
2361 if (packet->flags & SILC_PACKET_FLAG_LIST)
2362 silc_server_new_channel_list(server, sock, packet);
2364 silc_server_new_channel(server, sock, packet);
2367 case SILC_PACKET_HEARTBEAT:
2369 * Received heartbeat.
2371 SILC_LOG_DEBUG(("Heartbeat packet"));
2372 if (packet->flags & SILC_PACKET_FLAG_LIST)
2376 case SILC_PACKET_KEY_AGREEMENT:
2378 * Received heartbeat.
2380 SILC_LOG_DEBUG(("Key agreement packet"));
2381 if (packet->flags & SILC_PACKET_FLAG_LIST)
2383 silc_server_key_agreement(server, sock, packet);
2386 case SILC_PACKET_REKEY:
2388 * Received re-key packet. The sender wants to regenerate the session
2391 SILC_LOG_DEBUG(("Re-key packet"));
2392 if (packet->flags & SILC_PACKET_FLAG_LIST)
2394 silc_server_rekey(server, sock, packet);
2397 case SILC_PACKET_REKEY_DONE:
2399 * The re-key is done.
2401 SILC_LOG_DEBUG(("Re-key done packet"));
2402 if (packet->flags & SILC_PACKET_FLAG_LIST)
2405 if (sock->protocol && sock->protocol->protocol &&
2406 sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY) {
2408 SilcServerRekeyInternalContext *proto_ctx =
2409 (SilcServerRekeyInternalContext *)sock->protocol->context;
2411 if (proto_ctx->packet)
2412 silc_packet_context_free(proto_ctx->packet);
2414 proto_ctx->packet = silc_packet_context_dup(packet);
2416 /* Let the protocol handle the packet */
2417 silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
2419 SILC_LOG_ERROR(("Received Re-key done packet but no re-key "
2420 "protocol active, packet dropped."));
2424 case SILC_PACKET_FTP:
2426 SILC_LOG_DEBUG(("FTP packet"));
2427 if (packet->flags & SILC_PACKET_FLAG_LIST)
2429 silc_server_ftp(server, sock, packet);
2432 case SILC_PACKET_RESUME_CLIENT:
2434 SILC_LOG_DEBUG(("Resume Client packet"));
2435 if (packet->flags & SILC_PACKET_FLAG_LIST)
2437 silc_server_resume_client(server, sock, packet);
2440 case SILC_PACKET_RESUME_ROUTER:
2441 /* Resume router packet received. This packet is received for backup
2442 router resuming protocol. */
2443 SILC_LOG_DEBUG(("Resume router packet"));
2444 if (packet->flags & SILC_PACKET_FLAG_LIST)
2446 silc_server_backup_resume_router(server, sock, packet);
2450 SILC_LOG_ERROR(("Incorrect packet type %d, packet dropped", type));
2456 /* Creates connection to a remote router. */
2458 void silc_server_create_connection(SilcServer server,
2459 const char *remote_host, SilcUInt32 port)
2461 SilcServerConnection sconn;
2463 /* Allocate connection object for hold connection specific stuff. */
2464 sconn = silc_calloc(1, sizeof(*sconn));
2465 sconn->server = server;
2466 sconn->remote_host = strdup(remote_host);
2467 sconn->remote_port = port;
2468 sconn->no_reconnect = TRUE;
2470 silc_schedule_task_add(server->schedule, 0,
2471 silc_server_connect_router,
2472 (void *)sconn, 0, 1, SILC_TASK_TIMEOUT,
2473 SILC_TASK_PRI_NORMAL);
2476 SILC_TASK_CALLBACK(silc_server_close_connection_final)
2478 silc_socket_free((SilcSocketConnection)context);
2481 /* Closes connection to socket connection */
2483 void silc_server_close_connection(SilcServer server,
2484 SilcSocketConnection sock)
2486 if (!server->sockets[sock->sock])
2489 SILC_LOG_INFO(("Closing connection %s:%d [%s]", sock->hostname,
2491 (sock->type == SILC_SOCKET_TYPE_UNKNOWN ? "Unknown" :
2492 sock->type == SILC_SOCKET_TYPE_CLIENT ? "Client" :
2493 sock->type == SILC_SOCKET_TYPE_SERVER ? "Server" :
2496 /* We won't listen for this connection anymore */
2497 silc_schedule_unset_listen_fd(server->schedule, sock->sock);
2499 /* Unregister all tasks */
2500 silc_schedule_task_del_by_fd(server->schedule, sock->sock);
2502 /* Close the actual connection */
2503 silc_net_close_connection(sock->sock);
2504 server->sockets[sock->sock] = NULL;
2506 /* If sock->user_data is NULL then we'll check for active protocols
2507 here since the silc_server_free_sock_user_data has not been called
2508 for this connection. */
2509 if (!sock->user_data) {
2510 /* If any protocol is active cancel its execution. It will call
2511 the final callback which will finalize the disconnection. */
2512 if (sock->protocol) {
2513 silc_protocol_cancel(sock->protocol, server->schedule);
2514 sock->protocol->state = SILC_PROTOCOL_STATE_ERROR;
2515 silc_protocol_execute_final(sock->protocol, server->schedule);
2516 sock->protocol = NULL;
2521 silc_schedule_task_add(server->schedule, 0,
2522 silc_server_close_connection_final,
2523 (void *)sock, 0, 1, SILC_TASK_TIMEOUT,
2524 SILC_TASK_PRI_NORMAL);
2527 /* Sends disconnect message to remote connection and disconnects the
2530 void silc_server_disconnect_remote(SilcServer server,
2531 SilcSocketConnection sock,
2532 SilcStatus status, ...)
2535 unsigned char buf[512];
2543 memset(buf, 0, sizeof(buf));
2544 va_start(ap, status);
2545 cp = va_arg(ap, char *);
2547 vsnprintf(buf, sizeof(buf) - 1, cp, ap);
2552 SILC_LOG_DEBUG(("Disconnecting remote host"));
2554 /* Notify remote end that the conversation is over. The notify message
2555 is tried to be sent immediately. */
2559 len += silc_utf8_encoded_len(buf, strlen(buf), SILC_STRING_ASCII);
2561 buffer = silc_buffer_alloc_size(len);
2565 buffer->data[0] = status;
2567 silc_utf8_encode(buf, strlen(buf), SILC_STRING_ASCII, buffer->data + 1,
2569 silc_server_packet_send(server, sock, SILC_PACKET_DISCONNECT, 0,
2570 buffer->data, buffer->len, TRUE);
2571 silc_buffer_free(buffer);
2574 silc_server_packet_queue_purge(server, sock);
2576 /* Mark the connection to be disconnected */
2577 SILC_SET_DISCONNECTED(sock);
2578 silc_server_close_connection(server, sock);
2583 SilcClientEntry client;
2584 } *FreeClientInternal;
2586 SILC_TASK_CALLBACK(silc_server_free_client_data_timeout)
2588 FreeClientInternal i = (FreeClientInternal)context;
2590 silc_idlist_del_data(i->client);
2591 silc_idcache_purge_by_context(i->server->local_list->clients, i->client);
2595 /* Frees client data and notifies about client's signoff. */
2597 void silc_server_free_client_data(SilcServer server,
2598 SilcSocketConnection sock,
2599 SilcClientEntry client,
2601 const char *signoff)
2603 FreeClientInternal i = silc_calloc(1, sizeof(*i));
2605 /* If there is pending outgoing data for the client then purge it
2606 to the network before removing the client entry. */
2607 silc_server_packet_queue_purge(server, sock);
2610 /* Check if anyone is watching this nickname */
2611 if (server->server_type == SILC_ROUTER)
2612 silc_server_check_watcher_list(server, client, NULL,
2613 SILC_NOTIFY_TYPE_SIGNOFF);
2615 /* Send SIGNOFF notify to routers. */
2616 if (notify && !server->standalone && server->router)
2617 silc_server_send_notify_signoff(server, server->router->connection,
2618 server->server_type == SILC_SERVER ?
2619 FALSE : TRUE, client->id, signoff);
2621 /* Remove client from all channels */
2623 silc_server_remove_from_channels(server, NULL, client,
2624 TRUE, (char *)signoff, TRUE);
2626 silc_server_remove_from_channels(server, NULL, client,
2627 FALSE, NULL, FALSE);
2629 /* Remove this client from watcher list if it is */
2630 silc_server_del_from_watcher_list(server, client);
2633 /* Update statistics */
2634 server->stat.my_clients--;
2635 server->stat.clients--;
2636 if (server->stat.cell_clients)
2637 server->stat.cell_clients--;
2638 SILC_OPER_STATS_UPDATE(client, server, SILC_UMODE_SERVER_OPERATOR);
2639 SILC_OPER_STATS_UPDATE(client, router, SILC_UMODE_ROUTER_OPERATOR);
2640 silc_schedule_task_del_by_context(server->schedule, client);
2642 /* We will not delete the client entry right away. We will take it
2643 into history (for WHOWAS command) for 5 minutes */
2646 silc_schedule_task_add(server->schedule, 0,
2647 silc_server_free_client_data_timeout,
2649 SILC_TASK_TIMEOUT, SILC_TASK_PRI_LOW);
2650 client->data.status &= ~SILC_IDLIST_STATUS_REGISTERED;
2652 client->router = NULL;
2653 client->connection = NULL;
2656 /* Frees user_data pointer from socket connection object. This also sends
2657 appropriate notify packets to the network to inform about leaving
2660 void silc_server_free_sock_user_data(SilcServer server,
2661 SilcSocketConnection sock,
2662 const char *signoff_message)
2664 SILC_LOG_DEBUG(("Start"));
2666 switch (sock->type) {
2667 case SILC_SOCKET_TYPE_CLIENT:
2669 SilcClientEntry user_data = (SilcClientEntry)sock->user_data;
2670 silc_server_free_client_data(server, sock, user_data, TRUE,
2674 case SILC_SOCKET_TYPE_SERVER:
2675 case SILC_SOCKET_TYPE_ROUTER:
2677 SilcServerEntry user_data = (SilcServerEntry)sock->user_data;
2678 SilcServerEntry backup_router = NULL;
2681 backup_router = silc_server_backup_get(server, user_data->id);
2683 /* If this was our primary router connection then we're lost to
2684 the outside world. */
2685 if (server->router == user_data) {
2686 /* Check whether we have a backup router connection */
2687 if (!backup_router || backup_router == user_data) {
2688 silc_schedule_task_add(server->schedule, 0,
2689 silc_server_connect_to_router,
2692 SILC_TASK_PRI_NORMAL);
2694 server->id_entry->router = NULL;
2695 server->router = NULL;
2696 server->standalone = TRUE;
2697 backup_router = NULL;
2699 SILC_LOG_INFO(("New primary router is backup router %s",
2700 backup_router->server_name));
2701 SILC_LOG_DEBUG(("New primary router is backup router %s",
2702 backup_router->server_name));
2703 server->id_entry->router = backup_router;
2704 server->router = backup_router;
2705 server->router_connect = time(0);
2706 server->backup_primary = TRUE;
2707 if (server->server_type == SILC_BACKUP_ROUTER) {
2708 server->server_type = SILC_ROUTER;
2710 /* We'll need to constantly try to reconnect to the primary
2711 router so that we'll see when it comes back online. */
2712 silc_server_backup_reconnect(server, sock->ip, sock->port,
2713 silc_server_backup_connected,
2717 /* Mark this connection as replaced */
2718 silc_server_backup_replaced_add(server, user_data->id,
2721 } else if (backup_router) {
2722 SILC_LOG_INFO(("Enabling the use of backup router %s",
2723 backup_router->server_name));
2724 SILC_LOG_DEBUG(("Enabling the use of backup router %s",
2725 backup_router->server_name));
2727 /* Mark this connection as replaced */
2728 silc_server_backup_replaced_add(server, user_data->id,
2732 if (!backup_router) {
2733 /* Free all client entries that this server owns as they will
2734 become invalid now as well. */
2736 silc_server_remove_clients_by_server(server, user_data, TRUE);
2737 if (server->server_type == SILC_SERVER)
2738 silc_server_remove_channels_by_server(server, user_data);
2740 /* Update the client entries of this server to the new backup
2741 router. This also removes the clients that *really* was owned
2742 by the primary router and went down with the router. */
2743 silc_server_update_clients_by_server(server, user_data, backup_router,
2745 silc_server_update_servers_by_server(server, user_data, backup_router);
2746 if (server->server_type == SILC_SERVER)
2747 silc_server_update_channels_by_server(server, user_data,
2751 /* Free the server entry */
2752 silc_server_backup_del(server, user_data);
2753 silc_server_backup_replaced_del(server, user_data);
2754 silc_idlist_del_data(user_data);
2755 if (!silc_idlist_del_server(server->local_list, user_data))
2756 silc_idlist_del_server(server->global_list, user_data);
2757 server->stat.my_servers--;
2758 server->stat.servers--;
2759 if (server->server_type == SILC_ROUTER)
2760 server->stat.cell_servers--;
2762 if (backup_router) {
2763 /* Announce all of our stuff that was created about 5 minutes ago.
2764 The backup router knows all the other stuff already. */
2765 if (server->server_type == SILC_ROUTER)
2766 silc_server_announce_servers(server, FALSE, time(0) - 300,
2767 backup_router->connection);
2769 /* Announce our clients and channels to the router */
2770 silc_server_announce_clients(server, time(0) - 300,
2771 backup_router->connection);
2772 silc_server_announce_channels(server, time(0) - 300,
2773 backup_router->connection);
2779 SilcUnknownEntry user_data = (SilcUnknownEntry)sock->user_data;
2781 silc_idlist_del_data(user_data);
2782 silc_free(user_data);
2787 /* If any protocol is active cancel its execution */
2788 if (sock->protocol) {
2789 silc_protocol_cancel(sock->protocol, server->schedule);
2790 sock->protocol->state = SILC_PROTOCOL_STATE_ERROR;
2791 silc_protocol_execute_final(sock->protocol, server->schedule);
2792 sock->protocol = NULL;
2795 sock->user_data = NULL;
2798 /* Removes client from all channels it has joined. This is used when client
2799 connection is disconnected. If the client on a channel is last, the
2800 channel is removed as well. This sends the SIGNOFF notify types. */
2802 void silc_server_remove_from_channels(SilcServer server,
2803 SilcSocketConnection sock,
2804 SilcClientEntry client,
2806 const char *signoff_message,
2809 SilcChannelEntry channel;
2810 SilcChannelClientEntry chl;
2811 SilcHashTableList htl;
2814 SILC_LOG_DEBUG(("Start"));
2816 if (!client || !client->id)
2819 clidp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
2823 /* Remove the client from all channels. The client is removed from
2824 the channels' user list. */
2825 silc_hash_table_list(client->channels, &htl);
2826 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
2827 channel = chl->channel;
2829 /* Remove channel if this is last client leaving the channel, unless
2830 the channel is permanent. */
2831 if (server->server_type == SILC_ROUTER &&
2832 silc_hash_table_count(channel->user_list) < 2) {
2833 silc_server_channel_delete(server, channel);
2837 silc_hash_table_del(client->channels, channel);
2838 silc_hash_table_del(channel->user_list, chl->client);
2839 channel->user_count--;
2841 /* If there is no global users on the channel anymore mark the channel
2842 as local channel. Do not check if the removed client is local client. */
2843 if (server->server_type != SILC_ROUTER && channel->global_users &&
2844 chl->client->router && !silc_server_channel_has_global(channel))
2845 channel->global_users = FALSE;
2848 server->stat.my_chanclients--;
2850 /* If there is not at least one local user on the channel then we don't
2851 need the channel entry anymore, we can remove it safely, unless the
2852 channel is permanent channel */
2853 if (server->server_type != SILC_ROUTER &&
2854 !silc_server_channel_has_local(channel)) {
2855 /* Notify about leaving client if this channel has global users. */
2856 if (notify && channel->global_users)
2857 silc_server_send_notify_to_channel(server, NULL, channel, FALSE,
2858 SILC_NOTIFY_TYPE_SIGNOFF,
2859 signoff_message ? 2 : 1,
2860 clidp->data, clidp->len,
2861 signoff_message, signoff_message ?
2862 strlen(signoff_message) : 0);
2864 silc_schedule_task_del_by_context(server->schedule, channel->rekey);
2865 silc_server_channel_delete(server, channel);
2869 /* Send notify to channel about client leaving SILC and channel too */
2871 silc_server_send_notify_to_channel(server, NULL, channel, FALSE,
2872 SILC_NOTIFY_TYPE_SIGNOFF,
2873 signoff_message ? 2 : 1,
2874 clidp->data, clidp->len,
2875 signoff_message, signoff_message ?
2876 strlen(signoff_message) : 0);
2878 /* Re-generate channel key if needed */
2879 if (keygen && !(channel->mode & SILC_CHANNEL_MODE_PRIVKEY)) {
2880 if (!silc_server_create_channel_key(server, channel, 0))
2883 /* Send the channel key to the channel. The key of course is not sent
2884 to the client who was removed from the channel. */
2885 silc_server_send_channel_key(server, client->connection, channel,
2886 server->server_type == SILC_ROUTER ?
2887 FALSE : !server->standalone);
2891 silc_hash_table_list_reset(&htl);
2892 silc_buffer_free(clidp);
2895 /* Removes client from one channel. This is used for example when client
2896 calls LEAVE command to remove itself from the channel. Returns TRUE
2897 if channel still exists and FALSE if the channel is removed when
2898 last client leaves the channel. If `notify' is FALSE notify messages
2901 bool silc_server_remove_from_one_channel(SilcServer server,
2902 SilcSocketConnection sock,
2903 SilcChannelEntry channel,
2904 SilcClientEntry client,
2907 SilcChannelClientEntry chl;
2910 SILC_LOG_DEBUG(("Removing %s from channel %s",
2911 silc_id_render(client->id, SILC_ID_CLIENT),
2912 channel->channel_name));
2914 /* Get the entry to the channel, if this client is not on the channel
2916 if (!silc_hash_table_find(client->channels, channel, NULL, (void *)&chl))
2919 /* Remove channel if this is last client leaving the channel, unless
2920 the channel is permanent. */
2921 if (server->server_type == SILC_ROUTER &&
2922 silc_hash_table_count(channel->user_list) < 2) {
2923 silc_server_channel_delete(server, channel);
2927 silc_hash_table_del(client->channels, chl->channel);
2928 silc_hash_table_del(channel->user_list, chl->client);
2929 channel->user_count--;
2931 /* If there is no global users on the channel anymore mark the channel
2932 as local channel. Do not check if the client is local client. */
2933 if (server->server_type != SILC_ROUTER && channel->global_users &&
2934 chl->client->router && !silc_server_channel_has_global(channel))
2935 channel->global_users = FALSE;
2938 server->stat.my_chanclients--;
2940 clidp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
2944 /* If there is not at least one local user on the channel then we don't
2945 need the channel entry anymore, we can remove it safely, unless the
2946 channel is permanent channel */
2947 if (server->server_type != SILC_ROUTER &&
2948 !silc_server_channel_has_local(channel)) {
2949 /* Notify about leaving client if this channel has global users. */
2950 if (notify && channel->global_users)
2951 silc_server_send_notify_to_channel(server, NULL, channel, FALSE,
2952 SILC_NOTIFY_TYPE_LEAVE, 1,
2953 clidp->data, clidp->len);
2955 silc_schedule_task_del_by_context(server->schedule, channel->rekey);
2956 silc_server_channel_delete(server, channel);
2957 silc_buffer_free(clidp);
2961 /* Send notify to channel about client leaving the channel */
2963 silc_server_send_notify_to_channel(server, NULL, channel, FALSE,
2964 SILC_NOTIFY_TYPE_LEAVE, 1,
2965 clidp->data, clidp->len);
2967 silc_buffer_free(clidp);
2971 /* Timeout callback. This is called if connection is idle or for some
2972 other reason is not responding within some period of time. This
2973 disconnects the remote end. */
2975 SILC_TASK_CALLBACK(silc_server_timeout_remote)
2977 SilcServer server = (SilcServer)context;
2978 SilcSocketConnection sock = server->sockets[fd];
2979 SilcProtocolType protocol = 0;
2981 SILC_LOG_DEBUG(("Start"));
2986 SILC_LOG_ERROR(("No response from %s (%s), Connection timeout",
2987 sock->hostname, sock->ip));
2989 /* If we have protocol active we must assure that we call the protocol's
2990 final callback so that all the memory is freed. */
2991 if (sock->protocol) {
2992 protocol = sock->protocol->protocol->type;
2993 silc_protocol_cancel(sock->protocol, server->schedule);
2994 sock->protocol->state = SILC_PROTOCOL_STATE_ERROR;
2995 silc_protocol_execute_final(sock->protocol, server->schedule);
2996 sock->protocol = NULL;
3000 if (sock->user_data)
3001 silc_server_free_sock_user_data(server, sock, NULL);
3003 silc_server_disconnect_remote(server, sock,
3005 SILC_PROTOCOL_SERVER_CONNECTION_AUTH ?
3006 SILC_STATUS_ERR_AUTH_FAILED :
3007 SILC_STATUS_ERR_KEY_EXCHANGE_FAILED,
3008 "Connection timeout");
3011 /* Creates new channel. Sends NEW_CHANNEL packet to primary route. This
3012 function may be used only by router. In real SILC network all channels
3013 are created by routers thus this function is never used by normal
3016 SilcChannelEntry silc_server_create_new_channel(SilcServer server,
3017 SilcServerID *router_id,
3023 SilcChannelID *channel_id;
3024 SilcChannelEntry entry;
3028 SILC_LOG_DEBUG(("Creating new channel"));
3031 cipher = SILC_DEFAULT_CIPHER;
3033 hmac = SILC_DEFAULT_HMAC;
3035 /* Allocate cipher */
3036 if (!silc_cipher_alloc(cipher, &key))
3040 if (!silc_hmac_alloc(hmac, NULL, &newhmac)) {
3041 silc_cipher_free(key);
3045 channel_name = strdup(channel_name);
3047 /* Create the channel ID */
3048 if (!silc_id_create_channel_id(server, router_id, server->rng,
3050 silc_free(channel_name);
3051 silc_cipher_free(key);
3052 silc_hmac_free(newhmac);
3056 /* Create the channel */
3057 entry = silc_idlist_add_channel(server->local_list, channel_name,
3058 SILC_CHANNEL_MODE_NONE, channel_id,
3059 NULL, key, newhmac, 0);
3061 silc_free(channel_name);
3062 silc_cipher_free(key);
3063 silc_hmac_free(newhmac);
3064 silc_free(channel_id);
3068 entry->cipher = strdup(cipher);
3069 entry->hmac_name = strdup(hmac);
3071 /* Now create the actual key material */
3072 if (!silc_server_create_channel_key(server, entry,
3073 silc_cipher_get_key_len(key) / 8)) {
3074 silc_idlist_del_channel(server->local_list, entry);
3078 /* Notify other routers about the new channel. We send the packet
3079 to our primary route. */
3080 if (broadcast && server->standalone == FALSE)
3081 silc_server_send_new_channel(server, server->router->connection, TRUE,
3082 channel_name, entry->id,
3083 silc_id_get_len(entry->id, SILC_ID_CHANNEL),
3086 server->stat.my_channels++;
3088 if (server->server_type == SILC_ROUTER)
3089 entry->users_resolved = TRUE;
3094 /* Same as above but creates the channel with Channel ID `channel_id. */
3097 silc_server_create_new_channel_with_id(SilcServer server,
3101 SilcChannelID *channel_id,
3104 SilcChannelEntry entry;
3108 SILC_LOG_DEBUG(("Creating new channel"));
3111 cipher = SILC_DEFAULT_CIPHER;
3113 hmac = SILC_DEFAULT_HMAC;
3115 /* Allocate cipher */
3116 if (!silc_cipher_alloc(cipher, &key))
3120 if (!silc_hmac_alloc(hmac, NULL, &newhmac)) {
3121 silc_cipher_free(key);
3125 channel_name = strdup(channel_name);
3127 /* Create the channel */
3128 entry = silc_idlist_add_channel(server->local_list, channel_name,
3129 SILC_CHANNEL_MODE_NONE, channel_id,
3130 NULL, key, newhmac, 0);
3132 silc_cipher_free(key);
3133 silc_hmac_free(newhmac);
3134 silc_free(channel_name);
3138 /* Now create the actual key material */
3139 if (!silc_server_create_channel_key(server, entry,
3140 silc_cipher_get_key_len(key) / 8)) {
3141 silc_idlist_del_channel(server->local_list, entry);
3145 /* Notify other routers about the new channel. We send the packet
3146 to our primary route. */
3147 if (broadcast && server->standalone == FALSE)
3148 silc_server_send_new_channel(server, server->router->connection, TRUE,
3149 channel_name, entry->id,
3150 silc_id_get_len(entry->id, SILC_ID_CHANNEL),
3153 server->stat.my_channels++;
3155 if (server->server_type == SILC_ROUTER)
3156 entry->users_resolved = TRUE;
3161 /* Channel's key re-key timeout callback. */
3163 SILC_TASK_CALLBACK(silc_server_channel_key_rekey)
3165 SilcServerChannelRekey rekey = (SilcServerChannelRekey)context;
3166 SilcServer server = (SilcServer)rekey->context;
3170 if (!silc_server_create_channel_key(server, rekey->channel, rekey->key_len))
3173 silc_server_send_channel_key(server, NULL, rekey->channel, FALSE);
3176 /* Generates new channel key. This is used to create the initial channel key
3177 but also to re-generate new key for channel. If `key_len' is provided
3178 it is the bytes of the key length. */
3180 bool silc_server_create_channel_key(SilcServer server,
3181 SilcChannelEntry channel,
3185 unsigned char channel_key[32], hash[32];
3188 SILC_LOG_DEBUG(("Generating channel key"));
3190 if (channel->mode & SILC_CHANNEL_MODE_PRIVKEY) {
3191 SILC_LOG_DEBUG(("Channel has private keys, will not generate new key"));
3195 if (!channel->channel_key)
3196 if (!silc_cipher_alloc(SILC_DEFAULT_CIPHER, &channel->channel_key)) {
3197 channel->channel_key = NULL;
3203 else if (channel->key_len)
3204 len = channel->key_len / 8;
3206 len = silc_cipher_get_key_len(channel->channel_key) / 8;
3208 /* Create channel key */
3209 for (i = 0; i < len; i++) channel_key[i] = silc_rng_get_byte(server->rng);
3212 silc_cipher_set_key(channel->channel_key, channel_key, len * 8);
3214 /* Remove old key if exists */
3216 memset(channel->key, 0, channel->key_len / 8);
3217 silc_free(channel->key);
3221 channel->key_len = len * 8;
3222 channel->key = silc_memdup(channel_key, len);
3223 memset(channel_key, 0, sizeof(channel_key));
3225 /* Generate HMAC key from the channel key data and set it */
3227 silc_hmac_alloc(SILC_DEFAULT_HMAC, NULL, &channel->hmac);
3228 silc_hash_make(silc_hmac_get_hash(channel->hmac), channel->key, len, hash);
3229 silc_hmac_set_key(channel->hmac, hash,
3230 silc_hash_len(silc_hmac_get_hash(channel->hmac)));
3231 memset(hash, 0, sizeof(hash));
3233 if (server->server_type == SILC_ROUTER) {
3234 if (!channel->rekey)
3235 channel->rekey = silc_calloc(1, sizeof(*channel->rekey));
3236 channel->rekey->context = (void *)server;
3237 channel->rekey->channel = channel;
3238 channel->rekey->key_len = key_len;
3239 if (channel->rekey->task)
3240 silc_schedule_task_del(server->schedule, channel->rekey->task);
3242 channel->rekey->task =
3243 silc_schedule_task_add(server->schedule, 0,
3244 silc_server_channel_key_rekey,
3245 (void *)channel->rekey,
3246 server->config->channel_rekey_secs, 0,
3248 SILC_TASK_PRI_NORMAL);
3254 /* Saves the channel key found in the encoded `key_payload' buffer. This
3255 function is used when we receive Channel Key Payload and also when we're
3256 processing JOIN command reply. Returns entry to the channel. */
3258 SilcChannelEntry silc_server_save_channel_key(SilcServer server,
3259 SilcBuffer key_payload,
3260 SilcChannelEntry channel)
3262 SilcChannelKeyPayload payload = NULL;
3263 SilcChannelID *id = NULL;
3264 unsigned char *tmp, hash[32];
3268 SILC_LOG_DEBUG(("Start"));
3270 /* Decode channel key payload */
3271 payload = silc_channel_key_payload_parse(key_payload->data,
3274 SILC_LOG_ERROR(("Bad channel key payload received, dropped"));
3279 /* Get the channel entry */
3282 /* Get channel ID */
3283 tmp = silc_channel_key_get_id(payload, &tmp_len);
3284 id = silc_id_str2id(tmp, tmp_len, SILC_ID_CHANNEL);
3290 channel = silc_idlist_find_channel_by_id(server->local_list, id, NULL);
3292 channel = silc_idlist_find_channel_by_id(server->global_list, id, NULL);
3294 SILC_LOG_ERROR(("Received key for non-existent channel %s",
3295 silc_id_render(id, SILC_ID_CHANNEL)));
3301 tmp = silc_channel_key_get_key(payload, &tmp_len);
3307 cipher = silc_channel_key_get_cipher(payload, NULL);
3313 /* Remove old key if exists */
3315 memset(channel->key, 0, channel->key_len / 8);
3316 silc_free(channel->key);
3317 silc_cipher_free(channel->channel_key);
3320 /* Create new cipher */
3321 if (!silc_cipher_alloc(cipher, &channel->channel_key)) {
3322 channel->channel_key = NULL;
3327 if (channel->cipher)
3328 silc_free(channel->cipher);
3329 channel->cipher = strdup(cipher);
3332 channel->key_len = tmp_len * 8;
3333 channel->key = silc_memdup(tmp, tmp_len);
3334 silc_cipher_set_key(channel->channel_key, tmp, channel->key_len);
3336 /* Generate HMAC key from the channel key data and set it */
3338 silc_hmac_alloc(SILC_DEFAULT_HMAC, NULL, &channel->hmac);
3339 silc_hash_make(silc_hmac_get_hash(channel->hmac), tmp, tmp_len, hash);
3340 silc_hmac_set_key(channel->hmac, hash,
3341 silc_hash_len(silc_hmac_get_hash(channel->hmac)));
3343 memset(hash, 0, sizeof(hash));
3344 memset(tmp, 0, tmp_len);
3346 if (server->server_type == SILC_ROUTER) {
3347 if (!channel->rekey)
3348 channel->rekey = silc_calloc(1, sizeof(*channel->rekey));
3349 channel->rekey->context = (void *)server;
3350 channel->rekey->channel = channel;
3351 if (channel->rekey->task)
3352 silc_schedule_task_del(server->schedule, channel->rekey->task);
3354 channel->rekey->task =
3355 silc_schedule_task_add(server->schedule, 0,
3356 silc_server_channel_key_rekey,
3357 (void *)channel->rekey,
3358 server->config->channel_rekey_secs, 0,
3360 SILC_TASK_PRI_NORMAL);
3366 silc_channel_key_payload_free(payload);
3371 /* Heartbeat callback. This function is set as argument for the
3372 silc_socket_set_heartbeat function. The library will call this function
3373 at the set time interval. */
3375 void silc_server_perform_heartbeat(SilcSocketConnection sock,
3378 SilcServerHBContext hb = (SilcServerHBContext)hb_context;
3380 SILC_LOG_DEBUG(("Sending heartbeat to %s (%s)", sock->hostname, sock->ip));
3382 /* Send the heartbeat */
3383 silc_server_send_heartbeat(hb->server, sock);
3386 /* Returns assembled of all servers in the given ID list. The packet's
3387 form is dictated by the New ID payload. */
3389 static void silc_server_announce_get_servers(SilcServer server,
3390 SilcServerEntry remote,
3392 SilcBuffer *servers,
3393 unsigned long creation_time)
3395 SilcIDCacheList list;
3396 SilcIDCacheEntry id_cache;
3397 SilcServerEntry entry;
3400 /* Go through all clients in the list */
3401 if (silc_idcache_get_all(id_list->servers, &list)) {
3402 if (silc_idcache_list_first(list, &id_cache)) {
3404 entry = (SilcServerEntry)id_cache->context;
3406 /* Do not announce the one we've sending our announcements and
3407 do not announce ourself. Also check the creation time if it's
3409 if ((entry == remote) || (entry == server->id_entry) ||
3410 (creation_time && entry->data.created < creation_time)) {
3411 if (!silc_idcache_list_next(list, &id_cache))
3416 idp = silc_id_payload_encode(entry->id, SILC_ID_SERVER);
3418 *servers = silc_buffer_realloc(*servers,
3420 (*servers)->truelen + idp->len :
3422 silc_buffer_pull_tail(*servers, ((*servers)->end - (*servers)->data));
3423 silc_buffer_put(*servers, idp->data, idp->len);
3424 silc_buffer_pull(*servers, idp->len);
3425 silc_buffer_free(idp);
3427 if (!silc_idcache_list_next(list, &id_cache))
3432 silc_idcache_list_free(list);
3437 silc_server_announce_encode_notify(SilcNotifyType notify, SilcUInt32 argc, ...)
3443 p = silc_notify_payload_encode(notify, argc, ap);
3449 /* This function is used by router to announce existing servers to our
3450 primary router when we've connected to it. If `creation_time' is non-zero
3451 then only the servers that has been created after the `creation_time'
3452 will be announced. */
3454 void silc_server_announce_servers(SilcServer server, bool global,
3455 unsigned long creation_time,
3456 SilcSocketConnection remote)
3458 SilcBuffer servers = NULL;
3460 SILC_LOG_DEBUG(("Announcing servers"));
3462 /* Get servers in local list */
3463 silc_server_announce_get_servers(server, remote->user_data,
3464 server->local_list, &servers,
3468 /* Get servers in global list */
3469 silc_server_announce_get_servers(server, remote->user_data,
3470 server->global_list, &servers,
3474 silc_buffer_push(servers, servers->data - servers->head);
3475 SILC_LOG_HEXDUMP(("servers"), servers->data, servers->len);
3477 /* Send the packet */
3478 silc_server_packet_send(server, remote,
3479 SILC_PACKET_NEW_ID, SILC_PACKET_FLAG_LIST,
3480 servers->data, servers->len, TRUE);
3482 silc_buffer_free(servers);
3486 /* Returns assembled packet of all clients in the given ID list. The
3487 packet's form is dictated by the New ID Payload. */
3489 static void silc_server_announce_get_clients(SilcServer server,
3491 SilcBuffer *clients,
3493 unsigned long creation_time)
3495 SilcIDCacheList list;
3496 SilcIDCacheEntry id_cache;
3497 SilcClientEntry client;
3500 unsigned char mode[4];
3502 /* Go through all clients in the list */
3503 if (silc_idcache_get_all(id_list->clients, &list)) {
3504 if (silc_idcache_list_first(list, &id_cache)) {
3506 client = (SilcClientEntry)id_cache->context;
3508 if (creation_time && client->data.created < creation_time) {
3509 if (!silc_idcache_list_next(list, &id_cache))
3514 idp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
3516 *clients = silc_buffer_realloc(*clients,
3518 (*clients)->truelen + idp->len :
3520 silc_buffer_pull_tail(*clients, ((*clients)->end - (*clients)->data));
3521 silc_buffer_put(*clients, idp->data, idp->len);
3522 silc_buffer_pull(*clients, idp->len);
3524 SILC_PUT32_MSB(client->mode, mode);
3525 tmp = silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_UMODE_CHANGE,
3526 2, idp->data, idp->len,
3528 *umodes = silc_buffer_realloc(*umodes,
3530 (*umodes)->truelen + tmp->len :
3532 silc_buffer_pull_tail(*umodes, ((*umodes)->end - (*umodes)->data));
3533 silc_buffer_put(*umodes, tmp->data, tmp->len);
3534 silc_buffer_pull(*umodes, tmp->len);
3535 silc_buffer_free(tmp);
3537 silc_buffer_free(idp);
3539 if (!silc_idcache_list_next(list, &id_cache))
3544 silc_idcache_list_free(list);
3548 /* This function is used to announce our existing clients to our router
3549 when we've connected to it. If `creation_time' is non-zero then only
3550 the clients that has been created after the `creation_time' will be
3553 void silc_server_announce_clients(SilcServer server,
3554 unsigned long creation_time,
3555 SilcSocketConnection remote)
3557 SilcBuffer clients = NULL;
3558 SilcBuffer umodes = NULL;
3560 SILC_LOG_DEBUG(("Announcing clients"));
3562 /* Get clients in local list */
3563 silc_server_announce_get_clients(server, server->local_list,
3564 &clients, &umodes, creation_time);
3566 /* As router we announce our global list as well */
3567 if (server->server_type == SILC_ROUTER)
3568 silc_server_announce_get_clients(server, server->global_list,
3569 &clients, &umodes, creation_time);
3572 silc_buffer_push(clients, clients->data - clients->head);
3573 SILC_LOG_HEXDUMP(("clients"), clients->data, clients->len);
3575 /* Send the packet */
3576 silc_server_packet_send(server, remote,
3577 SILC_PACKET_NEW_ID, SILC_PACKET_FLAG_LIST,
3578 clients->data, clients->len, TRUE);
3580 silc_buffer_free(clients);
3584 silc_buffer_push(umodes, umodes->data - umodes->head);
3585 SILC_LOG_HEXDUMP(("umodes"), umodes->data, umodes->len);
3587 /* Send the packet */
3588 silc_server_packet_send(server, remote,
3589 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
3590 umodes->data, umodes->len, TRUE);
3592 silc_buffer_free(umodes);
3596 /* Returns channel's topic for announcing it */
3598 void silc_server_announce_get_channel_topic(SilcServer server,
3599 SilcChannelEntry channel,
3604 if (channel->topic) {
3605 chidp = silc_id_payload_encode(channel->id, SILC_ID_CHANNEL);
3606 *topic = silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_TOPIC_SET, 2,
3607 chidp->data, chidp->len,
3609 strlen(channel->topic));
3610 silc_buffer_free(chidp);
3614 /* Returns assembled packets for channel users of the `channel'. */
3616 void silc_server_announce_get_channel_users(SilcServer server,
3617 SilcChannelEntry channel,
3618 SilcBuffer *channel_modes,
3619 SilcBuffer *channel_users,
3620 SilcBuffer *channel_users_modes)
3622 SilcChannelClientEntry chl;
3623 SilcHashTableList htl;
3624 SilcBuffer chidp, clidp, csidp;
3627 unsigned char mode[4], *fkey = NULL;
3628 SilcUInt32 fkey_len = 0;
3631 SILC_LOG_DEBUG(("Start"));
3633 chidp = silc_id_payload_encode(channel->id, SILC_ID_CHANNEL);
3634 csidp = silc_id_payload_encode(server->id, SILC_ID_SERVER);
3637 SILC_PUT32_MSB(channel->mode, mode);
3638 hmac = channel->hmac ? (char *)silc_hmac_get_name(channel->hmac) : NULL;
3639 if (channel->founder_key)
3640 fkey = silc_pkcs_public_key_encode(channel->founder_key, &fkey_len);
3642 silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_CMODE_CHANGE,
3643 6, csidp->data, csidp->len,
3646 hmac, hmac ? strlen(hmac) : 0,
3647 channel->passphrase,
3648 channel->passphrase ?
3649 strlen(channel->passphrase) : 0,
3653 silc_buffer_realloc(*channel_modes,
3655 (*channel_modes)->truelen + len : len));
3656 silc_buffer_pull_tail(*channel_modes,
3657 ((*channel_modes)->end -
3658 (*channel_modes)->data));
3659 silc_buffer_put(*channel_modes, tmp->data, tmp->len);
3660 silc_buffer_pull(*channel_modes, len);
3661 silc_buffer_free(tmp);
3664 /* Now find all users on the channel */
3665 silc_hash_table_list(channel->user_list, &htl);
3666 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
3667 clidp = silc_id_payload_encode(chl->client->id, SILC_ID_CLIENT);
3670 tmp = silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_JOIN, 2,
3671 clidp->data, clidp->len,
3672 chidp->data, chidp->len);
3675 silc_buffer_realloc(*channel_users,
3677 (*channel_users)->truelen + len : len));
3678 silc_buffer_pull_tail(*channel_users,
3679 ((*channel_users)->end -
3680 (*channel_users)->data));
3682 silc_buffer_put(*channel_users, tmp->data, tmp->len);
3683 silc_buffer_pull(*channel_users, len);
3684 silc_buffer_free(tmp);
3686 /* CUMODE notify for mode change on the channel */
3687 SILC_PUT32_MSB(chl->mode, mode);
3688 if (chl->mode & SILC_CHANNEL_UMODE_CHANFO && channel->founder_key)
3689 fkey = silc_pkcs_public_key_encode(channel->founder_key, &fkey_len);
3690 tmp = silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_CUMODE_CHANGE,
3691 4, csidp->data, csidp->len,
3693 clidp->data, clidp->len,
3696 *channel_users_modes =
3697 silc_buffer_realloc(*channel_users_modes,
3698 (*channel_users_modes ?
3699 (*channel_users_modes)->truelen + len : len));
3700 silc_buffer_pull_tail(*channel_users_modes,
3701 ((*channel_users_modes)->end -
3702 (*channel_users_modes)->data));
3704 silc_buffer_put(*channel_users_modes, tmp->data, tmp->len);
3705 silc_buffer_pull(*channel_users_modes, len);
3706 silc_buffer_free(tmp);
3708 silc_buffer_free(clidp);
3710 silc_hash_table_list_reset(&htl);
3711 silc_buffer_free(chidp);
3712 silc_buffer_free(csidp);
3715 /* Returns assembled packets for all channels and users on those channels
3716 from the given ID List. The packets are in the form dictated by the
3717 New Channel and New Channel User payloads. */
3719 void silc_server_announce_get_channels(SilcServer server,
3721 SilcBuffer *channels,
3722 SilcBuffer **channel_modes,
3723 SilcBuffer *channel_users,
3724 SilcBuffer **channel_users_modes,
3725 SilcUInt32 *channel_users_modes_c,
3726 SilcBuffer **channel_topics,
3727 SilcChannelID ***channel_ids,
3728 unsigned long creation_time)
3730 SilcIDCacheList list;
3731 SilcIDCacheEntry id_cache;
3732 SilcChannelEntry channel;
3735 SilcUInt16 name_len;
3737 int i = *channel_users_modes_c;
3740 SILC_LOG_DEBUG(("Start"));
3742 /* Go through all channels in the list */
3743 if (silc_idcache_get_all(id_list->channels, &list)) {
3744 if (silc_idcache_list_first(list, &id_cache)) {
3746 channel = (SilcChannelEntry)id_cache->context;
3748 if (creation_time && channel->created < creation_time)
3753 cid = silc_id_id2str(channel->id, SILC_ID_CHANNEL);
3754 id_len = silc_id_get_len(channel->id, SILC_ID_CHANNEL);
3755 name_len = strlen(channel->channel_name);
3758 len = 4 + name_len + id_len + 4;
3760 silc_buffer_realloc(*channels,
3761 (*channels ? (*channels)->truelen +
3763 silc_buffer_pull_tail(*channels,
3764 ((*channels)->end - (*channels)->data));
3765 silc_buffer_format(*channels,
3766 SILC_STR_UI_SHORT(name_len),
3767 SILC_STR_UI_XNSTRING(channel->channel_name,
3769 SILC_STR_UI_SHORT(id_len),
3770 SILC_STR_UI_XNSTRING(cid, id_len),
3771 SILC_STR_UI_INT(channel->mode),
3773 silc_buffer_pull(*channels, len);
3776 /* Channel user modes */
3777 *channel_users_modes = silc_realloc(*channel_users_modes,
3778 sizeof(**channel_users_modes) *
3780 (*channel_users_modes)[i] = NULL;
3781 *channel_modes = silc_realloc(*channel_modes,
3782 sizeof(**channel_modes) * (i + 1));
3783 (*channel_modes)[i] = NULL;
3784 *channel_ids = silc_realloc(*channel_ids,
3785 sizeof(**channel_ids) * (i + 1));
3786 (*channel_ids)[i] = NULL;
3787 silc_server_announce_get_channel_users(server, channel,
3788 &(*channel_modes)[i],
3790 &(*channel_users_modes)[i]);
3791 (*channel_ids)[i] = channel->id;
3793 /* Channel's topic */
3794 *channel_topics = silc_realloc(*channel_topics,
3795 sizeof(**channel_topics) * (i + 1));
3796 (*channel_topics)[i] = NULL;
3797 silc_server_announce_get_channel_topic(server, channel,
3798 &(*channel_topics)[i]);
3801 if (!silc_idcache_list_next(list, &id_cache))
3805 *channel_users_modes_c += i;
3808 silc_idcache_list_free(list);
3812 /* This function is used to announce our existing channels to our router
3813 when we've connected to it. This also announces the users on the
3814 channels to the router. If the `creation_time' is non-zero only the
3815 channels that was created after the `creation_time' are announced.
3816 Note that the channel users are still announced even if the `creation_time'
3819 void silc_server_announce_channels(SilcServer server,
3820 unsigned long creation_time,
3821 SilcSocketConnection remote)
3823 SilcBuffer channels = NULL, *channel_modes = NULL, channel_users = NULL;
3824 SilcBuffer *channel_users_modes = NULL;
3825 SilcBuffer *channel_topics = NULL;
3826 SilcUInt32 channel_users_modes_c = 0;
3827 SilcChannelID **channel_ids = NULL;
3829 SILC_LOG_DEBUG(("Announcing channels and channel users"));
3831 /* Get channels and channel users in local list */
3832 silc_server_announce_get_channels(server, server->local_list,
3833 &channels, &channel_modes,
3835 &channel_users_modes,
3836 &channel_users_modes_c,
3838 &channel_ids, creation_time);
3840 /* Get channels and channel users in global list */
3841 if (server->server_type != SILC_SERVER)
3842 silc_server_announce_get_channels(server, server->global_list,
3843 &channels, &channel_modes,
3845 &channel_users_modes,
3846 &channel_users_modes_c,
3848 &channel_ids, creation_time);
3851 silc_buffer_push(channels, channels->data - channels->head);
3852 SILC_LOG_HEXDUMP(("channels"), channels->data, channels->len);
3854 /* Send the packet */
3855 silc_server_packet_send(server, remote,
3856 SILC_PACKET_NEW_CHANNEL, SILC_PACKET_FLAG_LIST,
3857 channels->data, channels->len,
3860 silc_buffer_free(channels);
3863 if (channel_modes) {
3866 for (i = 0; i < channel_users_modes_c; i++) {
3867 if (!channel_modes[i])
3869 silc_buffer_push(channel_modes[i],
3870 channel_modes[i]->data -
3871 channel_modes[i]->head);
3872 SILC_LOG_HEXDUMP(("channel modes"), channel_modes[i]->data,
3873 channel_modes[i]->len);
3874 silc_server_packet_send_dest(server, remote,
3875 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
3876 channel_ids[i], SILC_ID_CHANNEL,
3877 channel_modes[i]->data,
3878 channel_modes[i]->len,
3880 silc_buffer_free(channel_modes[i]);
3882 silc_free(channel_modes);
3885 if (channel_users) {
3886 silc_buffer_push(channel_users, channel_users->data - channel_users->head);
3887 SILC_LOG_HEXDUMP(("channel users"), channel_users->data,
3888 channel_users->len);
3890 /* Send the packet */
3891 silc_server_packet_send(server, remote,
3892 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
3893 channel_users->data, channel_users->len,
3896 silc_buffer_free(channel_users);
3899 if (channel_users_modes) {
3902 for (i = 0; i < channel_users_modes_c; i++) {
3903 if (!channel_users_modes[i])
3905 silc_buffer_push(channel_users_modes[i],
3906 channel_users_modes[i]->data -
3907 channel_users_modes[i]->head);
3908 SILC_LOG_HEXDUMP(("channel users modes"), channel_users_modes[i]->data,
3909 channel_users_modes[i]->len);
3910 silc_server_packet_send_dest(server, remote,
3911 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
3912 channel_ids[i], SILC_ID_CHANNEL,
3913 channel_users_modes[i]->data,
3914 channel_users_modes[i]->len,
3916 silc_buffer_free(channel_users_modes[i]);
3918 silc_free(channel_users_modes);
3921 if (channel_topics) {
3924 for (i = 0; i < channel_users_modes_c; i++) {
3925 if (!channel_topics[i])
3928 silc_buffer_push(channel_topics[i],
3929 channel_topics[i]->data -
3930 channel_topics[i]->head);
3931 SILC_LOG_HEXDUMP(("channel topic"), channel_topics[i]->data,
3932 channel_topics[i]->len);
3933 silc_server_packet_send_dest(server, remote,
3934 SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
3935 channel_ids[i], SILC_ID_CHANNEL,
3936 channel_topics[i]->data,
3937 channel_topics[i]->len,
3939 silc_buffer_free(channel_topics[i]);
3941 silc_free(channel_topics);
3944 silc_free(channel_ids);
3947 /* Failure timeout callback. If this is called then we will immediately
3948 process the received failure. We always process the failure with timeout
3949 since we do not want to blindly trust to received failure packets.
3950 This won't be called (the timeout is cancelled) if the failure was
3951 bogus (it is bogus if remote does not close the connection after sending
3954 SILC_TASK_CALLBACK(silc_server_failure_callback)
3956 SilcServerFailureContext f = (SilcServerFailureContext)context;
3958 if (f->sock->protocol) {
3959 f->sock->protocol->state = SILC_PROTOCOL_STATE_FAILURE;
3960 silc_protocol_execute(f->sock->protocol, f->server->schedule, 0, 0);
3966 /* Assembles user list and users mode list from the `channel'. */
3968 bool silc_server_get_users_on_channel(SilcServer server,
3969 SilcChannelEntry channel,
3970 SilcBuffer *user_list,
3971 SilcBuffer *mode_list,
3972 SilcUInt32 *user_count)
3974 SilcChannelClientEntry chl;
3975 SilcHashTableList htl;
3976 SilcBuffer client_id_list;
3977 SilcBuffer client_mode_list;
3979 SilcUInt32 list_count = 0, len = 0;
3981 if (!silc_hash_table_count(channel->user_list))
3984 silc_hash_table_list(channel->user_list, &htl);
3985 while (silc_hash_table_get(&htl, NULL, (void *)&chl))
3986 len += (silc_id_get_len(chl->client->id, SILC_ID_CLIENT) + 4);
3987 silc_hash_table_list_reset(&htl);
3989 client_id_list = silc_buffer_alloc(len);
3991 silc_buffer_alloc(4 * silc_hash_table_count(channel->user_list));
3992 silc_buffer_pull_tail(client_id_list, SILC_BUFFER_END(client_id_list));
3993 silc_buffer_pull_tail(client_mode_list, SILC_BUFFER_END(client_mode_list));
3995 silc_hash_table_list(channel->user_list, &htl);
3996 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
3998 idp = silc_id_payload_encode(chl->client->id, SILC_ID_CLIENT);
3999 silc_buffer_put(client_id_list, idp->data, idp->len);
4000 silc_buffer_pull(client_id_list, idp->len);
4001 silc_buffer_free(idp);
4003 /* Client's mode on channel */
4004 SILC_PUT32_MSB(chl->mode, client_mode_list->data);
4005 silc_buffer_pull(client_mode_list, 4);
4009 silc_hash_table_list_reset(&htl);
4010 silc_buffer_push(client_id_list,
4011 client_id_list->data - client_id_list->head);
4012 silc_buffer_push(client_mode_list,
4013 client_mode_list->data - client_mode_list->head);
4015 *user_list = client_id_list;
4016 *mode_list = client_mode_list;
4017 *user_count = list_count;
4021 /* Saves users and their modes to the `channel'. */
4023 void silc_server_save_users_on_channel(SilcServer server,
4024 SilcSocketConnection sock,
4025 SilcChannelEntry channel,
4026 SilcClientID *noadd,
4027 SilcBuffer user_list,
4028 SilcBuffer mode_list,
4029 SilcUInt32 user_count)
4034 SilcClientID *client_id;
4035 SilcClientEntry client;
4036 SilcIDCacheEntry cache;
4037 SilcChannelClientEntry chl;
4040 SILC_LOG_DEBUG(("Start"));
4042 for (i = 0; i < user_count; i++) {
4044 SILC_GET16_MSB(idp_len, user_list->data + 2);
4046 client_id = silc_id_payload_parse_id(user_list->data, idp_len, NULL);
4047 silc_buffer_pull(user_list, idp_len);
4052 SILC_GET32_MSB(mode, mode_list->data);
4053 silc_buffer_pull(mode_list, 4);
4055 if (noadd && SILC_ID_CLIENT_COMPARE(client_id, noadd)) {
4056 silc_free(client_id);
4062 /* Check if we have this client cached already. */
4063 client = silc_idlist_find_client_by_id(server->local_list, client_id,
4064 server->server_type, &cache);
4066 client = silc_idlist_find_client_by_id(server->global_list,
4067 client_id, server->server_type,
4072 /* If router did not find such Client ID in its lists then this must
4073 be bogus client or some router in the net is buggy. */
4074 if (server->server_type == SILC_ROUTER) {
4075 silc_free(client_id);
4079 /* We don't have that client anywhere, add it. The client is added
4080 to global list since server didn't have it in the lists so it must be
4082 client = silc_idlist_add_client(server->global_list, NULL, NULL, NULL,
4083 silc_id_dup(client_id, SILC_ID_CLIENT),
4084 sock->user_data, NULL, 0);
4086 SILC_LOG_ERROR(("Could not add new client to the ID Cache"));
4087 silc_free(client_id);
4091 client->data.status |= SILC_IDLIST_STATUS_REGISTERED;
4093 /* Found, if it is from global list we'll assure that we won't
4094 expire it now that the entry is on channel. */
4099 silc_free(client_id);
4101 if (!silc_server_client_on_channel(client, channel, &chl)) {
4102 /* Client was not on the channel, add it. */
4103 chl = silc_calloc(1, sizeof(*chl));
4104 chl->client = client;
4106 chl->channel = channel;
4107 silc_hash_table_add(channel->user_list, chl->client, chl);
4108 silc_hash_table_add(client->channels, chl->channel, chl);
4109 channel->user_count++;
4117 /* Saves channels and channels user modes to the `client'. Removes
4118 the client from those channels that are not sent in the list but
4121 void silc_server_save_user_channels(SilcServer server,
4122 SilcSocketConnection sock,
4123 SilcClientEntry client,
4124 SilcBuffer channels,
4125 SilcBuffer channels_user_modes)
4128 SilcUInt32 *chumodes;
4129 SilcChannelPayload entry;
4130 SilcChannelEntry channel;
4131 SilcChannelID *channel_id;
4132 SilcChannelClientEntry chl;
4133 SilcHashTable ht = NULL;
4134 SilcHashTableList htl;
4138 if (!channels ||!channels_user_modes)
4141 ch = silc_channel_payload_parse_list(channels->data, channels->len);
4142 if (ch && silc_get_mode_list(channels_user_modes, silc_dlist_count(ch),
4144 ht = silc_hash_table_alloc(0, silc_hash_ptr, NULL, NULL,
4145 NULL, NULL, NULL, TRUE);
4146 silc_dlist_start(ch);
4147 while ((entry = silc_dlist_get(ch)) != SILC_LIST_END) {
4148 /* Check if we have this channel, and add it if we don't have it.
4149 Also add the client on the channel unless it is there already. */
4150 channel_id = silc_channel_get_id_parse(entry);
4151 channel = silc_idlist_find_channel_by_id(server->local_list,
4154 channel = silc_idlist_find_channel_by_id(server->global_list,
4157 if (server->server_type != SILC_SERVER) {
4158 silc_free(channel_id);
4163 /* We don't have that channel anywhere, add it. */
4164 name = silc_channel_get_name(entry, NULL);
4165 channel = silc_idlist_add_channel(server->global_list, strdup(name), 0,
4166 channel_id, server->router,
4169 silc_free(channel_id);
4176 channel->mode = silc_channel_get_mode(entry);
4178 /* Add the client on the channel */
4179 if (!silc_server_client_on_channel(client, channel, &chl)) {
4180 chl = silc_calloc(1, sizeof(*chl));
4181 chl->client = client;
4182 chl->mode = chumodes[i++];
4183 chl->channel = channel;
4184 silc_hash_table_add(channel->user_list, chl->client, chl);
4185 silc_hash_table_add(client->channels, chl->channel, chl);
4186 channel->user_count++;
4189 chl->mode = chumodes[i++];
4192 silc_hash_table_add(ht, channel, channel);
4193 silc_free(channel_id);
4195 silc_channel_payload_list_free(ch);
4196 silc_free(chumodes);
4200 /* Go through the list again and remove client from channels that
4201 are no part of the list. */
4203 silc_hash_table_list(client->channels, &htl);
4204 while (silc_hash_table_get(&htl, NULL, (void **)&chl)) {
4205 if (!silc_hash_table_find(ht, chl->channel, NULL, NULL)) {
4206 silc_hash_table_del(chl->channel->user_list, chl->client);
4207 silc_hash_table_del(chl->client->channels, chl->channel);
4211 silc_hash_table_list_reset(&htl);
4212 silc_hash_table_free(ht);
4214 silc_hash_table_list(client->channels, &htl);
4215 while (silc_hash_table_get(&htl, NULL, (void **)&chl)) {
4216 silc_hash_table_del(chl->channel->user_list, chl->client);
4217 silc_hash_table_del(chl->client->channels, chl->channel);
4220 silc_hash_table_list_reset(&htl);
4224 /* Lookups route to the client indicated by the `id_data'. The connection
4225 object and internal data object is returned. Returns NULL if route
4226 could not be found to the client. If the `client_id' is specified then
4227 it is used and the `id_data' is ignored. */
4229 SilcSocketConnection
4230 silc_server_get_client_route(SilcServer server,
4231 unsigned char *id_data,
4233 SilcClientID *client_id,
4234 SilcIDListData *idata,
4235 SilcClientEntry *client_entry)
4238 SilcClientEntry client;
4240 SILC_LOG_DEBUG(("Start"));
4243 *client_entry = NULL;
4245 /* Decode destination Client ID */
4247 id = silc_id_str2id(id_data, id_len, SILC_ID_CLIENT);
4249 SILC_LOG_ERROR(("Could not decode destination Client ID, dropped"));
4253 id = silc_id_dup(client_id, SILC_ID_CLIENT);
4256 /* If the destination belongs to our server we don't have to route
4257 the packet anywhere but to send it to the local destination. */
4258 client = silc_idlist_find_client_by_id(server->local_list, id, TRUE, NULL);
4262 /* If we are router and the client has router then the client is in
4263 our cell but not directly connected to us. */
4264 if (server->server_type == SILC_ROUTER && client->router) {
4265 /* We are of course in this case the client's router thus the route
4266 to the client is the server who owns the client. So, we will send
4267 the packet to that server. */
4269 *idata = (SilcIDListData)client->router;
4270 return client->router->connection;
4273 /* Seems that client really is directly connected to us */
4275 *idata = (SilcIDListData)client;
4277 *client_entry = client;
4278 return client->connection;
4281 /* Destination belongs to someone not in this server. If we are normal
4282 server our action is to send the packet to our router. */
4283 if (server->server_type != SILC_ROUTER && !server->standalone) {
4286 *idata = (SilcIDListData)server->router;
4287 return server->router->connection;
4290 /* We are router and we will perform route lookup for the destination
4291 and send the packet to fastest route. */
4292 if (server->server_type == SILC_ROUTER && !server->standalone) {
4293 /* Check first that the ID is valid */
4294 client = silc_idlist_find_client_by_id(server->global_list, id,
4297 SilcSocketConnection dst_sock;
4299 dst_sock = silc_server_route_get(server, id, SILC_ID_CLIENT);
4303 *idata = (SilcIDListData)dst_sock->user_data;
4312 /* Encodes and returns channel list of channels the `client' has joined.
4313 Secret channels are not put to the list. */
4315 SilcBuffer silc_server_get_client_channel_list(SilcServer server,
4316 SilcClientEntry client,
4319 SilcBuffer *user_mode_list)
4321 SilcBuffer buffer = NULL;
4322 SilcChannelEntry channel;
4323 SilcChannelClientEntry chl;
4324 SilcHashTableList htl;
4327 SilcUInt16 name_len;
4331 *user_mode_list = NULL;
4333 silc_hash_table_list(client->channels, &htl);
4334 while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
4335 channel = chl->channel;
4337 if (channel->mode & SILC_CHANNEL_MODE_SECRET && !get_secret)
4339 if (channel->mode & SILC_CHANNEL_MODE_PRIVATE && !get_private)
4342 cid = silc_id_id2str(channel->id, SILC_ID_CHANNEL);
4343 id_len = silc_id_get_len(channel->id, SILC_ID_CHANNEL);
4344 name_len = strlen(channel->channel_name);
4346 len = 4 + name_len + id_len + 4;
4347 buffer = silc_buffer_realloc(buffer,
4348 (buffer ? buffer->truelen + len : len));
4349 silc_buffer_pull_tail(buffer, (buffer->end - buffer->data));
4350 silc_buffer_format(buffer,
4351 SILC_STR_UI_SHORT(name_len),
4352 SILC_STR_UI_XNSTRING(channel->channel_name,
4354 SILC_STR_UI_SHORT(id_len),
4355 SILC_STR_UI_XNSTRING(cid, id_len),
4356 SILC_STR_UI_INT(chl->channel->mode),
4358 silc_buffer_pull(buffer, len);
4361 if (user_mode_list) {
4362 *user_mode_list = silc_buffer_realloc(*user_mode_list,
4364 (*user_mode_list)->truelen + 4 :
4366 silc_buffer_pull_tail(*user_mode_list, ((*user_mode_list)->end -
4367 (*user_mode_list)->data));
4368 SILC_PUT32_MSB(chl->mode, (*user_mode_list)->data);
4369 silc_buffer_pull(*user_mode_list, 4);
4372 silc_hash_table_list_reset(&htl);
4375 silc_buffer_push(buffer, buffer->data - buffer->head);
4376 if (user_mode_list && *user_mode_list)
4377 silc_buffer_push(*user_mode_list, ((*user_mode_list)->data -
4378 (*user_mode_list)->head));
4383 /* Finds client entry by Client ID and if it is not found then resolves
4384 it using WHOIS command. */
4386 SilcClientEntry silc_server_get_client_resolve(SilcServer server,
4387 SilcClientID *client_id,
4388 bool always_resolve,
4391 SilcClientEntry client;
4396 client = silc_idlist_find_client_by_id(server->local_list, client_id,
4399 client = silc_idlist_find_client_by_id(server->global_list,
4400 client_id, TRUE, NULL);
4401 if (!client && server->server_type == SILC_ROUTER)
4405 if (!client && server->standalone)
4408 if (!client || !client->nickname || !client->username ||
4410 SilcBuffer buffer, idp;
4413 client->data.status |= SILC_IDLIST_STATUS_RESOLVING;
4414 client->data.status &= ~SILC_IDLIST_STATUS_RESOLVED;
4415 client->resolve_cmd_ident = ++server->cmd_ident;
4418 idp = silc_id_payload_encode(client_id, SILC_ID_CLIENT);
4419 buffer = silc_command_payload_encode_va(SILC_COMMAND_WHOIS,
4420 server->cmd_ident, 1,
4421 4, idp->data, idp->len);
4422 silc_server_packet_send(server, client ? client->router->connection :
4423 server->router->connection,
4424 SILC_PACKET_COMMAND, 0,
4425 buffer->data, buffer->len, FALSE);
4426 silc_buffer_free(idp);
4427 silc_buffer_free(buffer);
4438 /* A timeout callback for the re-key. We will be the initiator of the
4441 SILC_TASK_CALLBACK(silc_server_rekey_callback)
4443 SilcSocketConnection sock = (SilcSocketConnection)context;
4444 SilcIDListData idata = (SilcIDListData)sock->user_data;
4445 SilcServer server = (SilcServer)idata->rekey->context;
4446 SilcProtocol protocol;
4447 SilcServerRekeyInternalContext *proto_ctx;
4449 SILC_LOG_DEBUG(("Start"));
4451 /* Allocate internal protocol context. This is sent as context
4453 proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
4454 proto_ctx->server = (void *)server;
4455 proto_ctx->sock = sock;
4456 proto_ctx->responder = FALSE;
4457 proto_ctx->pfs = idata->rekey->pfs;
4459 /* Perform rekey protocol. Will call the final callback after the
4460 protocol is over. */
4461 silc_protocol_alloc(SILC_PROTOCOL_SERVER_REKEY,
4462 &protocol, proto_ctx, silc_server_rekey_final);
4463 sock->protocol = protocol;
4465 /* Run the protocol */
4466 silc_protocol_execute(protocol, server->schedule, 0, 0);
4468 /* Re-register re-key timeout */
4469 silc_schedule_task_add(server->schedule, sock->sock,
4470 silc_server_rekey_callback,
4471 context, idata->rekey->timeout, 0,
4472 SILC_TASK_TIMEOUT, SILC_TASK_PRI_NORMAL);
4475 /* The final callback for the REKEY protocol. This will actually take the
4476 new key material into use. */
4478 SILC_TASK_CALLBACK_GLOBAL(silc_server_rekey_final)
4480 SilcProtocol protocol = (SilcProtocol)context;
4481 SilcServerRekeyInternalContext *ctx =
4482 (SilcServerRekeyInternalContext *)protocol->context;
4483 SilcServer server = (SilcServer)ctx->server;
4484 SilcSocketConnection sock = ctx->sock;
4486 SILC_LOG_DEBUG(("Start"));
4488 if (protocol->state == SILC_PROTOCOL_STATE_ERROR ||
4489 protocol->state == SILC_PROTOCOL_STATE_FAILURE) {
4490 /* Error occured during protocol */
4491 SILC_LOG_ERROR(("Error occurred during rekey protocol"));
4492 silc_protocol_cancel(protocol, server->schedule);
4493 silc_protocol_free(protocol);
4494 sock->protocol = NULL;
4496 silc_packet_context_free(ctx->packet);
4498 silc_ske_free(ctx->ske);
4503 /* Purge the outgoing data queue to assure that all rekey packets really
4504 go to the network before we quit the protocol. */
4505 silc_server_packet_queue_purge(server, sock);
4508 silc_protocol_free(protocol);
4509 sock->protocol = NULL;
4511 silc_packet_context_free(ctx->packet);
4513 silc_ske_free(ctx->ske);
4517 /* Task callback used to retrieve network statistical information from
4518 router server once in a while. */
4520 SILC_TASK_CALLBACK(silc_server_get_stats)
4522 SilcServer server = (SilcServer)context;
4523 SilcBuffer idp, packet;
4525 SILC_LOG_DEBUG(("Retrieving stats from router"));
4527 if (!server->standalone) {
4528 idp = silc_id_payload_encode(server->router->id, SILC_ID_SERVER);
4529 packet = silc_command_payload_encode_va(SILC_COMMAND_STATS,
4530 ++server->cmd_ident, 1,
4531 1, idp->data, idp->len);
4532 silc_server_packet_send(server, server->router->connection,
4533 SILC_PACKET_COMMAND, 0, packet->data,
4534 packet->len, FALSE);
4535 silc_buffer_free(packet);
4536 silc_buffer_free(idp);
4539 silc_schedule_task_add(server->schedule, 0, silc_server_get_stats,
4540 server, 120, 0, SILC_TASK_TIMEOUT,