05323399eda32a43a8612d13898fbf6f42f15bef
[silc.git] / apps / silcd / server.c
1 /*
2
3   server.c
4
5   Author: Pekka Riikonen <priikone@silcnet.org>
6
7   Copyright (C) 1997 - 2001 Pekka Riikonen
8
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.
13   
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.
18
19 */
20 /*
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.
24  */
25 /* $Id$ */
26
27 #include "serverincludes.h"
28 #include "server_internal.h"
29
30 /* Static prototypes */
31 SILC_TASK_CALLBACK(silc_server_connect_router);
32 SILC_TASK_CALLBACK(silc_server_connect_to_router);
33 SILC_TASK_CALLBACK(silc_server_connect_to_router_second);
34 SILC_TASK_CALLBACK(silc_server_connect_to_router_final);
35 SILC_TASK_CALLBACK(silc_server_accept_new_connection);
36 SILC_TASK_CALLBACK(silc_server_accept_new_connection_second);
37 SILC_TASK_CALLBACK(silc_server_accept_new_connection_final);
38 SILC_TASK_CALLBACK(silc_server_packet_process);
39 SILC_TASK_CALLBACK(silc_server_packet_parse_real);
40 SILC_TASK_CALLBACK(silc_server_timeout_remote);
41 SILC_TASK_CALLBACK(silc_server_failure_callback);
42 SILC_TASK_CALLBACK(silc_server_rekey_callback);
43
44 /* Allocates a new SILC server object. This has to be done before the server
45    can be used. After allocation one must call silc_server_init to initialize
46    the server. The new allocated server object is returned to the new_server
47    argument. */
48
49 int silc_server_alloc(SilcServer *new_server)
50 {
51   SilcServer server;
52
53   SILC_LOG_DEBUG(("Allocating new server object"));
54
55   server = silc_calloc(1, sizeof(*server));
56   server->server_type = SILC_SERVER;
57   server->standalone = TRUE;
58   server->local_list = silc_calloc(1, sizeof(*server->local_list));
59   server->global_list = silc_calloc(1, sizeof(*server->global_list));
60   server->pending_commands = silc_dlist_init();
61 #ifdef SILC_SIM
62   server->sim = silc_dlist_init();
63 #endif
64
65   *new_server = server;
66
67   return TRUE;
68 }
69
70 /* Free's the SILC server object. This is called at the very end before
71    the program ends. */
72
73 void silc_server_free(SilcServer server)
74 {
75   if (server) {
76 #ifdef SILC_SIM
77     SilcSimContext *sim;
78 #endif
79
80     silc_free(server->local_list);
81     silc_free(server->global_list);
82     if (server->rng)
83       silc_rng_free(server->rng);
84
85     if (server->pkcs)
86       silc_pkcs_free(server->pkcs);
87
88 #ifdef SILC_SIM
89     while ((sim = silc_dlist_get(server->sim)) != SILC_LIST_END) {
90       silc_dlist_del(server->sim, sim);
91       silc_sim_free(sim);
92     }
93     silc_dlist_uninit(server->sim);
94 #endif
95
96     silc_free(server->params);
97
98     if (server->pending_commands)
99       silc_dlist_uninit(server->pending_commands);
100
101     silc_free(server);
102   }
103 }
104
105 /* Initializes the entire SILC server. This is called always before running
106    the server. This is called only once at the initialization of the program.
107    This binds the server to its listenning port. After this function returns 
108    one should call silc_server_run to start the server. This returns TRUE 
109    when everything is ok to run the server. Configuration file must be
110    read and parsed before calling this. */
111
112 int silc_server_init(SilcServer server)
113 {
114   int *sock = NULL, sock_count = 0, i;
115   SilcServerID *id;
116   SilcServerEntry id_entry;
117   SilcIDListPurge purge;
118   SilcServerConfigSectionListenPort *listen;
119
120   SILC_LOG_DEBUG(("Initializing server"));
121   assert(server);
122   assert(server->config);
123
124   /* Set public and private keys */
125   if (!server->config->server_keys ||
126       !server->config->server_keys->public_key || 
127       !server->config->server_keys->private_key) {
128     SILC_LOG_ERROR(("Server public key and/or private key does not exist"));
129     return FALSE;
130   }
131   server->public_key = server->config->server_keys->public_key;
132   server->private_key = server->config->server_keys->private_key;
133
134   /* XXX After server is made as Silc Server Library this can be given
135      as argument, for now this is hard coded */
136   server->params = silc_calloc(1, sizeof(*server->params));
137   server->params->retry_count = SILC_SERVER_RETRY_COUNT;
138   server->params->retry_interval_min = SILC_SERVER_RETRY_INTERVAL_MIN;
139   server->params->retry_interval_max = SILC_SERVER_RETRY_INTERVAL_MAX;
140   server->params->retry_keep_trying = FALSE;
141   server->params->protocol_timeout = 60;
142   server->params->require_reverse_mapping = FALSE;
143
144   /* Set log files where log message should be saved. */
145   server->config->server = server;
146   silc_server_config_setlogfiles(server->config);
147  
148   /* Register all configured ciphers, PKCS and hash functions. */
149   if (!silc_server_config_register_ciphers(server->config))
150     silc_cipher_register_default();
151   if (!silc_server_config_register_pkcs(server->config))
152     silc_pkcs_register_default();
153   if (!silc_server_config_register_hashfuncs(server->config))
154     silc_hash_register_default();
155   if (!silc_server_config_register_hmacs(server->config))
156     silc_hmac_register_default();
157
158   /* Initialize random number generator for the server. */
159   server->rng = silc_rng_alloc();
160   silc_rng_init(server->rng);
161   silc_rng_global_init(server->rng);
162
163   /* Initialize hash functions for server to use */
164   silc_hash_alloc("md5", &server->md5hash);
165   silc_hash_alloc("sha1", &server->sha1hash);
166
167   /* Initialize none cipher */
168   silc_cipher_alloc("none", &server->none_cipher);
169
170   /* Allocate PKCS context for local public and private keys */
171   silc_pkcs_alloc(server->public_key->name, &server->pkcs);
172   silc_pkcs_public_key_set(server->pkcs, server->public_key);
173   silc_pkcs_private_key_set(server->pkcs, server->private_key);
174
175   /* Create a listening server. Note that our server can listen on multiple
176      ports. All listeners are created here and now. */
177   sock_count = 0;
178   listen = server->config->listen_port;
179   while(listen) {
180     int tmp;
181
182     tmp = silc_net_create_server(server->config->listen_port->port,
183                                  server->config->listen_port->listener_ip);
184     if (tmp < 0)
185       goto err0;
186
187     sock = silc_realloc(sock, (sizeof(int *) * (sock_count + 1)));
188     sock[sock_count] = tmp;
189     sock_count++;
190     listen = listen->next;
191   }
192
193   /* Initialize ID caches */
194   server->local_list->clients = 
195     silc_idcache_alloc(0, SILC_ID_CLIENT, silc_idlist_client_destructor);
196   server->local_list->servers = silc_idcache_alloc(0, SILC_ID_SERVER, NULL);
197   server->local_list->channels = silc_idcache_alloc(0, SILC_ID_CHANNEL, NULL);
198
199   /* These are allocated for normal server as well as these hold some 
200      global information that the server has fetched from its router. For 
201      router these are used as they are supposed to be used on router. */
202   server->global_list->clients = 
203     silc_idcache_alloc(0, SILC_ID_CLIENT, silc_idlist_client_destructor);
204   server->global_list->servers = silc_idcache_alloc(0, SILC_ID_SERVER, NULL);
205   server->global_list->channels = silc_idcache_alloc(0, SILC_ID_CHANNEL, NULL);
206
207   /* Allocate the entire socket list that is used in server. Eventually 
208      all connections will have entry in this table (it is a table of 
209      pointers to the actual object that is allocated individually 
210      later). */
211   server->sockets = silc_calloc(SILC_SERVER_MAX_CONNECTIONS,
212                                 sizeof(*server->sockets));
213
214   for (i = 0; i < sock_count; i++) {
215     SilcSocketConnection newsocket = NULL;
216
217     /* Set socket to non-blocking mode */
218     silc_net_set_socket_nonblock(sock[i]);
219     server->sock = sock[i];
220     
221     /* Create a Server ID for the server. */
222     silc_id_create_server_id(sock[i], server->rng, &id);
223     if (!id) {
224       goto err0;
225     }
226     
227     server->id = id;
228     server->id_string = silc_id_id2str(id, SILC_ID_SERVER);
229     server->id_string_len = silc_id_get_len(id, SILC_ID_SERVER);
230     server->id_type = SILC_ID_SERVER;
231     server->server_name = server->config->server_info->server_name;
232
233     /* Add ourselves to the server list. We don't have a router yet 
234        beacuse we haven't established a route yet. It will be done later. 
235        For now, NULL is sent as router. This allocates new entry to
236        the ID list. */
237     id_entry = 
238       silc_idlist_add_server(server->local_list,
239                              server->config->server_info->server_name,
240                              server->server_type, server->id, NULL, NULL);
241     if (!id_entry) {
242       SILC_LOG_ERROR(("Could not add ourselves to cache"));
243       goto err0;
244     }
245     id_entry->data.status |= SILC_IDLIST_STATUS_REGISTERED;
246     
247     /* Add ourselves also to the socket table. The entry allocated above
248        is sent as argument for fast referencing in the future. */
249     silc_socket_alloc(sock[i], SILC_SOCKET_TYPE_SERVER, id_entry, 
250                       &newsocket);
251
252     server->sockets[sock[i]] = newsocket;
253     
254     /* Perform name and address lookups to resolve the listenning address
255        and port. */
256     if (!silc_net_check_local_by_sock(sock[i], &newsocket->hostname, 
257                                      &newsocket->ip)) {
258       if ((server->params->require_reverse_mapping && !newsocket->hostname) ||
259           !newsocket->ip) {
260         SILC_LOG_ERROR(("IP/DNS lookup failed for local host %s",
261                         newsocket->hostname ? newsocket->hostname :
262                         newsocket->ip ? newsocket->ip : ""));
263         server->stat.conn_failures++;
264         goto err0;
265       }
266       if (!newsocket->hostname)
267         newsocket->hostname = strdup(newsocket->ip);
268     }
269     newsocket->port = silc_net_get_local_port(sock[i]);
270
271     /* Put the allocated socket pointer also to the entry allocated above 
272        for fast back-referencing to the socket list. */
273     id_entry->connection = (void *)server->sockets[sock[i]];
274     server->id_entry = id_entry;
275   }
276
277   /* Register protocols */
278   silc_server_protocols_register();
279
280   /* Initialize the scheduler. */
281   server->schedule = silc_schedule_init(SILC_SERVER_MAX_CONNECTIONS);
282   if (!server->schedule)
283     goto err0;
284   
285   /* Add the first task to the scheduler. This is task that is executed by
286      timeout. It expires as soon as the caller calls silc_server_run. This
287      task performs authentication protocol and key exchange with our
288      primary router. */
289   silc_schedule_task_add(server->schedule, sock[0], 
290                          silc_server_connect_to_router,
291                          (void *)server, 0, 1,
292                          SILC_TASK_TIMEOUT,
293                          SILC_TASK_PRI_NORMAL);
294
295   /* Add listener task to the scheduler. This task receives new connections
296      to the server. This task remains on the queue until the end of the 
297      program. */
298   silc_schedule_task_add(server->schedule, sock[0],
299                          silc_server_accept_new_connection,
300                          (void *)server, 0, 0, 
301                          SILC_TASK_FD,
302                          SILC_TASK_PRI_NORMAL);
303   server->listenning = TRUE;
304
305   /* If server connections has been configured then we must be router as
306      normal server cannot have server connections, only router connections. */
307   if (server->config->servers) {
308     SilcServerConfigSectionServerConnection *ptr = server->config->servers;
309
310     server->server_type = SILC_ROUTER;
311     while (ptr) {
312       if (ptr->backup_router) {
313         server->server_type = SILC_BACKUP_ROUTER;
314         server->backup_router = TRUE;
315         break;
316       }
317       ptr = ptr->next;
318     }
319   }
320
321   /* Register the ID Cache purge task. This periodically purges the ID cache
322      and removes the expired cache entries. */
323
324   /* Clients local list */
325   purge = silc_calloc(1, sizeof(*purge));
326   purge->cache = server->local_list->clients;
327   purge->schedule = server->schedule;
328   silc_schedule_task_add(purge->schedule, 0, 
329                          silc_idlist_purge,
330                          (void *)purge, 600, 0,
331                          SILC_TASK_TIMEOUT, SILC_TASK_PRI_LOW);
332
333   /* Clients global list */
334   purge = silc_calloc(1, sizeof(*purge));
335   purge->cache = server->global_list->clients;
336   purge->schedule = server->schedule;
337   silc_schedule_task_add(purge->schedule, 0, 
338                          silc_idlist_purge,
339                          (void *)purge, 300, 0,
340                          SILC_TASK_TIMEOUT, SILC_TASK_PRI_LOW);
341
342   SILC_LOG_DEBUG(("Server initialized"));
343
344   /* We are done here, return succesfully */
345   return TRUE;
346
347  err0:
348   for (i = 0; i < sock_count; i++)
349     silc_net_close_server(sock[i]);
350
351   return FALSE;
352 }
353
354 /* Fork server to background and set gid+uid to non-root.
355    Silcd will not run as root, so trying to set either user or group to
356    root will cause silcd to exit. */
357
358 void silc_server_daemonise(SilcServer server)
359 {
360   /* Are we executing silcd as root or a regular user? */
361   if (geteuid()==0) {
362     
363     struct passwd *pw;
364     struct group *gr;
365     char *user, *group;
366     
367     if (!server->config->identity || !server->config->identity->user || 
368         !server->config->identity->group) {
369       fprintf(stderr, "Error:"
370        "\tSILC server must not be run as root.  For the security of your\n"
371        "\tsystem it is strongly suggested that you run SILC under dedicated\n"
372        "\tuser account.  Modify the [Identity] configuration section to run\n"
373        "\tthe server as non-root user.\n");
374       exit(1);
375     }
376     
377     /* Get the values given for user and group in configuration file */
378     user=server->config->identity->user;
379     group=server->config->identity->group;
380     
381     /* Check whether the user/group information is text */ 
382     if (atoi(user)!=0 || atoi(group)!=0) {
383       SILC_LOG_DEBUG(("Invalid user and/or group information"));
384       SILC_LOG_DEBUG(("User and/or group given as number"));
385       fprintf(stderr, "Invalid user and/or group information\n");
386       fprintf(stderr, "Please assign them as names, not numbers\n");
387       exit(1);
388     }
389     
390     /* Catch the nasty incident of string "0" returning 0 from atoi */
391     if (strcmp("0", user)==0 || strcmp("0", group)==0) {
392       SILC_LOG_DEBUG(("User and/or group configured to 0. Unacceptable"));
393       fprintf(stderr, "User and/or group configured to 0. Exiting\n");
394       exit(1);
395     }
396     
397     pw=getpwnam(user);
398     gr=getgrnam(group);
399
400     if (!pw) {
401       fprintf(stderr, "No such user %s found\n", user);
402       exit(1);
403     }
404
405     if (!gr) {
406       fprintf(stderr, "No such group %s found\n", group);
407       exit(1);
408     }
409     
410     /* Check whether user and/or group is set to root. If yes, exit
411        immediately. Otherwise, setgid and setuid server to user.group */
412     if (gr->gr_gid==0 || pw->pw_uid==0) {
413       fprintf(stderr, "Error:"
414        "\tSILC server must not be run as root.  For the security of your\n"
415        "\tsystem it is strongly suggested that you run SILC under dedicated\n"
416        "\tuser account.  Modify the [Identity] configuration section to run\n"
417        "\tthe server as non-root user.\n");
418       exit(1);
419     } else {
420       /* Fork server to background, making it a daemon */
421       if (fork()) {
422         SILC_LOG_DEBUG(("Server started as root. Dropping privileges."));
423         SILC_LOG_DEBUG(("Forking SILC server to background"));
424         exit(0);
425       } 
426       setsid();
427       
428       SILC_LOG_DEBUG(("Changing to group %s", group));
429       if(setgid(gr->gr_gid)==0) {
430         SILC_LOG_DEBUG(("Setgid to %s", group));
431       } else {
432         SILC_LOG_DEBUG(("Setgid to %s failed", group));
433         fprintf(stderr, "Tried to setgid %s but no such group. Exiting\n",
434                 group);
435         exit(1);
436       }
437       SILC_LOG_DEBUG(("Changing to user nobody"));
438       if(setuid(pw->pw_uid)==0) {
439         SILC_LOG_DEBUG(("Setuid to %s", user));
440       } else {
441         SILC_LOG_DEBUG(("Setuid to %s failed", user));
442         fprintf(stderr, "Tried to setuid %s but no such user. Exiting\n",
443                 user);
444         exit(1);
445       }
446     }
447   } else {
448     /* Fork server to background, making it a daemon */
449     if (fork()) {
450       SILC_LOG_DEBUG(("Server started as user")); 
451       SILC_LOG_DEBUG(("Forking SILC server to background"));
452       exit(0);
453     }
454     setsid();
455   }
456 }
457
458 /* The heart of the server. This runs the scheduler thus runs the server. 
459    When this returns the server has been stopped and the program will
460    be terminated. */
461
462 void silc_server_run(SilcServer server)
463 {
464   SILC_LOG_DEBUG(("Running server"));
465
466   SILC_LOG_INFO(("SILC Server started"));
467
468   /* Start the scheduler, the heart of the SILC server. When this returns
469      the program will be terminated. */
470   silc_schedule(server->schedule);
471 }
472
473 /* Stops the SILC server. This function is used to shutdown the server. 
474    This is usually called after the scheduler has returned. After stopping 
475    the server one should call silc_server_free. */
476
477 void silc_server_stop(SilcServer server)
478 {
479   SILC_LOG_DEBUG(("Stopping server"));
480
481   silc_schedule_stop(server->schedule);
482   silc_schedule_uninit(server->schedule);
483
484   silc_server_protocols_unregister();
485
486   SILC_LOG_DEBUG(("Server stopped"));
487 }
488
489 /* Function that is called when the network connection to a router has
490    been established.  This will continue with the key exchange protocol
491    with the remote router. */
492
493 void silc_server_start_key_exchange(SilcServer server,
494                                     SilcServerConnection sconn,
495                                     int sock)
496 {
497   SilcSocketConnection newsocket;
498   SilcProtocol protocol;
499   SilcServerKEInternalContext *proto_ctx;
500   void *context;
501
502   /* Set socket options */
503   silc_net_set_socket_nonblock(sock);
504   silc_net_set_socket_opt(sock, SOL_SOCKET, SO_REUSEADDR, 1);
505
506   /* Create socket connection for the connection. Even though we
507      know that we are connecting to a router we will mark the socket
508      to be unknown connection until we have executed authentication
509      protocol. */
510   silc_socket_alloc(sock, SILC_SOCKET_TYPE_UNKNOWN, NULL, &newsocket);
511   server->sockets[sock] = newsocket;
512   newsocket->hostname = strdup(sconn->remote_host);
513   newsocket->ip = strdup(sconn->remote_host);
514   newsocket->port = sconn->remote_port;
515   sconn->sock = newsocket;
516
517   /* Allocate internal protocol context. This is sent as context
518      to the protocol. */
519   proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
520   proto_ctx->server = (void *)server;
521   proto_ctx->context = (void *)sconn;
522   proto_ctx->sock = newsocket;
523   proto_ctx->rng = server->rng;
524   proto_ctx->responder = FALSE;
525       
526   /* Perform key exchange protocol. silc_server_connect_to_router_second
527      will be called after the protocol is finished. */
528   silc_protocol_alloc(SILC_PROTOCOL_SERVER_KEY_EXCHANGE, 
529                       &protocol, proto_ctx,
530                       silc_server_connect_to_router_second);
531   newsocket->protocol = protocol;
532       
533   /* Register a timeout task that will be executed if the protocol
534      is not executed within set limit. */
535   proto_ctx->timeout_task = 
536     silc_schedule_task_add(server->schedule, sock, 
537                        silc_server_timeout_remote,
538                        server, server->params->protocol_timeout,
539                        server->params->protocol_timeout_usec,
540                        SILC_TASK_TIMEOUT,
541                        SILC_TASK_PRI_LOW);
542
543   /* Register the connection for network input and output. This sets
544      that scheduler will listen for incoming packets for this connection 
545      and sets that outgoing packets may be sent to this connection as 
546      well. However, this doesn't set the scheduler for outgoing traffic,
547      it will be set separately by calling SILC_SET_CONNECTION_FOR_OUTPUT,
548      later when outgoing data is available. */
549   context = (void *)server;
550   SILC_REGISTER_CONNECTION_FOR_IO(sock);
551   
552   /* Run the protocol */
553   silc_protocol_execute(protocol, server->schedule, 0, 0);
554 }
555
556 /* Timeout callback that will be called to retry connecting to remote
557    router. This is used by both normal and router server. This will wait
558    before retrying the connecting. The timeout is generated by exponential
559    backoff algorithm. */
560
561 SILC_TASK_CALLBACK(silc_server_connect_to_router_retry)
562 {
563   SilcServerConnection sconn = (SilcServerConnection)context;
564   SilcServer server = sconn->server;
565
566   SILC_LOG_INFO(("Retrying connecting to a router"));
567
568   /* Calculate next timeout */
569   if (sconn->retry_count >= 1) {
570     sconn->retry_timeout = sconn->retry_timeout * SILC_SERVER_RETRY_MULTIPLIER;
571     if (sconn->retry_timeout > SILC_SERVER_RETRY_INTERVAL_MAX)
572       sconn->retry_timeout = SILC_SERVER_RETRY_INTERVAL_MAX;
573   } else {
574     sconn->retry_timeout = server->params->retry_interval_min;
575   }
576   sconn->retry_count++;
577   sconn->retry_timeout = sconn->retry_timeout +
578     silc_rng_get_rn32(server->rng) % SILC_SERVER_RETRY_RANDOMIZER;
579
580   /* If we've reached max retry count, give up. */
581   if (sconn->retry_count > server->params->retry_count && 
582       server->params->retry_keep_trying == FALSE) {
583     SILC_LOG_ERROR(("Could not connect to router, giving up"));
584     return;
585   }
586
587   /* Wait one before retrying */
588   silc_schedule_task_add(server->schedule, fd, silc_server_connect_router,
589                          context, sconn->retry_timeout, 
590                          server->params->retry_interval_min_usec,
591                          SILC_TASK_TIMEOUT, SILC_TASK_PRI_NORMAL);
592 }
593
594 /* Generic routine to use connect to a router. */
595
596 SILC_TASK_CALLBACK(silc_server_connect_router)
597 {    
598   SilcServerConnection sconn = (SilcServerConnection)context;
599   SilcServer server = sconn->server;
600   int sock;
601
602   SILC_LOG_INFO(("Connecting to the %s %s on port %d", 
603                  (sconn->backup ? "backup router" : "router"), 
604                  sconn->remote_host, sconn->remote_port));
605
606   server->router_connect = time(0);
607
608   /* Connect to remote host */
609   sock = silc_net_create_connection(server->config->listen_port->local_ip,
610                                     sconn->remote_port, 
611                                     sconn->remote_host);
612   if (sock < 0) {
613     SILC_LOG_ERROR(("Could not connect to router"));
614     silc_schedule_task_add(server->schedule, fd, 
615                            silc_server_connect_to_router_retry,
616                            context, 0, 1, SILC_TASK_TIMEOUT, 
617                            SILC_TASK_PRI_NORMAL);
618     return;
619   }
620
621   /* Continue with key exchange protocol */
622   silc_server_start_key_exchange(server, sconn, sock);
623 }
624   
625 /* This function connects to our primary router or if we are a router this
626    establishes all our primary routes. This is called at the start of the
627    server to do authentication and key exchange with our router - called
628    from schedule. */
629
630 SILC_TASK_CALLBACK(silc_server_connect_to_router)
631 {
632   SilcServer server = (SilcServer)context;
633   SilcServerConnection sconn;
634   SilcServerConfigSectionServerConnection *ptr;
635
636   SILC_LOG_DEBUG(("Connecting to router(s)"));
637
638   if (server->server_type == SILC_SERVER) {
639     SILC_LOG_DEBUG(("We are normal server"));
640   } else if (server->server_type == SILC_ROUTER) {
641     SILC_LOG_DEBUG(("We are router"));
642   } else {
643     SILC_LOG_DEBUG(("We are backup router/normal server"));
644   }
645
646   /* Create the connections to all our routes */
647   ptr = server->config->routers;
648   while (ptr) {
649     
650     SILC_LOG_DEBUG(("%s connection [%s] %s:%d",
651                     ptr->backup_router ? "Backup router" : "Router",
652                     ptr->initiator ? "Initiator" : "Responder",
653                     ptr->host, ptr->port));
654
655     if (ptr->initiator) {
656       /* Allocate connection object for hold connection specific stuff. */
657       sconn = silc_calloc(1, sizeof(*sconn));
658       sconn->server = server;
659       sconn->remote_host = strdup(ptr->host);
660       sconn->remote_port = ptr->port;
661       sconn->backup = ptr->backup_router;
662       
663       silc_schedule_task_add(server->schedule, fd, 
664                              silc_server_connect_router,
665                              (void *)sconn, 0, 1, SILC_TASK_TIMEOUT, 
666                              SILC_TASK_PRI_NORMAL);
667     }
668
669     if (!ptr->next)
670       return;
671     
672     ptr = ptr->next;
673   }
674
675   SILC_LOG_DEBUG(("No router(s), server will be standalone"));
676   
677   /* There wasn't a configured router, we will continue but we don't
678      have a connection to outside world.  We will be standalone server. */
679   server->standalone = TRUE;
680 }
681
682 /* Second part of connecting to router(s). Key exchange protocol has been
683    executed and now we will execute authentication protocol. */
684
685 SILC_TASK_CALLBACK(silc_server_connect_to_router_second)
686 {
687   SilcProtocol protocol = (SilcProtocol)context;
688   SilcServerKEInternalContext *ctx = 
689     (SilcServerKEInternalContext *)protocol->context;
690   SilcServer server = (SilcServer)ctx->server;
691   SilcServerConnection sconn = (SilcServerConnection)ctx->context;
692   SilcSocketConnection sock = ctx->sock;
693   SilcServerConnAuthInternalContext *proto_ctx;
694   SilcServerConfigSectionServerConnection *conn = NULL;
695
696   SILC_LOG_DEBUG(("Start"));
697
698   if (protocol->state == SILC_PROTOCOL_STATE_ERROR ||
699       protocol->state == SILC_PROTOCOL_STATE_FAILURE) {
700     /* Error occured during protocol */
701     silc_protocol_free(protocol);
702     sock->protocol = NULL;
703     silc_ske_free_key_material(ctx->keymat);
704     if (ctx->packet)
705       silc_packet_context_free(ctx->packet);
706     if (ctx->ske)
707       silc_ske_free(ctx->ske);
708     silc_free(ctx->dest_id);
709     silc_free(ctx);
710     silc_schedule_task_del_by_callback(server->schedule,
711                                        silc_server_failure_callback);
712     silc_server_disconnect_remote(server, sock, "Server closed connection: "
713                                   "Key exchange failed");
714     return;
715   }
716   
717   /* We now have the key material as the result of the key exchange
718      protocol. Take the key material into use. Free the raw key material
719      as soon as we've set them into use. */
720   if (!silc_server_protocol_ke_set_keys(ctx->ske, ctx->sock, ctx->keymat,
721                                         ctx->ske->prop->cipher,
722                                         ctx->ske->prop->pkcs,
723                                         ctx->ske->prop->hash,
724                                         ctx->ske->prop->hmac,
725                                         ctx->ske->prop->group,
726                                         ctx->responder)) {
727     silc_protocol_free(protocol);
728     sock->protocol = NULL;
729     silc_ske_free_key_material(ctx->keymat);
730     if (ctx->packet)
731       silc_packet_context_free(ctx->packet);
732     if (ctx->ske)
733       silc_ske_free(ctx->ske);
734     silc_free(ctx->dest_id);
735     silc_free(ctx);
736     silc_schedule_task_del_by_callback(server->schedule,
737                                        silc_server_failure_callback);
738     silc_server_disconnect_remote(server, sock, "Server closed connection: "
739                                   "Key exchange failed");
740     return;
741   }    
742   silc_ske_free_key_material(ctx->keymat);
743
744   /* Allocate internal context for the authentication protocol. This
745      is sent as context for the protocol. */
746   proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
747   proto_ctx->server = (void *)server;
748   proto_ctx->context = (void *)sconn;
749   proto_ctx->sock = sock;
750   proto_ctx->ske = ctx->ske;       /* Save SKE object from previous protocol */
751   proto_ctx->dest_id_type = ctx->dest_id_type;
752   proto_ctx->dest_id = ctx->dest_id;
753
754   /* Resolve the authentication method used in this connection. Check if 
755      we find a match from user configured connections */
756   conn = silc_server_config_find_router_conn(server->config,
757                                              sock->hostname,
758                                              sock->port);
759   if (conn) {
760     /* Match found. Use the configured authentication method */
761     proto_ctx->auth_meth = conn->auth_meth;
762     if (conn->auth_data) {
763       proto_ctx->auth_data = strdup(conn->auth_data);
764       proto_ctx->auth_data_len = strlen(conn->auth_data);
765     }
766   } else {
767     SILC_LOG_ERROR(("Could not find connection data for %s (%s) on port",
768                     sock->hostname, sock->ip, sock->port));
769     silc_protocol_free(protocol);
770     sock->protocol = NULL;
771     if (ctx->packet)
772       silc_packet_context_free(ctx->packet);
773     if (ctx->ske)
774       silc_ske_free(ctx->ske);
775     silc_free(ctx->dest_id);
776     silc_free(ctx);
777     silc_schedule_task_del_by_callback(server->schedule,
778                                        silc_server_failure_callback);
779     silc_server_disconnect_remote(server, sock, "Server closed connection: "
780                                   "Key exchange failed");
781     return;
782   }
783
784   /* Free old protocol as it is finished now */
785   silc_protocol_free(protocol);
786   if (ctx->packet)
787     silc_packet_context_free(ctx->packet);
788   silc_free(ctx);
789   sock->protocol = NULL;
790
791   /* Allocate the authentication protocol. This is allocated here
792      but we won't start it yet. We will be receiving party of this
793      protocol thus we will wait that connecting party will make
794      their first move. */
795   silc_protocol_alloc(SILC_PROTOCOL_SERVER_CONNECTION_AUTH, 
796                       &sock->protocol, proto_ctx, 
797                       silc_server_connect_to_router_final);
798
799   /* Register timeout task. If the protocol is not executed inside
800      this timelimit the connection will be terminated. Currently
801      this is 15 seconds and is hard coded limit (XXX). */
802   proto_ctx->timeout_task = 
803     silc_schedule_task_add(server->schedule, sock->sock, 
804                        silc_server_timeout_remote,
805                        (void *)server, 15, 0,
806                        SILC_TASK_TIMEOUT,
807                        SILC_TASK_PRI_LOW);
808
809   /* Run the protocol */
810   silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
811 }
812
813 /* Finalizes the connection to router. Registers a server task to the
814    queue so that we can accept new connections. */
815
816 SILC_TASK_CALLBACK(silc_server_connect_to_router_final)
817 {
818   SilcProtocol protocol = (SilcProtocol)context;
819   SilcServerConnAuthInternalContext *ctx = 
820     (SilcServerConnAuthInternalContext *)protocol->context;
821   SilcServer server = (SilcServer)ctx->server;
822   SilcServerConnection sconn = (SilcServerConnection)ctx->context;
823   SilcSocketConnection sock = ctx->sock;
824   SilcServerEntry id_entry;
825   SilcBuffer packet;
826   SilcServerHBContext hb_context;
827   unsigned char *id_string;
828   uint32 id_len;
829   SilcIDListData idata;
830
831   SILC_LOG_DEBUG(("Start"));
832
833   if (protocol->state == SILC_PROTOCOL_STATE_ERROR ||
834       protocol->state == SILC_PROTOCOL_STATE_FAILURE) {
835     /* Error occured during protocol */
836     silc_free(ctx->dest_id);
837     silc_server_disconnect_remote(server, sock, "Server closed connection: "
838                                   "Authentication failed");
839     goto out;
840   }
841
842   /* Add a task to the queue. This task receives new connections to the 
843      server. This task remains on the queue until the end of the program. */
844   if (!server->listenning && !sconn->backup) {
845     silc_schedule_task_add(server->schedule, server->sock, 
846                            silc_server_accept_new_connection,
847                            (void *)server, 0, 0, 
848                            SILC_TASK_FD,
849                            SILC_TASK_PRI_NORMAL);
850     server->listenning = TRUE;
851   }
852
853   /* Send NEW_SERVER packet to the router. We will become registered
854      to the SILC network after sending this packet. */
855   id_string = silc_id_id2str(server->id, SILC_ID_SERVER);
856   id_len = silc_id_get_len(server->id, SILC_ID_SERVER);
857   packet = silc_buffer_alloc(2 + 2 + id_len + strlen(server->server_name));
858   silc_buffer_pull_tail(packet, SILC_BUFFER_END(packet));
859   silc_buffer_format(packet,
860                      SILC_STR_UI_SHORT(id_len),
861                      SILC_STR_UI_XNSTRING(id_string, id_len),
862                      SILC_STR_UI_SHORT(strlen(server->server_name)),
863                      SILC_STR_UI_XNSTRING(server->server_name,
864                                           strlen(server->server_name)),
865                      SILC_STR_END);
866
867   /* Send the packet */
868   silc_server_packet_send(server, ctx->sock, SILC_PACKET_NEW_SERVER, 0,
869                           packet->data, packet->len, TRUE);
870   silc_buffer_free(packet);
871   silc_free(id_string);
872
873   SILC_LOG_INFO(("Connected to router %s", sock->hostname));
874
875   /* Add the connected router to local server list */
876   id_entry = silc_idlist_add_server(server->local_list, strdup(sock->hostname),
877                                     SILC_ROUTER, ctx->dest_id, NULL, sock);
878   if (!id_entry) {
879     silc_free(ctx->dest_id);
880     silc_server_disconnect_remote(server, sock, "Server closed connection: "
881                                   "Authentication failed");
882     goto out;
883   }
884
885   silc_idlist_add_data(id_entry, (SilcIDListData)sock->user_data);
886   silc_free(sock->user_data);
887   sock->user_data = (void *)id_entry;
888   sock->type = SILC_SOCKET_TYPE_ROUTER;
889   idata = (SilcIDListData)sock->user_data;
890   idata->status |= SILC_IDLIST_STATUS_REGISTERED;
891
892   /* Perform keepalive. The `hb_context' will be freed automatically
893      when finally calling the silc_socket_free function. XXX hardcoded 
894      timeout!! */
895   hb_context = silc_calloc(1, sizeof(*hb_context));
896   hb_context->server = server;
897   silc_socket_set_heartbeat(sock, 600, hb_context,
898                             silc_server_perform_heartbeat,
899                             server->schedule);
900
901   /* Register re-key timeout */
902   idata->rekey->timeout = 3600; /* XXX hardcoded */
903   idata->rekey->context = (void *)server;
904   silc_schedule_task_add(server->schedule, sock->sock, 
905                          silc_server_rekey_callback,
906                          (void *)sock, idata->rekey->timeout, 0,
907                          SILC_TASK_TIMEOUT, SILC_TASK_PRI_NORMAL);
908
909   if (!sconn->backup) {
910     /* Mark this router our primary router if we're still standalone */
911     if (server->standalone) {
912       server->id_entry->router = id_entry;
913       server->router = id_entry;
914       server->standalone = FALSE;
915     
916       /* If we are router then announce our possible servers. */
917       if (server->server_type == SILC_ROUTER)
918         silc_server_announce_servers(server, FALSE, 0, 
919                                      server->router->connection);
920
921       /* Announce our clients and channels to the router */
922       silc_server_announce_clients(server, 0, server->router->connection);
923       silc_server_announce_channels(server, 0, server->router->connection);
924     }
925   } else {
926     /* Add this server to be our backup router */
927     silc_server_backup_add(server, id_entry, FALSE);
928   }
929
930   sock->protocol = NULL;
931
932   /* Call the completion callback to indicate that we've connected to
933      the router */
934   if (sconn->callback)
935     (*sconn->callback)(server, id_entry, sconn->callback_context);
936
937  out:
938   /* Free the temporary connection data context */
939   if (sconn) {
940     silc_free(sconn->remote_host);
941     silc_free(sconn);
942   }
943
944   /* Free the protocol object */
945   if (sock->protocol == protocol)
946     sock->protocol = NULL;
947   silc_protocol_free(protocol);
948   if (ctx->packet)
949     silc_packet_context_free(ctx->packet);
950   if (ctx->ske)
951     silc_ske_free(ctx->ske);
952   silc_free(ctx);
953 }
954
955 /* Host lookup callbcak that is called after the incoming connection's
956    IP and FQDN lookup is performed. This will actually check the acceptance
957    of the incoming connection and will register the key exchange protocol
958    for this connection. */
959
960 static void 
961 silc_server_accept_new_connection_lookup(SilcSocketConnection sock,
962                                          void *context)
963 {
964   SilcServer server = (SilcServer)context;
965   SilcServerKEInternalContext *proto_ctx;
966   void *cconfig, *sconfig, *rconfig;
967   SilcServerConfigSectionDenyConnection *deny;
968   int port;
969
970   SILC_LOG_DEBUG(("Start"));
971
972   /* Check whether we could resolve both IP and FQDN. */
973   if (!sock->ip || (!strcmp(sock->ip, sock->hostname) &&
974                     server->params->require_reverse_mapping)) {
975     SILC_LOG_ERROR(("IP/DNS lookup failed %s",
976                     sock->hostname ? sock->hostname :
977                     sock->ip ? sock->ip : ""));
978     server->stat.conn_failures++;
979     silc_server_disconnect_remote(server, sock,
980                                   "Server closed connection: Unknown host");
981     return;
982   }
983
984   /* Register the connection for network input and output. This sets
985      that scheduler will listen for incoming packets for this connection 
986      and sets that outgoing packets may be sent to this connection as well.
987      However, this doesn't set the scheduler for outgoing traffic, it
988      will be set separately by calling SILC_SET_CONNECTION_FOR_OUTPUT,
989      later when outgoing data is available. */
990   SILC_REGISTER_CONNECTION_FOR_IO(sock->sock);
991
992   SILC_LOG_INFO(("Incoming connection from %s (%s)", sock->hostname,
993                  sock->ip));
994
995   port = server->sockets[server->sock]->port; /* Listenning port */
996
997   /* Check whether this connection is denied to connect to us. */
998   deny = silc_server_config_denied_conn(server->config, sock->ip, port);
999   if (!deny)
1000     deny = silc_server_config_denied_conn(server->config, sock->hostname,
1001                                           port);
1002   if (deny) {
1003     /* The connection is denied */
1004     SILC_LOG_INFO(("Connection %s (%s) is denied", 
1005                    sock->hostname, sock->ip));
1006     silc_server_disconnect_remote(server, sock, deny->comment ?
1007                                   deny->comment :
1008                                   "Server closed connection: "
1009                                   "Connection refused");
1010     server->stat.conn_failures++;
1011     return;
1012   }
1013
1014   /* Check whether we have configred this sort of connection at all. We
1015      have to check all configurations since we don't know what type of
1016      connection this is. */
1017   if (!(cconfig = silc_server_config_find_client_conn(server->config,
1018                                                       sock->ip, port)))
1019     cconfig = silc_server_config_find_client_conn(server->config,
1020                                                   sock->hostname, 
1021                                                   port);
1022   if (!(sconfig = silc_server_config_find_server_conn(server->config,
1023                                                      sock->ip, 
1024                                                      port)))
1025     sconfig = silc_server_config_find_server_conn(server->config,
1026                                                   sock->hostname,
1027                                                   port);
1028   if (!(rconfig = silc_server_config_find_router_conn(server->config,
1029                                                      sock->ip, port)))
1030     rconfig = silc_server_config_find_router_conn(server->config,
1031                                                   sock->hostname, 
1032                                                   port);
1033   if (!cconfig && !sconfig && !rconfig) {
1034     silc_server_disconnect_remote(server, sock, 
1035                                   "Server closed connection: "
1036                                   "Connection refused");
1037     server->stat.conn_failures++;
1038     return;
1039   }
1040
1041   /* The connection is allowed */
1042
1043   /* Allocate internal context for key exchange protocol. This is
1044      sent as context for the protocol. */
1045   proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
1046   proto_ctx->server = context;
1047   proto_ctx->sock = sock;
1048   proto_ctx->rng = server->rng;
1049   proto_ctx->responder = TRUE;
1050   proto_ctx->cconfig = cconfig;
1051   proto_ctx->sconfig = sconfig;
1052   proto_ctx->rconfig = rconfig;
1053
1054   /* Prepare the connection for key exchange protocol. We allocate the
1055      protocol but will not start it yet. The connector will be the
1056      initiator of the protocol thus we will wait for initiation from 
1057      there before we start the protocol. */
1058   server->stat.auth_attempts++;
1059   silc_protocol_alloc(SILC_PROTOCOL_SERVER_KEY_EXCHANGE, 
1060                       &sock->protocol, proto_ctx, 
1061                       silc_server_accept_new_connection_second);
1062
1063   /* Register a timeout task that will be executed if the connector
1064      will not start the key exchange protocol within 60 seconds. For
1065      now, this is a hard coded limit. After 60 secs the connection will
1066      be closed if the key exchange protocol has not been started. */
1067   proto_ctx->timeout_task = 
1068     silc_schedule_task_add(server->schedule, sock->sock, 
1069                            silc_server_timeout_remote,
1070                            context, 60, 0,
1071                            SILC_TASK_TIMEOUT,
1072                            SILC_TASK_PRI_LOW);
1073 }
1074
1075 /* Accepts new connections to the server. Accepting new connections are
1076    done in three parts to make it async. */
1077
1078 SILC_TASK_CALLBACK(silc_server_accept_new_connection)
1079 {
1080   SilcServer server = (SilcServer)context;
1081   SilcSocketConnection newsocket;
1082   int sock;
1083
1084   SILC_LOG_DEBUG(("Accepting new connection"));
1085
1086   server->stat.conn_attempts++;
1087
1088   sock = silc_net_accept_connection(server->sock);
1089   if (sock < 0) {
1090     SILC_LOG_ERROR(("Could not accept new connection: %s", strerror(errno)));
1091     server->stat.conn_failures++;
1092     return;
1093   }
1094
1095   /* Check max connections */
1096   if (sock > SILC_SERVER_MAX_CONNECTIONS) {
1097     SILC_LOG_ERROR(("Refusing connection, server is full"));
1098     server->stat.conn_failures++;
1099     return;
1100   }
1101
1102   /* Set socket options */
1103   silc_net_set_socket_nonblock(sock);
1104   silc_net_set_socket_opt(sock, SOL_SOCKET, SO_REUSEADDR, 1);
1105
1106   /* We don't create a ID yet, since we don't know what type of connection
1107      this is yet. But, we do add the connection to the socket table. */
1108   silc_socket_alloc(sock, SILC_SOCKET_TYPE_UNKNOWN, NULL, &newsocket);
1109   server->sockets[sock] = newsocket;
1110
1111   /* Perform asynchronous host lookup. This will lookup the IP and the
1112      FQDN of the remote connection. After the lookup is done the connection
1113      is accepted further. */
1114   silc_socket_host_lookup(newsocket, TRUE, 
1115                           silc_server_accept_new_connection_lookup, context, 
1116                           server->schedule);
1117 }
1118
1119 /* Second part of accepting new connection. Key exchange protocol has been
1120    performed and now it is time to do little connection authentication
1121    protocol to figure out whether this connection is client or server
1122    and whether it has right to access this server (especially server
1123    connections needs to be authenticated). */
1124
1125 SILC_TASK_CALLBACK(silc_server_accept_new_connection_second)
1126 {
1127   SilcProtocol protocol = (SilcProtocol)context;
1128   SilcServerKEInternalContext *ctx = 
1129     (SilcServerKEInternalContext *)protocol->context;
1130   SilcServer server = (SilcServer)ctx->server;
1131   SilcSocketConnection sock = ctx->sock;
1132   SilcServerConnAuthInternalContext *proto_ctx;
1133
1134   SILC_LOG_DEBUG(("Start"));
1135
1136   if (protocol->state == SILC_PROTOCOL_STATE_ERROR ||
1137       protocol->state == SILC_PROTOCOL_STATE_FAILURE) {
1138     /* Error occured during protocol */
1139     silc_protocol_free(protocol);
1140     sock->protocol = NULL;
1141     silc_ske_free_key_material(ctx->keymat);
1142     if (ctx->packet)
1143       silc_packet_context_free(ctx->packet);
1144     if (ctx->ske)
1145       silc_ske_free(ctx->ske);
1146     silc_free(ctx->dest_id);
1147     silc_free(ctx);
1148     silc_schedule_task_del_by_callback(server->schedule,
1149                                        silc_server_failure_callback);
1150     silc_server_disconnect_remote(server, sock, "Server closed connection: "
1151                                   "Key exchange failed");
1152     server->stat.auth_failures++;
1153     return;
1154   }
1155
1156   /* We now have the key material as the result of the key exchange
1157      protocol. Take the key material into use. Free the raw key material
1158      as soon as we've set them into use. */
1159   if (!silc_server_protocol_ke_set_keys(ctx->ske, ctx->sock, ctx->keymat,
1160                                         ctx->ske->prop->cipher,
1161                                         ctx->ske->prop->pkcs,
1162                                         ctx->ske->prop->hash,
1163                                         ctx->ske->prop->hmac,
1164                                         ctx->ske->prop->group,
1165                                         ctx->responder)) {
1166     silc_protocol_free(protocol);
1167     sock->protocol = NULL;
1168     silc_ske_free_key_material(ctx->keymat);
1169     if (ctx->packet)
1170       silc_packet_context_free(ctx->packet);
1171     if (ctx->ske)
1172       silc_ske_free(ctx->ske);
1173     silc_free(ctx->dest_id);
1174     silc_free(ctx);
1175     silc_schedule_task_del_by_callback(server->schedule,
1176                                        silc_server_failure_callback);
1177     silc_server_disconnect_remote(server, sock, "Server closed connection: "
1178                                   "Key exchange failed");
1179     server->stat.auth_failures++;
1180     return;
1181   }    
1182   silc_ske_free_key_material(ctx->keymat);
1183
1184   /* Allocate internal context for the authentication protocol. This
1185      is sent as context for the protocol. */
1186   proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
1187   proto_ctx->server = (void *)server;
1188   proto_ctx->sock = sock;
1189   proto_ctx->ske = ctx->ske;    /* Save SKE object from previous protocol */
1190   proto_ctx->responder = TRUE;
1191   proto_ctx->dest_id_type = ctx->dest_id_type;
1192   proto_ctx->dest_id = ctx->dest_id;
1193   proto_ctx->cconfig = ctx->cconfig;
1194   proto_ctx->sconfig = ctx->sconfig;
1195   proto_ctx->rconfig = ctx->rconfig;
1196
1197   /* Free old protocol as it is finished now */
1198   silc_protocol_free(protocol);
1199   if (ctx->packet)
1200     silc_packet_context_free(ctx->packet);
1201   silc_free(ctx);
1202   sock->protocol = NULL;
1203
1204   /* Allocate the authentication protocol. This is allocated here
1205      but we won't start it yet. We will be receiving party of this
1206      protocol thus we will wait that connecting party will make
1207      their first move. */
1208   silc_protocol_alloc(SILC_PROTOCOL_SERVER_CONNECTION_AUTH, 
1209                       &sock->protocol, proto_ctx, 
1210                       silc_server_accept_new_connection_final);
1211
1212   /* Register timeout task. If the protocol is not executed inside
1213      this timelimit the connection will be terminated. Currently
1214      this is 60 seconds and is hard coded limit (XXX). */
1215   proto_ctx->timeout_task = 
1216     silc_schedule_task_add(server->schedule, sock->sock, 
1217                            silc_server_timeout_remote,
1218                            (void *)server, 60, 0,
1219                            SILC_TASK_TIMEOUT,
1220                            SILC_TASK_PRI_LOW);
1221 }
1222
1223 /* Final part of accepting new connection. The connection has now
1224    been authenticated and keys has been exchanged. We also know whether
1225    this is client or server connection. */
1226
1227 SILC_TASK_CALLBACK(silc_server_accept_new_connection_final)
1228 {
1229   SilcProtocol protocol = (SilcProtocol)context;
1230   SilcServerConnAuthInternalContext *ctx = 
1231     (SilcServerConnAuthInternalContext *)protocol->context;
1232   SilcServer server = (SilcServer)ctx->server;
1233   SilcSocketConnection sock = ctx->sock;
1234   SilcServerHBContext hb_context;
1235   SilcUnknownEntry entry = (SilcUnknownEntry)sock->user_data;
1236   void *id_entry = NULL;
1237
1238   SILC_LOG_DEBUG(("Start"));
1239
1240   if (protocol->state == SILC_PROTOCOL_STATE_ERROR ||
1241       protocol->state == SILC_PROTOCOL_STATE_FAILURE) {
1242     /* Error occured during protocol */
1243     silc_protocol_free(protocol);
1244     sock->protocol = NULL;
1245     if (ctx->packet)
1246       silc_packet_context_free(ctx->packet);
1247     if (ctx->ske)
1248       silc_ske_free(ctx->ske);
1249     silc_free(ctx->dest_id);
1250     silc_free(ctx);
1251     if (sock)
1252       sock->protocol = NULL;
1253     silc_schedule_task_del_by_callback(server->schedule,
1254                                        silc_server_failure_callback);
1255     silc_server_disconnect_remote(server, sock, "Server closed connection: "
1256                                   "Authentication failed");
1257     server->stat.auth_failures++;
1258     return;
1259   }
1260
1261   entry->data.last_receive = time(NULL);
1262
1263   switch (ctx->conn_type) {
1264   case SILC_SOCKET_TYPE_CLIENT:
1265     {
1266       SilcClientEntry client;
1267
1268       SILC_LOG_DEBUG(("Remote host is client"));
1269       SILC_LOG_INFO(("Connection from %s (%s) is client", sock->hostname,
1270                      sock->ip));
1271
1272       /* Add the client to the client ID cache. The nickname and Client ID
1273          and other information is created after we have received NEW_CLIENT
1274          packet from client. */
1275       client = silc_idlist_add_client(server->local_list, 
1276                                       NULL, NULL, NULL, NULL, NULL, sock);
1277       if (!client) {
1278         SILC_LOG_ERROR(("Could not add new client to cache"));
1279         silc_free(sock->user_data);
1280         silc_server_disconnect_remote(server, sock, 
1281                                       "Server closed connection: "
1282                                       "Authentication failed");
1283         server->stat.auth_failures++;
1284         goto out;
1285       }
1286
1287       /* Statistics */
1288       server->stat.my_clients++;
1289       server->stat.clients++;
1290       if (server->server_type == SILC_ROUTER)
1291         server->stat.cell_clients++;
1292
1293       id_entry = (void *)client;
1294       break;
1295     }
1296   case SILC_SOCKET_TYPE_SERVER:
1297   case SILC_SOCKET_TYPE_ROUTER:
1298     {
1299       SilcServerEntry new_server;
1300       SilcServerConfigSectionServerConnection *conn = 
1301         ctx->conn_type == SILC_SOCKET_TYPE_SERVER ? 
1302         ctx->sconfig : ctx->rconfig;
1303
1304       SILC_LOG_DEBUG(("Remote host is %s", 
1305                       ctx->conn_type == SILC_SOCKET_TYPE_SERVER ? 
1306                       "server" : (conn->backup_router ? 
1307                                   "backup router" : "router")));
1308       SILC_LOG_INFO(("Connection from %s (%s) is %s", sock->hostname,
1309                      sock->ip, ctx->conn_type == SILC_SOCKET_TYPE_SERVER ? 
1310                      "server" : (conn->backup_router ? 
1311                                  "backup router" : "router")));
1312
1313       /* Add the server into server cache. The server name and Server ID
1314          is updated after we have received NEW_SERVER packet from the
1315          server. We mark ourselves as router for this server if we really
1316          are router. */
1317       new_server = 
1318         silc_idlist_add_server(server->local_list, NULL,
1319                                ctx->conn_type == SILC_SOCKET_TYPE_SERVER ?
1320                                SILC_SERVER : SILC_ROUTER, NULL, 
1321                                ctx->conn_type == SILC_SOCKET_TYPE_SERVER ?
1322                                server->id_entry : NULL, sock);
1323       if (!new_server) {
1324         SILC_LOG_ERROR(("Could not add new server to cache"));
1325         silc_free(sock->user_data);
1326         silc_server_disconnect_remote(server, sock, 
1327                                       "Server closed connection: "
1328                                       "Authentication failed");
1329         server->stat.auth_failures++;
1330         goto out;
1331       }
1332
1333       /* Statistics */
1334       if (ctx->conn_type == SILC_SOCKET_TYPE_SERVER)
1335         server->stat.my_servers++;
1336       else
1337         server->stat.my_routers++;
1338       server->stat.servers++;
1339
1340       id_entry = (void *)new_server;
1341
1342       /* If the incoming connection is router and marked as backup router
1343          then add it to be one of our backups */
1344       if (ctx->conn_type == SILC_SOCKET_TYPE_ROUTER && conn->backup_router) {
1345         silc_server_backup_add(server, new_server, conn->backup_local);
1346
1347         /* Change it back to SERVER type since that's what it really is. */
1348         if (conn->backup_local) {
1349           ctx->conn_type = SILC_SOCKET_TYPE_SERVER;
1350           new_server->server_type = SILC_BACKUP_ROUTER;
1351         }
1352       }
1353
1354 #if 0
1355       /* If the incoming connection is normal server and marked as backup
1356          server then it will use us as backup router. We'll disable the
1357          connection until it is allowed to be used. */
1358       if (ctx->conn_type == SILC_SOCKET_TYPE_SERVER && conn->backup_router)
1359         SILC_SET_DISABLED(sock);
1360 #endif
1361
1362       /* Check whether this connection is to be our primary router connection
1363          if we do not already have the primary route. */
1364       if (server->standalone && ctx->conn_type == SILC_SOCKET_TYPE_ROUTER) {
1365         if (silc_server_config_is_primary_route(server->config) &&
1366             !conn->initiator)
1367           break;
1368
1369         SILC_LOG_DEBUG(("We are not standalone server anymore"));
1370         server->standalone = FALSE;
1371         if (!server->id_entry->router) {
1372           server->id_entry->router = id_entry;
1373           server->router = id_entry;
1374         }
1375       }
1376
1377       break;
1378     }
1379   default:
1380     break;
1381   }
1382
1383   sock->type = ctx->conn_type;
1384
1385   /* Add the common data structure to the ID entry. */
1386   if (id_entry)
1387     silc_idlist_add_data(id_entry, (SilcIDListData)sock->user_data);
1388       
1389   /* Add to sockets internal pointer for fast referencing */
1390   silc_free(sock->user_data);
1391   sock->user_data = id_entry;
1392
1393   /* Connection has been fully established now. Everything is ok. */
1394   SILC_LOG_DEBUG(("New connection authenticated"));
1395
1396   /* Perform keepalive. The `hb_context' will be freed automatically
1397      when finally calling the silc_socket_free function. XXX hardcoded 
1398      timeout!! */
1399   hb_context = silc_calloc(1, sizeof(*hb_context));
1400   hb_context->server = server;
1401   silc_socket_set_heartbeat(sock, 600, hb_context,
1402                             silc_server_perform_heartbeat,
1403                             server->schedule);
1404
1405  out:
1406   silc_schedule_task_del_by_callback(server->schedule,
1407                                      silc_server_failure_callback);
1408   silc_protocol_free(protocol);
1409   if (ctx->packet)
1410     silc_packet_context_free(ctx->packet);
1411   if (ctx->ske)
1412     silc_ske_free(ctx->ske);
1413   silc_free(ctx->dest_id);
1414   silc_free(ctx);
1415   sock->protocol = NULL;
1416 }
1417
1418 /* This function is used to read packets from network and send packets to
1419    network. This is usually a generic task. */
1420
1421 SILC_TASK_CALLBACK(silc_server_packet_process)
1422 {
1423   SilcServer server = (SilcServer)context;
1424   SilcSocketConnection sock = server->sockets[fd];
1425   SilcIDListData idata;
1426   SilcCipher cipher = NULL;
1427   SilcHmac hmac = NULL;
1428   int ret;
1429
1430   if (!sock)
1431     return;
1432
1433   SILC_LOG_DEBUG(("Processing packet"));
1434
1435   /* Packet sending */
1436
1437   if (type == SILC_TASK_WRITE) {
1438     /* Do not send data to disconnected connection */
1439     if (SILC_IS_DISCONNECTED(sock))
1440       return;
1441
1442     server->stat.packets_sent++;
1443
1444     if (sock->outbuf->data - sock->outbuf->head)
1445      silc_buffer_push(sock->outbuf, sock->outbuf->data - sock->outbuf->head);
1446
1447     /* Send the packet */
1448     ret = silc_packet_send(sock, TRUE);
1449
1450     /* If returned -2 could not write to connection now, will do
1451        it later. */
1452     if (ret == -2)
1453       return;
1454
1455     if (ret == -1) {
1456       SILC_LOG_ERROR(("Error sending packet to connection "
1457                       "%s:%d [%s]", sock->hostname, sock->port,  
1458                       (sock->type == SILC_SOCKET_TYPE_UNKNOWN ? "Unknown" :
1459                        sock->type == SILC_SOCKET_TYPE_CLIENT ? "Client" :
1460                        sock->type == SILC_SOCKET_TYPE_SERVER ? "Server" :
1461                        "Router")));
1462       return;
1463     }
1464     
1465     /* The packet has been sent and now it is time to set the connection
1466        back to only for input. When there is again some outgoing data 
1467        available for this connection it will be set for output as well. 
1468        This call clears the output setting and sets it only for input. */
1469     SILC_SET_CONNECTION_FOR_INPUT(server->schedule, fd);
1470     SILC_UNSET_OUTBUF_PENDING(sock);
1471
1472     silc_buffer_clear(sock->outbuf);
1473     return;
1474   }
1475
1476   /* Packet receiving */
1477
1478   /* Read some data from connection */
1479   ret = silc_packet_receive(sock);
1480   if (ret < 0) {
1481
1482     if (ret == -1)
1483       SILC_LOG_ERROR(("Error receiving packet from connection "
1484                       "%s:%d [%s]", sock->hostname, sock->port,  
1485                       (sock->type == SILC_SOCKET_TYPE_UNKNOWN ? "Unknown" :
1486                        sock->type == SILC_SOCKET_TYPE_CLIENT ? "Client" :
1487                        sock->type == SILC_SOCKET_TYPE_SERVER ? "Server" :
1488                        "Router")));
1489     return;
1490   }    
1491
1492   /* EOF */
1493   if (ret == 0) {
1494     SILC_LOG_DEBUG(("Read EOF"));
1495       
1496     /* If connection is disconnecting already we will finally
1497        close the connection */
1498     if (SILC_IS_DISCONNECTING(sock)) {
1499       if (sock->user_data)
1500         silc_server_free_sock_user_data(server, sock);
1501       silc_server_close_connection(server, sock);
1502       return;
1503     }
1504       
1505     SILC_LOG_DEBUG(("Premature EOF from connection %d", sock->sock));
1506     SILC_SET_DISCONNECTING(sock);
1507
1508     if (sock->user_data)
1509       silc_server_free_sock_user_data(server, sock);
1510     silc_server_close_connection(server, sock);
1511     return;
1512   }
1513
1514   /* If connection is disconnecting or disconnected we will ignore
1515      what we read. */
1516   if (SILC_IS_DISCONNECTING(sock) || SILC_IS_DISCONNECTED(sock)) {
1517     SILC_LOG_DEBUG(("Ignoring read data from disonnected connection"));
1518     return;
1519   }
1520
1521   server->stat.packets_received++;
1522
1523   /* Get keys and stuff from ID entry */
1524   idata = (SilcIDListData)sock->user_data;
1525   if (idata) {
1526     cipher = idata->receive_key;
1527     hmac = idata->hmac_receive;
1528   }
1529  
1530   /* Process the packet. This will call the parser that will then
1531      decrypt and parse the packet. */
1532   silc_packet_receive_process(sock, cipher, hmac, silc_server_packet_parse, 
1533                               server);
1534 }
1535
1536 /* Callback function that the silc_packet_decrypt will call to make the
1537    decision whether the packet is normal or special packet. We will 
1538    return TRUE if it is normal and FALSE if it is special */
1539
1540 static int silc_server_packet_decrypt_check(SilcPacketType packet_type,
1541                                             SilcBuffer buffer,
1542                                             SilcPacketContext *packet,
1543                                             void *context)
1544 {
1545   SilcPacketParserContext *parse_ctx = (SilcPacketParserContext *)context;
1546   SilcServer server = (SilcServer)parse_ctx->context;
1547
1548   /* Packet is normal packet, if: 
1549
1550      1) packet is private message packet and does not have private key set
1551      2) is other packet than channel message packet
1552      3) is channel message packet and remote is router and we are router 
1553
1554      all other packets are special packets 
1555   */
1556
1557   if (packet_type == SILC_PACKET_PRIVATE_MESSAGE &&
1558       (buffer->data[2] & SILC_PACKET_FLAG_PRIVMSG_KEY))
1559     return FALSE;
1560
1561   if (packet_type != SILC_PACKET_CHANNEL_MESSAGE || 
1562       (packet_type == SILC_PACKET_CHANNEL_MESSAGE &&
1563        parse_ctx->sock->type == SILC_SOCKET_TYPE_ROUTER &&
1564        server->server_type == SILC_ROUTER))
1565     return TRUE;
1566
1567   return FALSE;
1568 }
1569   
1570 /* Parses whole packet, received earlier. */
1571
1572 SILC_TASK_CALLBACK(silc_server_packet_parse_real)
1573 {
1574   SilcPacketParserContext *parse_ctx = (SilcPacketParserContext *)context;
1575   SilcServer server = (SilcServer)parse_ctx->context;
1576   SilcSocketConnection sock = parse_ctx->sock;
1577   SilcPacketContext *packet = parse_ctx->packet;
1578   SilcIDListData idata = (SilcIDListData)sock->user_data;
1579   int ret;
1580
1581   SILC_LOG_DEBUG(("Start"));
1582
1583   /* Decrypt the received packet */
1584   ret = silc_packet_decrypt(idata ? idata->receive_key : NULL, 
1585                             idata ? idata->hmac_receive : NULL, 
1586                             packet->buffer, packet,
1587                             silc_server_packet_decrypt_check, parse_ctx);
1588   if (ret < 0) {
1589     SILC_LOG_WARNING(("Packet decryption failed for connection "
1590                       "%s:%d [%s]", sock->hostname, sock->port,  
1591                       (sock->type == SILC_SOCKET_TYPE_UNKNOWN ? "Unknown" :
1592                        sock->type == SILC_SOCKET_TYPE_CLIENT ? "Client" :
1593                        sock->type == SILC_SOCKET_TYPE_SERVER ? "Server" :
1594                        "Router")));
1595     goto out;
1596   }
1597
1598   if (ret == 0) {
1599     /* Parse the packet. Packet type is returned. */
1600     ret = silc_packet_parse(packet);
1601   } else {
1602     /* Parse the packet header in special way as this is "special"
1603        packet type. */
1604     ret = silc_packet_parse_special(packet);
1605   }
1606
1607   /* If entry is disabled ignore what we got. */
1608   if (ret != SILC_PACKET_RESUME_ROUTER &&
1609       idata && idata->status & SILC_IDLIST_STATUS_DISABLED)
1610     goto out;
1611
1612   if (ret == SILC_PACKET_NONE)
1613     goto out;
1614
1615   /* Check that the the current client ID is same as in the client's packet. */
1616   if (sock->type == SILC_SOCKET_TYPE_CLIENT) {
1617     SilcClientEntry client = (SilcClientEntry)sock->user_data;
1618     if (client && client->id) {
1619       void *id = silc_id_str2id(packet->src_id, packet->src_id_len,
1620                                 packet->src_id_type);
1621       if (!id || !SILC_ID_CLIENT_COMPARE(client->id, id)) {
1622         silc_free(id);
1623         goto out;
1624       }
1625       silc_free(id);
1626     }
1627   }
1628
1629   if (server->server_type == SILC_ROUTER) {
1630     /* Route the packet if it is not destined to us. Other ID types but
1631        server are handled separately after processing them. */
1632     if (!(packet->flags & SILC_PACKET_FLAG_BROADCAST) &&
1633         packet->dst_id_type == SILC_ID_SERVER && 
1634         sock->type != SILC_SOCKET_TYPE_CLIENT &&
1635         memcmp(packet->dst_id, server->id_string, packet->dst_id_len)) {
1636       
1637       /* Route the packet to fastest route for the destination ID */
1638       void *id = silc_id_str2id(packet->dst_id, packet->dst_id_len, 
1639                                 packet->dst_id_type);
1640       if (!id)
1641         goto out;
1642       silc_server_packet_route(server,
1643                                silc_server_route_get(server, id,
1644                                                      packet->dst_id_type),
1645                                packet);
1646       silc_free(id);
1647       goto out;
1648     }
1649   }
1650
1651   /* Parse the incoming packet type */
1652   silc_server_packet_parse_type(server, sock, packet);
1653
1654   if (server->server_type == SILC_ROUTER) {
1655     /* Broadcast packet if it is marked as broadcast packet and it is
1656        originated from router and we are router. */
1657     if (sock->type == SILC_SOCKET_TYPE_ROUTER &&
1658         packet->flags & SILC_PACKET_FLAG_BROADCAST &&
1659         !server->standalone) {
1660       /* Broadcast to our primary route */
1661       silc_server_packet_broadcast(server, server->router->connection, packet);
1662
1663       /* If we have backup routers then we need to feed all broadcast
1664          data to those servers. */
1665       silc_server_backup_broadcast(server, sock, packet);
1666     }
1667   }
1668
1669  out:
1670   silc_packet_context_free(packet);
1671   silc_free(parse_ctx);
1672 }
1673
1674 /* Parser callback called by silc_packet_receive_process. This merely
1675    registers timeout that will handle the actual parsing when appropriate. */
1676
1677 void silc_server_packet_parse(SilcPacketParserContext *parser_context)
1678 {
1679   SilcServer server = (SilcServer)parser_context->context;
1680   SilcSocketConnection sock = parser_context->sock;
1681
1682   switch (sock->type) {
1683   case SILC_SOCKET_TYPE_UNKNOWN:
1684   case SILC_SOCKET_TYPE_CLIENT:
1685     /* Parse the packet with timeout */
1686     silc_schedule_task_add(server->schedule, sock->sock,
1687                            silc_server_packet_parse_real,
1688                            (void *)parser_context, 0, 100000,
1689                            SILC_TASK_TIMEOUT,
1690                            SILC_TASK_PRI_NORMAL);
1691     break;
1692   case SILC_SOCKET_TYPE_SERVER:
1693   case SILC_SOCKET_TYPE_ROUTER:
1694     /* Packets from servers are parsed as soon as possible */
1695     silc_schedule_task_add(server->schedule, sock->sock,
1696                            silc_server_packet_parse_real,
1697                            (void *)parser_context, 0, 1,
1698                            SILC_TASK_TIMEOUT,
1699                            SILC_TASK_PRI_NORMAL);
1700     break;
1701   default:
1702     return;
1703   }
1704 }
1705
1706 /* Parses the packet type and calls what ever routines the packet type
1707    requires. This is done for all incoming packets. */
1708
1709 void silc_server_packet_parse_type(SilcServer server, 
1710                                    SilcSocketConnection sock,
1711                                    SilcPacketContext *packet)
1712 {
1713   SilcPacketType type = packet->type;
1714   SilcIDListData idata = (SilcIDListData)sock->user_data;
1715
1716   SILC_LOG_DEBUG(("Parsing packet type %d", type));
1717
1718   /* Parse the packet type */
1719   switch (type) {
1720   case SILC_PACKET_DISCONNECT:
1721     SILC_LOG_DEBUG(("Disconnect packet"));
1722     if (packet->flags & SILC_PACKET_FLAG_LIST)
1723       break;
1724     break;
1725
1726   case SILC_PACKET_SUCCESS:
1727     /*
1728      * Success received for something. For now we can have only
1729      * one protocol for connection executing at once hence this
1730      * success message is for whatever protocol is executing currently.
1731      */
1732     SILC_LOG_DEBUG(("Success packet"));
1733     if (packet->flags & SILC_PACKET_FLAG_LIST)
1734       break;
1735     if (sock->protocol)
1736       silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
1737     break;
1738
1739   case SILC_PACKET_FAILURE:
1740     /*
1741      * Failure received for something. For now we can have only
1742      * one protocol for connection executing at once hence this
1743      * failure message is for whatever protocol is executing currently.
1744      */
1745     SILC_LOG_DEBUG(("Failure packet"));
1746     if (packet->flags & SILC_PACKET_FLAG_LIST)
1747       break;
1748     if (sock->protocol) {
1749       SilcServerFailureContext f;
1750       f = silc_calloc(1, sizeof(*f));
1751       f->server = server;
1752       f->sock = sock;
1753       
1754       /* We will wait 5 seconds to process this failure packet */
1755       silc_schedule_task_add(server->schedule, sock->sock,
1756                          silc_server_failure_callback, (void *)f, 5, 0,
1757                          SILC_TASK_TIMEOUT, SILC_TASK_PRI_NORMAL);
1758     }
1759     break;
1760
1761   case SILC_PACKET_REJECT:
1762     SILC_LOG_DEBUG(("Reject packet"));
1763     if (packet->flags & SILC_PACKET_FLAG_LIST)
1764       break;
1765     return;
1766     break;
1767
1768   case SILC_PACKET_NOTIFY:
1769     /*
1770      * Received notify packet. Server can receive notify packets from
1771      * router. Server then relays the notify messages to clients if needed.
1772      */
1773     SILC_LOG_DEBUG(("Notify packet"));
1774     if (packet->flags & SILC_PACKET_FLAG_LIST)
1775       silc_server_notify_list(server, sock, packet);
1776     else
1777       silc_server_notify(server, sock, packet);
1778     break;
1779
1780     /* 
1781      * Channel packets
1782      */
1783   case SILC_PACKET_CHANNEL_MESSAGE:
1784     /*
1785      * Received channel message. Channel messages are special packets
1786      * (although probably most common ones) thus they are handled
1787      * specially.
1788      */
1789     SILC_LOG_DEBUG(("Channel Message packet"));
1790     if (packet->flags & SILC_PACKET_FLAG_LIST)
1791       break;
1792     idata->last_receive = time(NULL);
1793     silc_server_channel_message(server, sock, packet);
1794     break;
1795
1796   case SILC_PACKET_CHANNEL_KEY:
1797     /*
1798      * Received key for channel. As channels are created by the router
1799      * the keys are as well. We will distribute the key to all of our
1800      * locally connected clients on the particular channel. Router
1801      * never receives this channel and thus is ignored.
1802      */
1803     SILC_LOG_DEBUG(("Channel Key packet"));
1804     if (packet->flags & SILC_PACKET_FLAG_LIST)
1805       break;
1806     silc_server_channel_key(server, sock, packet);
1807     break;
1808
1809     /*
1810      * Command packets
1811      */
1812   case SILC_PACKET_COMMAND:
1813     /*
1814      * Recived command. Processes the command request and allocates the
1815      * command context and calls the command.
1816      */
1817     SILC_LOG_DEBUG(("Command packet"));
1818     if (packet->flags & SILC_PACKET_FLAG_LIST)
1819       break;
1820     silc_server_command_process(server, sock, packet);
1821     break;
1822
1823   case SILC_PACKET_COMMAND_REPLY:
1824     /*
1825      * Received command reply packet. Received command reply to command. It
1826      * may be reply to command sent by us or reply to command sent by client
1827      * that we've routed further.
1828      */
1829     SILC_LOG_DEBUG(("Command Reply packet"));
1830     if (packet->flags & SILC_PACKET_FLAG_LIST)
1831       break;
1832     silc_server_command_reply(server, sock, packet);
1833     break;
1834
1835     /*
1836      * Private Message packets
1837      */
1838   case SILC_PACKET_PRIVATE_MESSAGE:
1839     /*
1840      * Received private message packet. The packet is coming from either
1841      * client or server.
1842      */
1843     SILC_LOG_DEBUG(("Private Message packet"));
1844     if (packet->flags & SILC_PACKET_FLAG_LIST)
1845       break;
1846     idata->last_receive = time(NULL);
1847     silc_server_private_message(server, sock, packet);
1848     break;
1849
1850   case SILC_PACKET_PRIVATE_MESSAGE_KEY:
1851     /*
1852      * Private message key packet.
1853      */
1854     if (packet->flags & SILC_PACKET_FLAG_LIST)
1855       break;
1856     silc_server_private_message_key(server, sock, packet);
1857     break;
1858
1859     /*
1860      * Key Exchange protocol packets
1861      */
1862   case SILC_PACKET_KEY_EXCHANGE:
1863     SILC_LOG_DEBUG(("KE packet"));
1864     if (packet->flags & SILC_PACKET_FLAG_LIST)
1865       break;
1866
1867     if (sock->protocol && sock->protocol->protocol &&
1868         sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_KEY_EXCHANGE) {
1869
1870       SilcServerKEInternalContext *proto_ctx = 
1871         (SilcServerKEInternalContext *)sock->protocol->context;
1872
1873       proto_ctx->packet = silc_packet_context_dup(packet);
1874
1875       /* Let the protocol handle the packet */
1876       silc_protocol_execute(sock->protocol, server->schedule, 0, 100000);
1877     } else {
1878       SILC_LOG_ERROR(("Received Key Exchange packet but no key exchange "
1879                       "protocol active, packet dropped."));
1880     }
1881     break;
1882
1883   case SILC_PACKET_KEY_EXCHANGE_1:
1884     SILC_LOG_DEBUG(("KE 1 packet"));
1885     if (packet->flags & SILC_PACKET_FLAG_LIST)
1886       break;
1887
1888     if (sock->protocol && sock->protocol->protocol &&
1889         (sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_KEY_EXCHANGE ||
1890          sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY)) {
1891
1892       if (sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY) {
1893         SilcServerRekeyInternalContext *proto_ctx = 
1894           (SilcServerRekeyInternalContext *)sock->protocol->context;
1895         
1896         if (proto_ctx->packet)
1897           silc_packet_context_free(proto_ctx->packet);
1898         
1899         proto_ctx->packet = silc_packet_context_dup(packet);
1900
1901         /* Let the protocol handle the packet */
1902         silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
1903       } else {
1904         SilcServerKEInternalContext *proto_ctx = 
1905           (SilcServerKEInternalContext *)sock->protocol->context;
1906         
1907         if (proto_ctx->packet)
1908           silc_packet_context_free(proto_ctx->packet);
1909         
1910         proto_ctx->packet = silc_packet_context_dup(packet);
1911         proto_ctx->dest_id_type = packet->src_id_type;
1912         proto_ctx->dest_id = silc_id_str2id(packet->src_id, packet->src_id_len,
1913                                             packet->src_id_type);
1914         if (!proto_ctx->dest_id)
1915           break;
1916
1917         /* Let the protocol handle the packet */
1918         silc_protocol_execute(sock->protocol, server->schedule, 
1919                               0, 100000);
1920       }
1921     } else {
1922       SILC_LOG_ERROR(("Received Key Exchange 1 packet but no key exchange "
1923                       "protocol active, packet dropped."));
1924     }
1925     break;
1926
1927   case SILC_PACKET_KEY_EXCHANGE_2:
1928     SILC_LOG_DEBUG(("KE 2 packet"));
1929     if (packet->flags & SILC_PACKET_FLAG_LIST)
1930       break;
1931
1932     if (sock->protocol && sock->protocol->protocol &&
1933         (sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_KEY_EXCHANGE ||
1934          sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY)) {
1935
1936       if (sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY) {
1937         SilcServerRekeyInternalContext *proto_ctx = 
1938           (SilcServerRekeyInternalContext *)sock->protocol->context;
1939         
1940         if (proto_ctx->packet)
1941           silc_packet_context_free(proto_ctx->packet);
1942         
1943         proto_ctx->packet = silc_packet_context_dup(packet);
1944
1945         /* Let the protocol handle the packet */
1946         silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
1947       } else {
1948         SilcServerKEInternalContext *proto_ctx = 
1949           (SilcServerKEInternalContext *)sock->protocol->context;
1950         
1951         if (proto_ctx->packet)
1952           silc_packet_context_free(proto_ctx->packet);
1953         
1954         proto_ctx->packet = silc_packet_context_dup(packet);
1955         proto_ctx->dest_id_type = packet->src_id_type;
1956         proto_ctx->dest_id = silc_id_str2id(packet->src_id, packet->src_id_len,
1957                                             packet->src_id_type);
1958         if (!proto_ctx->dest_id)
1959           break;
1960
1961         /* Let the protocol handle the packet */
1962         silc_protocol_execute(sock->protocol, server->schedule, 
1963                               0, 100000);
1964       }
1965     } else {
1966       SILC_LOG_ERROR(("Received Key Exchange 2 packet but no key exchange "
1967                       "protocol active, packet dropped."));
1968     }
1969     break;
1970
1971   case SILC_PACKET_CONNECTION_AUTH_REQUEST:
1972     /*
1973      * Connection authentication request packet. When we receive this packet
1974      * we will send to the other end information about our mandatory
1975      * authentication method for the connection. This packet maybe received
1976      * at any time. 
1977      */
1978     SILC_LOG_DEBUG(("Connection authentication request packet"));
1979     if (packet->flags & SILC_PACKET_FLAG_LIST)
1980       break;
1981     silc_server_connection_auth_request(server, sock, packet);
1982     break;
1983
1984     /*
1985      * Connection Authentication protocol packets
1986      */
1987   case SILC_PACKET_CONNECTION_AUTH:
1988     /* Start of the authentication protocol. We receive here the 
1989        authentication data and will verify it. */
1990     SILC_LOG_DEBUG(("Connection auth packet"));
1991     if (packet->flags & SILC_PACKET_FLAG_LIST)
1992       break;
1993
1994     if (sock->protocol && sock->protocol->protocol->type 
1995         == SILC_PROTOCOL_SERVER_CONNECTION_AUTH) {
1996
1997       SilcServerConnAuthInternalContext *proto_ctx = 
1998         (SilcServerConnAuthInternalContext *)sock->protocol->context;
1999
2000       proto_ctx->packet = silc_packet_context_dup(packet);
2001
2002       /* Let the protocol handle the packet */
2003       silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
2004     } else {
2005       SILC_LOG_ERROR(("Received Connection Auth packet but no authentication "
2006                       "protocol active, packet dropped."));
2007     }
2008     break;
2009
2010   case SILC_PACKET_NEW_ID:
2011     /*
2012      * Received New ID packet. This includes some new ID that has been
2013      * created. It may be for client, server or channel. This is the way
2014      * to distribute information about new registered entities in the
2015      * SILC network.
2016      */
2017     SILC_LOG_DEBUG(("New ID packet"));
2018     if (packet->flags & SILC_PACKET_FLAG_LIST)
2019       silc_server_new_id_list(server, sock, packet);
2020     else
2021       silc_server_new_id(server, sock, packet);
2022     break;
2023
2024   case SILC_PACKET_NEW_CLIENT:
2025     /*
2026      * Received new client packet. This includes client information that
2027      * we will use to create initial client ID. After creating new
2028      * ID we will send it to the client.
2029      */
2030     SILC_LOG_DEBUG(("New Client packet"));
2031     if (packet->flags & SILC_PACKET_FLAG_LIST)
2032       break;
2033     silc_server_new_client(server, sock, packet);
2034     break;
2035
2036   case SILC_PACKET_NEW_SERVER:
2037     /*
2038      * Received new server packet. This includes Server ID and some other
2039      * information that we may save. This is received after server has 
2040      * connected to us.
2041      */
2042     SILC_LOG_DEBUG(("New Server packet"));
2043     if (packet->flags & SILC_PACKET_FLAG_LIST)
2044       break;
2045     silc_server_new_server(server, sock, packet);
2046     break;
2047
2048   case SILC_PACKET_NEW_CHANNEL:
2049     /*
2050      * Received new channel packet. Information about new channel in the
2051      * network are distributed using this packet.
2052      */
2053     SILC_LOG_DEBUG(("New Channel packet"));
2054     if (packet->flags & SILC_PACKET_FLAG_LIST)
2055       silc_server_new_channel_list(server, sock, packet);
2056     else
2057       silc_server_new_channel(server, sock, packet);
2058     break;
2059
2060   case SILC_PACKET_HEARTBEAT:
2061     /*
2062      * Received heartbeat.
2063      */
2064     SILC_LOG_DEBUG(("Heartbeat packet"));
2065     if (packet->flags & SILC_PACKET_FLAG_LIST)
2066       break;
2067     break;
2068
2069   case SILC_PACKET_KEY_AGREEMENT:
2070     /*
2071      * Received heartbeat.
2072      */
2073     SILC_LOG_DEBUG(("Key agreement packet"));
2074     if (packet->flags & SILC_PACKET_FLAG_LIST)
2075       break;
2076     silc_server_key_agreement(server, sock, packet);
2077     break;
2078
2079   case SILC_PACKET_REKEY:
2080     /*
2081      * Received re-key packet. The sender wants to regenerate the session
2082      * keys.
2083      */
2084     SILC_LOG_DEBUG(("Re-key packet"));
2085     if (packet->flags & SILC_PACKET_FLAG_LIST)
2086       break;
2087     silc_server_rekey(server, sock, packet);
2088     break;
2089
2090   case SILC_PACKET_REKEY_DONE:
2091     /*
2092      * The re-key is done.
2093      */
2094     SILC_LOG_DEBUG(("Re-key done packet"));
2095     if (packet->flags & SILC_PACKET_FLAG_LIST)
2096       break;
2097
2098     if (sock->protocol && sock->protocol->protocol &&
2099         sock->protocol->protocol->type == SILC_PROTOCOL_SERVER_REKEY) {
2100
2101       SilcServerRekeyInternalContext *proto_ctx = 
2102         (SilcServerRekeyInternalContext *)sock->protocol->context;
2103
2104       if (proto_ctx->packet)
2105         silc_packet_context_free(proto_ctx->packet);
2106
2107       proto_ctx->packet = silc_packet_context_dup(packet);
2108
2109       /* Let the protocol handle the packet */
2110       silc_protocol_execute(sock->protocol, server->schedule, 0, 0);
2111     } else {
2112       SILC_LOG_ERROR(("Received Re-key done packet but no re-key "
2113                       "protocol active, packet dropped."));
2114     }
2115     break;
2116
2117   case SILC_PACKET_FTP:
2118     /* Ignored */
2119     break;
2120
2121   case SILC_PACKET_RESUME_ROUTER:
2122     /* Resume router packet received. This packet is received for backup
2123        router resuming protocol. */
2124     SILC_LOG_DEBUG(("Resume router packet"));
2125     if (packet->flags & SILC_PACKET_FLAG_LIST)
2126       break;
2127     silc_server_backup_resume_router(server, sock, packet);
2128     break;
2129
2130   default:
2131     SILC_LOG_ERROR(("Incorrect packet type %d, packet dropped", type));
2132     break;
2133   }
2134   
2135 }
2136
2137 /* Creates connection to a remote router. */
2138
2139 void silc_server_create_connection(SilcServer server,
2140                                    char *remote_host, uint32 port)
2141 {
2142   SilcServerConnection sconn;
2143
2144   /* Allocate connection object for hold connection specific stuff. */
2145   sconn = silc_calloc(1, sizeof(*sconn));
2146   sconn->server = server;
2147   sconn->remote_host = strdup(remote_host);
2148   sconn->remote_port = port;
2149
2150   silc_schedule_task_add(server->schedule, 0, 
2151                          silc_server_connect_router,
2152                          (void *)sconn, 0, 1, SILC_TASK_TIMEOUT, 
2153                          SILC_TASK_PRI_NORMAL);
2154 }
2155
2156 SILC_TASK_CALLBACK(silc_server_close_connection_final)
2157 {
2158   silc_socket_free((SilcSocketConnection)context);
2159 }
2160
2161 /* Closes connection to socket connection */
2162
2163 void silc_server_close_connection(SilcServer server,
2164                                   SilcSocketConnection sock)
2165 {
2166   SILC_LOG_INFO(("Closing connection %s:%d [%s]", sock->hostname,
2167                   sock->port,
2168                   (sock->type == SILC_SOCKET_TYPE_UNKNOWN ? "Unknown" :
2169                    sock->type == SILC_SOCKET_TYPE_CLIENT ? "Client" :
2170                    sock->type == SILC_SOCKET_TYPE_SERVER ? "Server" :
2171                    "Router")));
2172
2173   /* We won't listen for this connection anymore */
2174   silc_schedule_unset_listen_fd(server->schedule, sock->sock);
2175
2176   /* Unregister all tasks */
2177   silc_schedule_task_del_by_fd(server->schedule, sock->sock);
2178
2179   /* Close the actual connection */
2180   silc_net_close_connection(sock->sock);
2181   server->sockets[sock->sock] = NULL;
2182
2183   /* If sock->user_data is NULL then we'll check for active protocols
2184      here since the silc_server_free_sock_user_data has not been called
2185      for this connection. */
2186   if (!sock->user_data) {
2187     /* If any protocol is active cancel its execution. It will call
2188        the final callback which will finalize the disconnection. */
2189     if (sock->protocol) {
2190       silc_protocol_cancel(sock->protocol, server->schedule);
2191       sock->protocol->state = SILC_PROTOCOL_STATE_ERROR;
2192       silc_protocol_execute_final(sock->protocol, server->schedule);
2193       sock->protocol = NULL;
2194       return;
2195     }
2196   }
2197
2198   silc_schedule_task_add(server->schedule, 0, 
2199                          silc_server_close_connection_final,
2200                          (void *)sock, 0, 1, SILC_TASK_TIMEOUT, 
2201                          SILC_TASK_PRI_NORMAL);
2202 }
2203
2204 /* Sends disconnect message to remote connection and disconnects the 
2205    connection. */
2206
2207 void silc_server_disconnect_remote(SilcServer server,
2208                                    SilcSocketConnection sock,
2209                                    const char *fmt, ...)
2210 {
2211   va_list ap;
2212   unsigned char buf[4096];
2213
2214   if (!sock)
2215     return;
2216
2217   memset(buf, 0, sizeof(buf));
2218   va_start(ap, fmt);
2219   vsprintf(buf, fmt, ap);
2220   va_end(ap);
2221
2222   SILC_LOG_DEBUG(("Disconnecting remote host"));
2223
2224   /* Notify remote end that the conversation is over. The notify message
2225      is tried to be sent immediately. */
2226   silc_server_packet_send(server, sock, SILC_PACKET_DISCONNECT, 0,  
2227                           buf, strlen(buf), TRUE);
2228
2229   /* Mark the connection to be disconnected */
2230   SILC_SET_DISCONNECTED(sock);
2231   silc_server_close_connection(server, sock);
2232 }
2233
2234 typedef struct {
2235   SilcServer server;
2236   SilcClientEntry client;
2237 } *FreeClientInternal;
2238
2239 SILC_TASK_CALLBACK(silc_server_free_client_data_timeout)
2240 {
2241   FreeClientInternal i = (FreeClientInternal)context;
2242
2243   silc_idlist_del_data(i->client);
2244   silc_idcache_purge_by_context(i->server->local_list->clients, i->client);
2245   silc_free(i);
2246 }
2247
2248 /* Frees client data and notifies about client's signoff. */
2249
2250 void silc_server_free_client_data(SilcServer server, 
2251                                   SilcSocketConnection sock,
2252                                   SilcClientEntry client, 
2253                                   int notify,
2254                                   char *signoff)
2255 {
2256   FreeClientInternal i = silc_calloc(1, sizeof(*i));
2257
2258   /* If there is pending outgoing data for the client then purge it
2259      to the network before removing the client entry. */
2260   silc_server_packet_queue_purge(server, sock);
2261
2262   /* Send SIGNOFF notify to routers. */
2263   if (notify && !server->standalone && server->router)
2264     silc_server_send_notify_signoff(server, server->router->connection,
2265                                     server->server_type == SILC_SERVER ?
2266                                     FALSE : TRUE, client->id, signoff);
2267
2268   /* Remove client from all channels */
2269   if (notify)
2270     silc_server_remove_from_channels(server, NULL, client, 
2271                                      TRUE, signoff, TRUE);
2272   else
2273     silc_server_remove_from_channels(server, NULL, client, 
2274                                      FALSE, NULL, FALSE);
2275
2276   /* We will not delete the client entry right away. We will take it
2277      into history (for WHOWAS command) for 5 minutes */
2278   i->server = server;
2279   i->client = client;
2280   silc_schedule_task_add(server->schedule, 0, 
2281                          silc_server_free_client_data_timeout,
2282                          (void *)i, 300, 0,
2283                          SILC_TASK_TIMEOUT, SILC_TASK_PRI_LOW);
2284   client->data.status &= ~SILC_IDLIST_STATUS_REGISTERED;
2285   client->router = NULL;
2286   client->connection = NULL;
2287
2288   /* Free the client entry and everything in it */
2289   server->stat.my_clients--;
2290   server->stat.clients--;
2291   if (server->server_type == SILC_ROUTER)
2292     server->stat.cell_clients--;
2293 }
2294
2295 /* Frees user_data pointer from socket connection object. This also sends
2296    appropriate notify packets to the network to inform about leaving
2297    entities. */
2298
2299 void silc_server_free_sock_user_data(SilcServer server, 
2300                                      SilcSocketConnection sock)
2301 {
2302   SILC_LOG_DEBUG(("Start"));
2303
2304   switch (sock->type) {
2305   case SILC_SOCKET_TYPE_CLIENT:
2306     {
2307       SilcClientEntry user_data = (SilcClientEntry)sock->user_data;
2308       silc_server_free_client_data(server, sock, user_data, TRUE, NULL);
2309       break;
2310     }
2311   case SILC_SOCKET_TYPE_SERVER:
2312   case SILC_SOCKET_TYPE_ROUTER:
2313     {
2314       SilcServerEntry user_data = (SilcServerEntry)sock->user_data;
2315       SilcServerEntry backup_router = NULL;
2316
2317       /* If this was our primary router connection then we're lost to
2318          the outside world. */
2319       if (server->router == user_data) {
2320         backup_router = silc_server_backup_get(server);
2321
2322         /* Check whether we have a backup router connection */
2323         if (!backup_router || backup_router == user_data) {
2324           silc_schedule_task_add(server->schedule, 0, 
2325                                  silc_server_connect_to_router,
2326                                  server, 1, 0,
2327                                  SILC_TASK_TIMEOUT,
2328                                  SILC_TASK_PRI_NORMAL);
2329
2330           server->id_entry->router = NULL;
2331           server->router = NULL;
2332           server->standalone = TRUE;
2333           backup_router = NULL;
2334         } else {
2335           SILC_LOG_INFO(("New primary router is backup router %s",
2336                          backup_router->server_name));
2337           SILC_LOG_DEBUG(("New primary router is backup router %s",
2338                           backup_router->server_name));
2339           server->id_entry->router = backup_router;
2340           server->router = backup_router;
2341           server->router_connect = time(0);
2342           if (server->server_type == SILC_BACKUP_ROUTER) {
2343             server->server_type = SILC_ROUTER;
2344
2345             /* We'll need to constantly try to reconnect to the primary
2346                router so that we'll see when it comes back online. */
2347             silc_server_backup_reconnect(server, sock->ip, sock->port,
2348                                          silc_server_backup_connected,
2349                                          NULL);
2350           }
2351
2352           /* Mark this connection as replaced */
2353           silc_server_backup_replaced_add(server, user_data->id, 
2354                                           backup_router);
2355         }
2356       }
2357
2358       if (!backup_router) {
2359         /* Free all client entries that this server owns as they will
2360            become invalid now as well. */
2361         if (user_data->id)
2362           silc_server_remove_clients_by_server(server, user_data, TRUE);
2363       } else {
2364         /* Update the client entries of this server to the new backup
2365            router. This also removes the clients that *really* was owned
2366            by the primary router and went down with the router.  */
2367         silc_server_update_clients_by_server(server, user_data, backup_router,
2368                                              TRUE, TRUE);
2369       }
2370
2371       /* Free the server entry */
2372       silc_server_backup_del(server, user_data);
2373       silc_server_backup_replaced_del(server, user_data);
2374       silc_idlist_del_data(user_data);
2375       silc_idlist_del_server(server->local_list, user_data);
2376       server->stat.my_servers--;
2377       server->stat.servers--;
2378       if (server->server_type == SILC_ROUTER)
2379         server->stat.cell_servers--;
2380
2381       if (backup_router) {
2382         /* Announce all of our stuff that was created about 5 minutes ago.
2383            The backup router knows all the other stuff already. */
2384         if (server->server_type == SILC_ROUTER)
2385           silc_server_announce_servers(server, FALSE, 0,
2386                                        server->router->connection);
2387
2388         /* Announce our clients and channels to the router */
2389         silc_server_announce_clients(server, 0,
2390                                      server->router->connection);
2391         silc_server_announce_channels(server, 0,
2392                                       server->router->connection);
2393 #if 0
2394         if (server->server_type == SILC_ROUTER)
2395           silc_server_announce_servers(server, FALSE, time(0) - 300,
2396                                        server->router->connection);
2397
2398         /* Announce our clients and channels to the router */
2399         silc_server_announce_clients(server, time(0) - 300,
2400                                      server->router->connection);
2401         silc_server_announce_channels(server, time(0) - 300,
2402                                       server->router->connection);
2403 #endif
2404       }
2405       break;
2406     }
2407   default:
2408     {
2409       SilcUnknownEntry user_data = (SilcUnknownEntry)sock->user_data;
2410
2411       silc_idlist_del_data(user_data);
2412       silc_free(user_data);
2413       break;
2414     }
2415   }
2416
2417   /* If any protocol is active cancel its execution */
2418   if (sock->protocol) {
2419     silc_protocol_cancel(sock->protocol, server->schedule);
2420     sock->protocol->state = SILC_PROTOCOL_STATE_ERROR;
2421     silc_protocol_execute_final(sock->protocol, server->schedule);
2422     sock->protocol = NULL;
2423   }
2424
2425   sock->user_data = NULL;
2426 }
2427
2428 /* Removes client from all channels it has joined. This is used when client
2429    connection is disconnected. If the client on a channel is last, the
2430    channel is removed as well. This sends the SIGNOFF notify types. */
2431
2432 void silc_server_remove_from_channels(SilcServer server, 
2433                                       SilcSocketConnection sock,
2434                                       SilcClientEntry client,
2435                                       int notify,
2436                                       char *signoff_message,
2437                                       int keygen)
2438 {
2439   SilcChannelEntry channel;
2440   SilcChannelClientEntry chl;
2441   SilcHashTableList htl;
2442   SilcBuffer clidp;
2443
2444   SILC_LOG_DEBUG(("Start"));
2445
2446   if (!client || !client->id)
2447     return;
2448
2449   clidp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
2450
2451   /* Remove the client from all channels. The client is removed from
2452      the channels' user list. */
2453   silc_hash_table_list(client->channels, &htl);
2454   while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
2455     channel = chl->channel;
2456
2457     /* Remove channel from client's channel list */
2458     silc_hash_table_del(client->channels, channel);
2459
2460     /* Remove channel if there is no users anymore */
2461     if (server->server_type == SILC_ROUTER &&
2462         silc_hash_table_count(channel->user_list) < 2) {
2463       if (channel->rekey)
2464         silc_schedule_task_del_by_context(server->schedule, channel->rekey);
2465       if (!silc_idlist_del_channel(server->local_list, channel))
2466         silc_idlist_del_channel(server->global_list, channel);
2467       server->stat.my_channels--;
2468       continue;
2469     }
2470
2471     /* Remove client from channel's client list */
2472     silc_hash_table_del(channel->user_list, chl->client);
2473
2474     /* If there is no global users on the channel anymore mark the channel
2475        as local channel. Do not check if the removed client is local client. */
2476     if (server->server_type != SILC_ROUTER && channel->global_users && 
2477         chl->client->router && !silc_server_channel_has_global(channel))
2478       channel->global_users = FALSE;
2479
2480     silc_free(chl);
2481     server->stat.my_chanclients--;
2482
2483     /* If there is not at least one local user on the channel then we don't
2484        need the channel entry anymore, we can remove it safely. */
2485     if (server->server_type != SILC_ROUTER &&
2486         !silc_server_channel_has_local(channel)) {
2487       /* Notify about leaving client if this channel has global users. */
2488       if (notify && channel->global_users)
2489         silc_server_send_notify_to_channel(server, NULL, channel, FALSE,
2490                                            SILC_NOTIFY_TYPE_SIGNOFF, 
2491                                            signoff_message ? 2 : 1,
2492                                            clidp->data, clidp->len,
2493                                            signoff_message, signoff_message ?
2494                                            strlen(signoff_message) : 0);
2495
2496       if (channel->rekey)
2497         silc_schedule_task_del_by_context(server->schedule, channel->rekey);
2498
2499       if (channel->founder_key) {
2500         /* The founder auth data exists, do not remove the channel entry */
2501         SilcChannelClientEntry chl2;
2502         SilcHashTableList htl2;
2503
2504         channel->id = NULL;
2505
2506         silc_hash_table_list(channel->user_list, &htl2);
2507         while (silc_hash_table_get(&htl2, NULL, (void *)&chl2)) {
2508           silc_hash_table_del(chl2->client->channels, channel);
2509           silc_hash_table_del(channel->user_list, chl2->client);
2510           silc_free(chl2);
2511         }
2512         continue;
2513       }
2514
2515       /* Remove the channel entry */
2516       if (!silc_idlist_del_channel(server->local_list, channel))
2517         silc_idlist_del_channel(server->global_list, channel);
2518       server->stat.my_channels--;
2519       continue;
2520     }
2521
2522     /* Send notify to channel about client leaving SILC and thus
2523        the entire channel. */
2524     if (notify)
2525       silc_server_send_notify_to_channel(server, NULL, channel, FALSE,
2526                                          SILC_NOTIFY_TYPE_SIGNOFF, 
2527                                          signoff_message ? 2 : 1,
2528                                          clidp->data, clidp->len,
2529                                          signoff_message, signoff_message ?
2530                                          strlen(signoff_message) : 0);
2531
2532     if (keygen && !(channel->mode & SILC_CHANNEL_MODE_PRIVKEY)) {
2533       /* Re-generate channel key */
2534       if (!silc_server_create_channel_key(server, channel, 0))
2535         return;
2536       
2537       /* Send the channel key to the channel. The key of course is not sent
2538          to the client who was removed from the channel. */
2539       silc_server_send_channel_key(server, client->connection, channel, 
2540                                    server->server_type == SILC_ROUTER ? 
2541                                    FALSE : !server->standalone);
2542     }
2543   }
2544
2545   silc_buffer_free(clidp);
2546 }
2547
2548 /* Removes client from one channel. This is used for example when client
2549    calls LEAVE command to remove itself from the channel. Returns TRUE
2550    if channel still exists and FALSE if the channel is removed when
2551    last client leaves the channel. If `notify' is FALSE notify messages
2552    are not sent. */
2553
2554 int silc_server_remove_from_one_channel(SilcServer server, 
2555                                         SilcSocketConnection sock,
2556                                         SilcChannelEntry channel,
2557                                         SilcClientEntry client,
2558                                         int notify)
2559 {
2560   SilcChannelClientEntry chl;
2561   SilcBuffer clidp;
2562
2563   SILC_LOG_DEBUG(("Start"));
2564
2565   /* Get the entry to the channel, if this client is not on the channel
2566      then return Ok. */
2567   if (!silc_hash_table_find(client->channels, channel, NULL, (void *)&chl))
2568     return TRUE;
2569
2570   /* Remove the client from the channel. The client is removed from
2571      the channel's user list. */
2572
2573   clidp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
2574
2575   /* Remove channel from client's channel list */
2576   silc_hash_table_del(client->channels, chl->channel);
2577
2578   /* Remove channel if there is no users anymore */
2579   if (server->server_type == SILC_ROUTER &&
2580       silc_hash_table_count(channel->user_list) < 2) {
2581     if (channel->rekey)
2582       silc_schedule_task_del_by_context(server->schedule, channel->rekey);
2583     if (!silc_idlist_del_channel(server->local_list, channel))
2584       silc_idlist_del_channel(server->global_list, channel);
2585     silc_buffer_free(clidp);
2586     server->stat.my_channels--;
2587     return FALSE;
2588   }
2589
2590   /* Remove client from channel's client list */
2591   silc_hash_table_del(channel->user_list, chl->client);
2592   
2593   /* If there is no global users on the channel anymore mark the channel
2594      as local channel. Do not check if the client is local client. */
2595   if (server->server_type != SILC_ROUTER && channel->global_users &&
2596       chl->client->router && !silc_server_channel_has_global(channel))
2597     channel->global_users = FALSE;
2598
2599   silc_free(chl);
2600   server->stat.my_chanclients--;
2601
2602   /* If there is not at least one local user on the channel then we don't
2603      need the channel entry anymore, we can remove it safely. */
2604   if (server->server_type != SILC_ROUTER &&
2605       !silc_server_channel_has_local(channel)) {
2606     /* Notify about leaving client if this channel has global users. */
2607     if (notify && channel->global_users)
2608       silc_server_send_notify_to_channel(server, NULL, channel, FALSE,
2609                                          SILC_NOTIFY_TYPE_LEAVE, 1,
2610                                          clidp->data, clidp->len);
2611     
2612     silc_buffer_free(clidp);
2613     
2614     if (channel->rekey)
2615       silc_schedule_task_del_by_context(server->schedule, channel->rekey);
2616
2617     if (channel->founder_key) {
2618       /* The founder auth data exists, do not remove the channel entry */
2619       SilcChannelClientEntry chl2;
2620       SilcHashTableList htl2;
2621       
2622       channel->id = NULL;
2623       
2624       silc_hash_table_list(channel->user_list, &htl2);
2625       while (silc_hash_table_get(&htl2, NULL, (void *)&chl2)) {
2626         silc_hash_table_del(chl2->client->channels, channel);
2627         silc_hash_table_del(channel->user_list, chl2->client);
2628         silc_free(chl2);
2629       }
2630       return FALSE;
2631     }
2632
2633     /* Remove the channel entry */
2634     if (!silc_idlist_del_channel(server->local_list, channel))
2635       silc_idlist_del_channel(server->global_list, channel);
2636     server->stat.my_channels--;
2637     return FALSE;
2638   }
2639
2640   /* Send notify to channel about client leaving the channel */
2641   if (notify)
2642     silc_server_send_notify_to_channel(server, NULL, channel, FALSE,
2643                                        SILC_NOTIFY_TYPE_LEAVE, 1,
2644                                        clidp->data, clidp->len);
2645
2646   silc_buffer_free(clidp);
2647   return TRUE;
2648 }
2649
2650 /* Timeout callback. This is called if connection is idle or for some
2651    other reason is not responding within some period of time. This 
2652    disconnects the remote end. */
2653
2654 SILC_TASK_CALLBACK(silc_server_timeout_remote)
2655 {
2656   SilcServer server = (SilcServer)context;
2657   SilcSocketConnection sock = server->sockets[fd];
2658
2659   SILC_LOG_DEBUG(("Start"));
2660
2661   if (!sock)
2662     return;
2663
2664   /* If we have protocol active we must assure that we call the protocol's
2665      final callback so that all the memory is freed. */
2666   if (sock->protocol) {
2667     sock->protocol->state = SILC_PROTOCOL_STATE_ERROR;
2668     silc_protocol_execute_final(sock->protocol, server->schedule);
2669     return;
2670   }
2671
2672   if (sock->user_data)
2673     silc_server_free_sock_user_data(server, sock);
2674
2675   silc_server_disconnect_remote(server, sock, "Server closed connection: "
2676                                 "Connection timeout");
2677 }
2678
2679 /* Creates new channel. Sends NEW_CHANNEL packet to primary route. This
2680    function may be used only by router. In real SILC network all channels
2681    are created by routers thus this function is never used by normal
2682    server. */
2683
2684 SilcChannelEntry silc_server_create_new_channel(SilcServer server, 
2685                                                 SilcServerID *router_id,
2686                                                 char *cipher, 
2687                                                 char *hmac,
2688                                                 char *channel_name,
2689                                                 int broadcast)
2690 {
2691   SilcChannelID *channel_id;
2692   SilcChannelEntry entry;
2693   SilcCipher key;
2694   SilcHmac newhmac;
2695
2696   SILC_LOG_DEBUG(("Creating new channel"));
2697
2698   if (!cipher)
2699     cipher = SILC_DEFAULT_CIPHER;
2700   if (!hmac)
2701     hmac = SILC_DEFAULT_HMAC;
2702
2703   /* Allocate cipher */
2704   if (!silc_cipher_alloc(cipher, &key))
2705     return NULL;
2706
2707   /* Allocate hmac */
2708   if (!silc_hmac_alloc(hmac, NULL, &newhmac)) {
2709     silc_cipher_free(key);
2710     return NULL;
2711   }
2712
2713   channel_name = strdup(channel_name);
2714
2715   /* Create the channel */
2716   if (!silc_id_create_channel_id(server, router_id, server->rng, 
2717                                  &channel_id)) {
2718     silc_free(channel_name);
2719     silc_cipher_free(key);
2720     silc_hmac_free(newhmac);
2721     return NULL;
2722   }
2723   entry = silc_idlist_add_channel(server->local_list, channel_name, 
2724                                   SILC_CHANNEL_MODE_NONE, channel_id, 
2725                                   NULL, key, newhmac);
2726   if (!entry) {
2727     silc_free(channel_name);
2728     silc_cipher_free(key);
2729     silc_hmac_free(newhmac);
2730     return NULL;
2731   }
2732
2733   entry->cipher = strdup(cipher);
2734   entry->hmac_name = strdup(hmac);
2735
2736   /* Now create the actual key material */
2737   if (!silc_server_create_channel_key(server, entry, 
2738                                       silc_cipher_get_key_len(key) / 8)) {
2739     silc_free(channel_name);
2740     silc_cipher_free(key);
2741     silc_hmac_free(newhmac);
2742     silc_free(entry->cipher);
2743     silc_free(entry->hmac_name);
2744     return NULL;
2745   }
2746
2747   /* Notify other routers about the new channel. We send the packet
2748      to our primary route. */
2749   if (broadcast && server->standalone == FALSE)
2750     silc_server_send_new_channel(server, server->router->connection, TRUE, 
2751                                  channel_name, entry->id, 
2752                                  silc_id_get_len(entry->id, SILC_ID_CHANNEL),
2753                                  entry->mode);
2754
2755   server->stat.my_channels++;
2756
2757   return entry;
2758 }
2759
2760 /* Same as above but creates the channel with Channel ID `channel_id. */
2761
2762 SilcChannelEntry 
2763 silc_server_create_new_channel_with_id(SilcServer server, 
2764                                        char *cipher, 
2765                                        char *hmac,
2766                                        char *channel_name,
2767                                        SilcChannelID *channel_id,
2768                                        int broadcast)
2769 {
2770   SilcChannelEntry entry;
2771   SilcCipher key;
2772   SilcHmac newhmac;
2773
2774   SILC_LOG_DEBUG(("Creating new channel"));
2775
2776   if (!cipher)
2777     cipher = SILC_DEFAULT_CIPHER;
2778   if (!hmac)
2779     hmac = SILC_DEFAULT_HMAC;
2780
2781   /* Allocate cipher */
2782   if (!silc_cipher_alloc(cipher, &key))
2783     return NULL;
2784
2785   /* Allocate hmac */
2786   if (!silc_hmac_alloc(hmac, NULL, &newhmac)) {
2787     silc_cipher_free(key);
2788     return NULL;
2789   }
2790
2791   channel_name = strdup(channel_name);
2792
2793   /* Create the channel */
2794   entry = silc_idlist_add_channel(server->local_list, channel_name, 
2795                                   SILC_CHANNEL_MODE_NONE, channel_id, 
2796                                   NULL, key, newhmac);
2797   if (!entry) {
2798     silc_free(channel_name);
2799     return NULL;
2800   }
2801
2802   /* Now create the actual key material */
2803   if (!silc_server_create_channel_key(server, entry, 
2804                                       silc_cipher_get_key_len(key) / 8)) {
2805     silc_free(channel_name);
2806     return NULL;
2807   }
2808
2809   /* Notify other routers about the new channel. We send the packet
2810      to our primary route. */
2811   if (broadcast && server->standalone == FALSE)
2812     silc_server_send_new_channel(server, server->router->connection, TRUE, 
2813                                  channel_name, entry->id, 
2814                                  silc_id_get_len(entry->id, SILC_ID_CHANNEL),
2815                                  entry->mode);
2816
2817   server->stat.my_channels++;
2818
2819   return entry;
2820 }
2821
2822 /* Channel's key re-key timeout callback. */
2823
2824 SILC_TASK_CALLBACK(silc_server_channel_key_rekey)
2825 {
2826   SilcServerChannelRekey rekey = (SilcServerChannelRekey)context;
2827   SilcServer server = (SilcServer)rekey->context;
2828
2829   rekey->task = NULL;
2830
2831   if (!silc_server_create_channel_key(server, rekey->channel, rekey->key_len))
2832     return;
2833
2834   silc_server_send_channel_key(server, NULL, rekey->channel, FALSE);
2835 }
2836
2837 /* Generates new channel key. This is used to create the initial channel key
2838    but also to re-generate new key for channel. If `key_len' is provided
2839    it is the bytes of the key length. */
2840
2841 bool silc_server_create_channel_key(SilcServer server, 
2842                                     SilcChannelEntry channel,
2843                                     uint32 key_len)
2844 {
2845   int i;
2846   unsigned char channel_key[32], hash[32];
2847   uint32 len;
2848
2849   SILC_LOG_DEBUG(("Generating channel key"));
2850
2851   if (channel->mode & SILC_CHANNEL_MODE_PRIVKEY) {
2852     SILC_LOG_DEBUG(("Channel has private keys, will not generate new key"));
2853     return TRUE;
2854   }
2855
2856   if (!channel->channel_key)
2857     if (!silc_cipher_alloc(SILC_DEFAULT_CIPHER, &channel->channel_key))
2858       return FALSE;
2859
2860   if (key_len)
2861     len = key_len;
2862   else if (channel->key_len)
2863     len = channel->key_len / 8;
2864   else
2865     len = silc_cipher_get_key_len(channel->channel_key) / 8;
2866
2867   /* Create channel key */
2868   for (i = 0; i < len; i++) channel_key[i] = silc_rng_get_byte(server->rng);
2869   
2870   /* Set the key */
2871   silc_cipher_set_key(channel->channel_key, channel_key, len * 8);
2872
2873   /* Remove old key if exists */
2874   if (channel->key) {
2875     memset(channel->key, 0, channel->key_len / 8);
2876     silc_free(channel->key);
2877   }
2878
2879   /* Save the key */
2880   channel->key_len = len * 8;
2881   channel->key = silc_calloc(len, sizeof(*channel->key));
2882   memcpy(channel->key, channel_key, len);
2883   memset(channel_key, 0, sizeof(channel_key));
2884
2885   /* Generate HMAC key from the channel key data and set it */
2886   if (!channel->hmac)
2887     silc_hmac_alloc(SILC_DEFAULT_HMAC, NULL, &channel->hmac);
2888   silc_hash_make(channel->hmac->hash, channel->key, len, hash);
2889   silc_hmac_set_key(channel->hmac, hash, silc_hash_len(channel->hmac->hash));
2890   memset(hash, 0, sizeof(hash));
2891
2892   if (server->server_type == SILC_ROUTER) {
2893     if (!channel->rekey)
2894       channel->rekey = silc_calloc(1, sizeof(*channel->rekey));
2895     channel->rekey->context = (void *)server;
2896     channel->rekey->channel = channel;
2897     channel->rekey->key_len = key_len;
2898     if (channel->rekey->task)
2899       silc_schedule_task_del(server->schedule, channel->rekey->task);
2900
2901     channel->rekey->task = 
2902       silc_schedule_task_add(server->schedule, 0, 
2903                              silc_server_channel_key_rekey,
2904                              (void *)channel->rekey, 3600, 0,
2905                              SILC_TASK_TIMEOUT,
2906                              SILC_TASK_PRI_NORMAL);
2907   }
2908
2909   return TRUE;
2910 }
2911
2912 /* Saves the channel key found in the encoded `key_payload' buffer. This 
2913    function is used when we receive Channel Key Payload and also when we're
2914    processing JOIN command reply. Returns entry to the channel. */
2915
2916 SilcChannelEntry silc_server_save_channel_key(SilcServer server,
2917                                               SilcBuffer key_payload,
2918                                               SilcChannelEntry channel)
2919 {
2920   SilcChannelKeyPayload payload = NULL;
2921   SilcChannelID *id = NULL;
2922   unsigned char *tmp, hash[32];
2923   uint32 tmp_len;
2924   char *cipher;
2925
2926   SILC_LOG_DEBUG(("Start"));
2927
2928   /* Decode channel key payload */
2929   payload = silc_channel_key_payload_parse(key_payload);
2930   if (!payload) {
2931     SILC_LOG_ERROR(("Bad channel key payload, dropped"));
2932     channel = NULL;
2933     goto out;
2934   }
2935
2936   /* Get the channel entry */
2937   if (!channel) {
2938
2939     /* Get channel ID */
2940     tmp = silc_channel_key_get_id(payload, &tmp_len);
2941     id = silc_id_str2id(tmp, tmp_len, SILC_ID_CHANNEL);
2942     if (!id) {
2943       channel = NULL;
2944       goto out;
2945     }
2946
2947     channel = silc_idlist_find_channel_by_id(server->local_list, id, NULL);
2948     if (!channel) {
2949       channel = silc_idlist_find_channel_by_id(server->global_list, id, NULL);
2950       if (!channel) {
2951         SILC_LOG_ERROR(("Received key for non-existent channel"));
2952         goto out;
2953       }
2954     }
2955   }
2956
2957   tmp = silc_channel_key_get_key(payload, &tmp_len);
2958   if (!tmp) {
2959     channel = NULL;
2960     goto out;
2961   }
2962
2963   cipher = silc_channel_key_get_cipher(payload, NULL);
2964   if (!cipher) {
2965     channel = NULL;
2966     goto out;
2967   }
2968
2969   /* Remove old key if exists */
2970   if (channel->key) {
2971     memset(channel->key, 0, channel->key_len / 8);
2972     silc_free(channel->key);
2973     silc_cipher_free(channel->channel_key);
2974   }
2975
2976   /* Create new cipher */
2977   if (!silc_cipher_alloc(cipher, &channel->channel_key)) {
2978     channel = NULL;
2979     goto out;
2980   }
2981
2982   if (channel->cipher)
2983     silc_free(channel->cipher);
2984   channel->cipher = strdup(cipher);
2985
2986   /* Save the key */
2987   channel->key_len = tmp_len * 8;
2988   channel->key = silc_calloc(tmp_len, sizeof(unsigned char));
2989   memcpy(channel->key, tmp, tmp_len);
2990   silc_cipher_set_key(channel->channel_key, tmp, channel->key_len);
2991
2992   /* Generate HMAC key from the channel key data and set it */
2993   if (!channel->hmac)
2994     silc_hmac_alloc(SILC_DEFAULT_HMAC, NULL, &channel->hmac);
2995   silc_hash_make(channel->hmac->hash, tmp, tmp_len, hash);
2996   silc_hmac_set_key(channel->hmac, hash, silc_hash_len(channel->hmac->hash));
2997
2998   memset(hash, 0, sizeof(hash));
2999   memset(tmp, 0, tmp_len);
3000
3001   if (server->server_type == SILC_ROUTER) {
3002     if (!channel->rekey)
3003       channel->rekey = silc_calloc(1, sizeof(*channel->rekey));
3004     channel->rekey->context = (void *)server;
3005     channel->rekey->channel = channel;
3006     if (channel->rekey->task)
3007       silc_schedule_task_del(server->schedule, channel->rekey->task);
3008
3009     channel->rekey->task = 
3010       silc_schedule_task_add(server->schedule, 0, 
3011                              silc_server_channel_key_rekey,
3012                              (void *)channel->rekey, 3600, 0,
3013                              SILC_TASK_TIMEOUT,
3014                              SILC_TASK_PRI_NORMAL);
3015   }
3016
3017  out:
3018   silc_free(id);
3019   if (payload)
3020     silc_channel_key_payload_free(payload);
3021
3022   return channel;
3023 }
3024
3025 /* Heartbeat callback. This function is set as argument for the
3026    silc_socket_set_heartbeat function. The library will call this function
3027    at the set time interval. */
3028
3029 void silc_server_perform_heartbeat(SilcSocketConnection sock,
3030                                    void *hb_context)
3031 {
3032   SilcServerHBContext hb = (SilcServerHBContext)hb_context;
3033
3034   SILC_LOG_DEBUG(("Sending heartbeat to %s (%s)", sock->hostname,
3035                   sock->ip));
3036
3037   /* Send the heartbeat */
3038   silc_server_send_heartbeat(hb->server, sock);
3039 }
3040
3041 /* Returns assembled of all servers in the given ID list. The packet's
3042    form is dictated by the New ID payload. */
3043
3044 static void silc_server_announce_get_servers(SilcServer server,
3045                                              SilcServerEntry remote,
3046                                              SilcIDList id_list,
3047                                              SilcBuffer *servers,
3048                                              unsigned long creation_time)
3049 {
3050   SilcIDCacheList list;
3051   SilcIDCacheEntry id_cache;
3052   SilcServerEntry entry;
3053   SilcBuffer idp;
3054
3055   /* Go through all clients in the list */
3056   if (silc_idcache_get_all(id_list->servers, &list)) {
3057     if (silc_idcache_list_first(list, &id_cache)) {
3058       while (id_cache) {
3059         entry = (SilcServerEntry)id_cache->context;
3060
3061         /* Do not announce the one we've sending our announcements and
3062            do not announce ourself. Also check the creation time if it's
3063            provided. */
3064         if ((entry == remote) || (entry == server->id_entry) ||
3065             (creation_time && entry->data.created < creation_time)) {
3066           if (!silc_idcache_list_next(list, &id_cache))
3067             break;
3068           continue;
3069         }
3070
3071         idp = silc_id_payload_encode(entry->id, SILC_ID_SERVER);
3072
3073         *servers = silc_buffer_realloc(*servers, 
3074                                        (*servers ? 
3075                                         (*servers)->truelen + idp->len : 
3076                                         idp->len));
3077         silc_buffer_pull_tail(*servers, ((*servers)->end - (*servers)->data));
3078         silc_buffer_put(*servers, idp->data, idp->len);
3079         silc_buffer_pull(*servers, idp->len);
3080         silc_buffer_free(idp);
3081
3082         if (!silc_idcache_list_next(list, &id_cache))
3083           break;
3084       }
3085     }
3086
3087     silc_idcache_list_free(list);
3088   }
3089 }
3090
3091 /* This function is used by router to announce existing servers to our
3092    primary router when we've connected to it. If `creation_time' is non-zero
3093    then only the servers that has been created after the `creation_time'
3094    will be announced. */
3095
3096 void silc_server_announce_servers(SilcServer server, bool global,
3097                                   unsigned long creation_time,
3098                                   SilcSocketConnection remote)
3099 {
3100   SilcBuffer servers = NULL;
3101
3102   SILC_LOG_DEBUG(("Announcing servers"));
3103
3104   /* Get servers in local list */
3105   silc_server_announce_get_servers(server, remote->user_data,
3106                                    server->local_list, &servers,
3107                                    creation_time);
3108
3109   if (global)
3110     /* Get servers in global list */
3111     silc_server_announce_get_servers(server, remote->user_data,
3112                                      server->global_list, &servers,
3113                                      creation_time);
3114
3115   if (servers) {
3116     silc_buffer_push(servers, servers->data - servers->head);
3117     SILC_LOG_HEXDUMP(("servers"), servers->data, servers->len);
3118
3119     /* Send the packet */
3120     silc_server_packet_send(server, remote,
3121                             SILC_PACKET_NEW_ID, SILC_PACKET_FLAG_LIST,
3122                             servers->data, servers->len, TRUE);
3123
3124     silc_buffer_free(servers);
3125   }
3126 }
3127
3128 /* Returns assembled packet of all clients in the given ID list. The
3129    packet's form is dictated by the New ID Payload. */
3130
3131 static void silc_server_announce_get_clients(SilcServer server,
3132                                              SilcIDList id_list,
3133                                              SilcBuffer *clients,
3134                                              unsigned long creation_time)
3135 {
3136   SilcIDCacheList list;
3137   SilcIDCacheEntry id_cache;
3138   SilcClientEntry client;
3139   SilcBuffer idp;
3140
3141   /* Go through all clients in the list */
3142   if (silc_idcache_get_all(id_list->clients, &list)) {
3143     if (silc_idcache_list_first(list, &id_cache)) {
3144       while (id_cache) {
3145         client = (SilcClientEntry)id_cache->context;
3146
3147         if (creation_time && client->data.created < creation_time) {
3148           if (!silc_idcache_list_next(list, &id_cache))
3149             break;
3150           continue;
3151         }
3152
3153         idp = silc_id_payload_encode(client->id, SILC_ID_CLIENT);
3154
3155         *clients = silc_buffer_realloc(*clients, 
3156                                        (*clients ? 
3157                                         (*clients)->truelen + idp->len : 
3158                                         idp->len));
3159         silc_buffer_pull_tail(*clients, ((*clients)->end - (*clients)->data));
3160         silc_buffer_put(*clients, idp->data, idp->len);
3161         silc_buffer_pull(*clients, idp->len);
3162         silc_buffer_free(idp);
3163
3164         if (!silc_idcache_list_next(list, &id_cache))
3165           break;
3166       }
3167     }
3168
3169     silc_idcache_list_free(list);
3170   }
3171 }
3172
3173 /* This function is used to announce our existing clients to our router
3174    when we've connected to it. If `creation_time' is non-zero then only
3175    the clients that has been created after the `creation_time' will be
3176    announced. */
3177
3178 void silc_server_announce_clients(SilcServer server,
3179                                   unsigned long creation_time,
3180                                   SilcSocketConnection remote)
3181 {
3182   SilcBuffer clients = NULL;
3183
3184   SILC_LOG_DEBUG(("Announcing clients"));
3185
3186   /* Get clients in local list */
3187   silc_server_announce_get_clients(server, server->local_list,
3188                                    &clients, creation_time);
3189
3190   /* As router we announce our global list as well */
3191   if (server->server_type == SILC_ROUTER)
3192     silc_server_announce_get_clients(server, server->global_list,
3193                                      &clients, creation_time);
3194
3195   if (clients) {
3196     silc_buffer_push(clients, clients->data - clients->head);
3197     SILC_LOG_HEXDUMP(("clients"), clients->data, clients->len);
3198
3199     /* Send the packet */
3200     silc_server_packet_send(server, remote,
3201                             SILC_PACKET_NEW_ID, SILC_PACKET_FLAG_LIST,
3202                             clients->data, clients->len, TRUE);
3203
3204     silc_buffer_free(clients);
3205   }
3206 }
3207
3208 static SilcBuffer 
3209 silc_server_announce_encode_notify(SilcNotifyType notify, uint32 argc, ...)
3210 {
3211   va_list ap;
3212   SilcBuffer p;
3213
3214   va_start(ap, argc);
3215   p = silc_notify_payload_encode(notify, argc, ap);
3216   va_end(ap);
3217  
3218   return p;
3219 }
3220
3221 /* Returns assembled packets for channel users of the `channel'. */
3222
3223 void silc_server_announce_get_channel_users(SilcServer server,
3224                                             SilcChannelEntry channel,
3225                                             SilcBuffer *channel_users,
3226                                             SilcBuffer *channel_users_modes)
3227 {
3228   SilcChannelClientEntry chl;
3229   SilcHashTableList htl;
3230   SilcBuffer chidp, clidp;
3231   SilcBuffer tmp;
3232   int len;
3233   unsigned char mode[4];
3234
3235   SILC_LOG_DEBUG(("Start"));
3236
3237   /* Now find all users on the channel */
3238   chidp = silc_id_payload_encode(channel->id, SILC_ID_CHANNEL);
3239   silc_hash_table_list(channel->user_list, &htl);
3240   while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
3241     clidp = silc_id_payload_encode(chl->client->id, SILC_ID_CLIENT);
3242
3243     /* JOIN Notify */
3244     tmp = silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_JOIN, 2, 
3245                                              clidp->data, clidp->len,
3246                                              chidp->data, chidp->len);
3247     len = tmp->len;
3248     *channel_users = 
3249       silc_buffer_realloc(*channel_users, 
3250                           (*channel_users ? 
3251                            (*channel_users)->truelen + len : len));
3252     silc_buffer_pull_tail(*channel_users, 
3253                           ((*channel_users)->end - 
3254                            (*channel_users)->data));
3255     
3256     silc_buffer_put(*channel_users, tmp->data, tmp->len);
3257     silc_buffer_pull(*channel_users, len);
3258     silc_buffer_free(tmp);
3259
3260     /* CUMODE notify for mode change on the channel */
3261     SILC_PUT32_MSB(chl->mode, mode);
3262     tmp = silc_server_announce_encode_notify(SILC_NOTIFY_TYPE_CUMODE_CHANGE, 
3263                                              3, clidp->data, clidp->len,
3264                                              mode, 4,
3265                                              clidp->data, clidp->len);
3266     len = tmp->len;
3267     *channel_users_modes = 
3268       silc_buffer_realloc(*channel_users_modes, 
3269                           (*channel_users_modes ? 
3270                            (*channel_users_modes)->truelen + len : len));
3271     silc_buffer_pull_tail(*channel_users_modes, 
3272                           ((*channel_users_modes)->end - 
3273                            (*channel_users_modes)->data));
3274     
3275     silc_buffer_put(*channel_users_modes, tmp->data, tmp->len);
3276     silc_buffer_pull(*channel_users_modes, len);
3277     silc_buffer_free(tmp);
3278
3279     silc_buffer_free(clidp);
3280   }
3281   silc_buffer_free(chidp);
3282 }
3283
3284 /* Returns assembled packets for all channels and users on those channels
3285    from the given ID List. The packets are in the form dictated by the
3286    New Channel and New Channel User payloads. */
3287
3288 void silc_server_announce_get_channels(SilcServer server,
3289                                        SilcIDList id_list,
3290                                        SilcBuffer *channels,
3291                                        SilcBuffer *channel_users,
3292                                        SilcBuffer **channel_users_modes,
3293                                        uint32 *channel_users_modes_c,
3294                                        SilcChannelID ***channel_ids,
3295                                        unsigned long creation_time)
3296 {
3297   SilcIDCacheList list;
3298   SilcIDCacheEntry id_cache;
3299   SilcChannelEntry channel;
3300   unsigned char *cid;
3301   uint32 id_len;
3302   uint16 name_len;
3303   int len;
3304   int i = *channel_users_modes_c;
3305   bool announce;
3306
3307   SILC_LOG_DEBUG(("Start"));
3308
3309   /* Go through all channels in the list */
3310   if (silc_idcache_get_all(id_list->channels, &list)) {
3311     if (silc_idcache_list_first(list, &id_cache)) {
3312       while (id_cache) {
3313         channel = (SilcChannelEntry)id_cache->context;
3314
3315         if (creation_time && channel->created < creation_time)
3316           announce = FALSE;
3317         else
3318           announce = TRUE;
3319
3320         cid = silc_id_id2str(channel->id, SILC_ID_CHANNEL);
3321         id_len = silc_id_get_len(channel->id, SILC_ID_CHANNEL);
3322         name_len = strlen(channel->channel_name);
3323
3324         if (announce) {
3325           len = 4 + name_len + id_len + 4;
3326           *channels = 
3327             silc_buffer_realloc(*channels, 
3328                                 (*channels ? (*channels)->truelen + 
3329                                  len : len));
3330           silc_buffer_pull_tail(*channels, 
3331                                 ((*channels)->end - (*channels)->data));
3332           silc_buffer_format(*channels,
3333                              SILC_STR_UI_SHORT(name_len),
3334                              SILC_STR_UI_XNSTRING(channel->channel_name, 
3335                                                   name_len),
3336                              SILC_STR_UI_SHORT(id_len),
3337                              SILC_STR_UI_XNSTRING(cid, id_len),
3338                              SILC_STR_UI_INT(channel->mode),
3339                              SILC_STR_END);
3340           silc_buffer_pull(*channels, len);
3341         }
3342
3343         *channel_users_modes = silc_realloc(*channel_users_modes,
3344                                             sizeof(**channel_users_modes) * 
3345                                             (i + 1));
3346         (*channel_users_modes)[i] = NULL;
3347         *channel_ids = silc_realloc(*channel_ids, 
3348                                     sizeof(**channel_ids) * (i + 1));
3349         (*channel_ids)[i] = NULL;
3350         silc_server_announce_get_channel_users(server, channel,
3351                                                channel_users,
3352                                                channel_users_modes[i]);
3353         (*channel_ids)[i] = channel->id;
3354         i++;
3355
3356         if (!silc_idcache_list_next(list, &id_cache))
3357           break;
3358       }
3359
3360       *channel_users_modes_c += i;
3361     }
3362
3363     silc_idcache_list_free(list);
3364   }
3365 }
3366
3367 /* This function is used to announce our existing channels to our router
3368    when we've connected to it. This also announces the users on the
3369    channels to the router. If the `creation_time' is non-zero only the
3370    channels that was created after the `creation_time' are announced.
3371    Note that the channel users are still announced even if the `creation_time'
3372    was provided. */
3373
3374 void silc_server_announce_channels(SilcServer server,
3375                                    unsigned long creation_time,
3376                                    SilcSocketConnection remote)
3377 {
3378   SilcBuffer channels = NULL, channel_users = NULL;
3379   SilcBuffer *channel_users_modes = NULL;
3380   uint32 channel_users_modes_c = 0;
3381   SilcChannelID **channel_ids = NULL;
3382
3383   SILC_LOG_DEBUG(("Announcing channels and channel users"));
3384
3385   /* Get channels and channel users in local list */
3386   silc_server_announce_get_channels(server, server->local_list,
3387                                     &channels, &channel_users,
3388                                     &channel_users_modes,
3389                                     &channel_users_modes_c,
3390                                     &channel_ids, creation_time);
3391
3392   /* Get channels and channel users in global list */
3393   silc_server_announce_get_channels(server, server->global_list,
3394                                     &channels, &channel_users,
3395                                     &channel_users_modes,
3396                                     &channel_users_modes_c,
3397                                     &channel_ids, creation_time);
3398
3399   if (channels) {
3400     silc_buffer_push(channels, channels->data - channels->head);
3401     SILC_LOG_HEXDUMP(("channels"), channels->data, channels->len);
3402
3403     /* Send the packet */
3404     silc_server_packet_send(server, remote,
3405                             SILC_PACKET_NEW_CHANNEL, SILC_PACKET_FLAG_LIST,
3406                             channels->data, channels->len,
3407                             FALSE);
3408
3409     silc_buffer_free(channels);
3410   }
3411
3412   if (channel_users) {
3413     silc_buffer_push(channel_users, channel_users->data - channel_users->head);
3414     SILC_LOG_HEXDUMP(("channel users"), channel_users->data, 
3415                      channel_users->len);
3416
3417     /* Send the packet */
3418     silc_server_packet_send(server, remote,
3419                             SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
3420                             channel_users->data, channel_users->len,
3421                             FALSE);
3422
3423     silc_buffer_free(channel_users);
3424   }
3425
3426   if (channel_users_modes) {
3427     int i;
3428
3429     for (i = 0; i < channel_users_modes_c; i++) {
3430       silc_buffer_push(channel_users_modes[i], 
3431                        channel_users_modes[i]->data - 
3432                        channel_users_modes[i]->head);
3433       SILC_LOG_HEXDUMP(("channel users modes"), channel_users_modes[i]->data, 
3434                        channel_users_modes[i]->len);
3435       silc_server_packet_send_dest(server, remote,
3436                                    SILC_PACKET_NOTIFY, SILC_PACKET_FLAG_LIST,
3437                                    channel_ids[i], SILC_ID_CHANNEL,
3438                                    channel_users_modes[i]->data, 
3439                                    channel_users_modes[i]->len,
3440                                    FALSE);
3441       silc_buffer_free(channel_users_modes[i]);
3442     }
3443     silc_free(channel_users_modes);
3444     silc_free(channel_ids);
3445   }
3446 }
3447
3448 /* Failure timeout callback. If this is called then we will immediately
3449    process the received failure. We always process the failure with timeout
3450    since we do not want to blindly trust to received failure packets. 
3451    This won't be called (the timeout is cancelled) if the failure was
3452    bogus (it is bogus if remote does not close the connection after sending
3453    the failure). */
3454
3455 SILC_TASK_CALLBACK(silc_server_failure_callback)
3456 {
3457   SilcServerFailureContext f = (SilcServerFailureContext)context;
3458
3459   if (f->sock->protocol) {
3460     f->sock->protocol->state = SILC_PROTOCOL_STATE_FAILURE;
3461     silc_protocol_execute(f->sock->protocol, f->server->schedule, 0, 0);
3462   }
3463
3464   silc_free(f);
3465 }
3466
3467 /* Assembles user list and users mode list from the `channel'. */
3468
3469 void silc_server_get_users_on_channel(SilcServer server,
3470                                       SilcChannelEntry channel,
3471                                       SilcBuffer *user_list,
3472                                       SilcBuffer *mode_list,
3473                                       uint32 *user_count)
3474 {
3475   SilcChannelClientEntry chl;
3476   SilcHashTableList htl;
3477   SilcBuffer client_id_list;
3478   SilcBuffer client_mode_list;
3479   SilcBuffer idp;
3480   uint32 list_count = 0, len = 0;
3481
3482   silc_hash_table_list(channel->user_list, &htl);
3483   while (silc_hash_table_get(&htl, NULL, (void *)&chl))
3484     len += (silc_id_get_len(chl->client->id, SILC_ID_CLIENT) + 4);
3485
3486   client_id_list = silc_buffer_alloc(len);
3487   client_mode_list = 
3488     silc_buffer_alloc(4 * silc_hash_table_count(channel->user_list));
3489   silc_buffer_pull_tail(client_id_list, SILC_BUFFER_END(client_id_list));
3490   silc_buffer_pull_tail(client_mode_list, SILC_BUFFER_END(client_mode_list));
3491
3492   silc_hash_table_list(channel->user_list, &htl);
3493   while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
3494     /* Client ID */
3495     idp = silc_id_payload_encode(chl->client->id, SILC_ID_CLIENT);
3496     silc_buffer_put(client_id_list, idp->data, idp->len);
3497     silc_buffer_pull(client_id_list, idp->len);
3498     silc_buffer_free(idp);
3499
3500     /* Client's mode on channel */
3501     SILC_PUT32_MSB(chl->mode, client_mode_list->data);
3502     silc_buffer_pull(client_mode_list, 4);
3503
3504     list_count++;
3505   }
3506   silc_buffer_push(client_id_list, 
3507                    client_id_list->data - client_id_list->head);
3508   silc_buffer_push(client_mode_list, 
3509                    client_mode_list->data - client_mode_list->head);
3510
3511   *user_list = client_id_list;
3512   *mode_list = client_mode_list;
3513   *user_count = list_count;
3514 }
3515
3516 /* Saves users and their modes to the `channel'. */
3517
3518 void silc_server_save_users_on_channel(SilcServer server,
3519                                        SilcSocketConnection sock,
3520                                        SilcChannelEntry channel,
3521                                        SilcClientID *noadd,
3522                                        SilcBuffer user_list,
3523                                        SilcBuffer mode_list,
3524                                        uint32 user_count)
3525 {
3526   int i;
3527
3528   for (i = 0; i < user_count; i++) {
3529     uint16 idp_len;
3530     uint32 mode;
3531     SilcClientID *client_id;
3532     SilcClientEntry client;
3533
3534     /* Client ID */
3535     SILC_GET16_MSB(idp_len, user_list->data + 2);
3536     idp_len += 4;
3537     client_id = silc_id_payload_parse_id(user_list->data, idp_len);
3538     silc_buffer_pull(user_list, idp_len);
3539     if (!client_id)
3540       continue;
3541
3542     /* Mode */
3543     SILC_GET32_MSB(mode, mode_list->data);
3544     silc_buffer_pull(mode_list, 4);
3545
3546     if (noadd && SILC_ID_CLIENT_COMPARE(client_id, noadd)) {
3547       silc_free(client_id);
3548       continue;
3549     }
3550     
3551     /* Check if we have this client cached already. */
3552     client = silc_idlist_find_client_by_id(server->local_list, client_id,
3553                                            server->server_type, NULL);
3554     if (!client)
3555       client = silc_idlist_find_client_by_id(server->global_list, 
3556                                              client_id, server->server_type,
3557                                              NULL);
3558     if (!client) {
3559       /* If router did not find such Client ID in its lists then this must
3560          be bogus client or some router in the net is buggy. */
3561       if (server->server_type == SILC_ROUTER) {
3562         silc_free(client_id);
3563         continue;
3564       }
3565
3566       /* We don't have that client anywhere, add it. The client is added
3567          to global list since server didn't have it in the lists so it must be 
3568          global. */
3569       client = silc_idlist_add_client(server->global_list, NULL, NULL, NULL,
3570                                       silc_id_dup(client_id, SILC_ID_CLIENT), 
3571                                       sock->user_data, NULL);
3572       if (!client) {
3573         SILC_LOG_ERROR(("Could not add new client to the ID Cache"));
3574         silc_free(client_id);
3575         continue;
3576       }
3577
3578       client->data.status |= SILC_IDLIST_STATUS_REGISTERED;
3579     }
3580
3581     silc_free(client_id);
3582
3583     if (!silc_server_client_on_channel(client, channel)) {
3584       /* Client was not on the channel, add it. */
3585       SilcChannelClientEntry chl = silc_calloc(1, sizeof(*chl));
3586       chl->client = client;
3587       chl->mode = mode;
3588       chl->channel = channel;
3589       silc_hash_table_add(channel->user_list, chl->client, chl);
3590       silc_hash_table_add(client->channels, chl->channel, chl);
3591     }
3592   }
3593 }
3594
3595 /* Lookups route to the client indicated by the `id_data'. The connection
3596    object and internal data object is returned. Returns NULL if route
3597    could not be found to the client. If the `client_id' is specified then
3598    it is used and the `id_data' is ignored. */
3599
3600 SilcSocketConnection silc_server_get_client_route(SilcServer server,
3601                                                   unsigned char *id_data,
3602                                                   uint32 id_len,
3603                                                   SilcClientID *client_id,
3604                                                   SilcIDListData *idata)
3605 {
3606   SilcClientID *id;
3607   SilcClientEntry client;
3608
3609   SILC_LOG_DEBUG(("Start"));
3610
3611   /* Decode destination Client ID */
3612   if (!client_id) {
3613     id = silc_id_str2id(id_data, id_len, SILC_ID_CLIENT);
3614     if (!id) {
3615       SILC_LOG_ERROR(("Could not decode destination Client ID, dropped"));
3616       return NULL;
3617     }
3618   } else {
3619     id = silc_id_dup(client_id, SILC_ID_CLIENT);
3620   }
3621
3622   /* If the destination belongs to our server we don't have to route
3623      the packet anywhere but to send it to the local destination. */
3624   client = silc_idlist_find_client_by_id(server->local_list, id, TRUE, NULL);
3625   if (client) {
3626     silc_free(id);
3627
3628     /* If we are router and the client has router then the client is in
3629        our cell but not directly connected to us. */
3630     if (server->server_type == SILC_ROUTER && client->router) {
3631       /* We are of course in this case the client's router thus the route
3632          to the client is the server who owns the client. So, we will send
3633          the packet to that server. */
3634       if (idata)
3635         *idata = (SilcIDListData)client->router;
3636       return client->router->connection;
3637     }
3638
3639     /* Seems that client really is directly connected to us */
3640     if (idata)
3641       *idata = (SilcIDListData)client;
3642     return client->connection;
3643   }
3644
3645   /* Destination belongs to someone not in this server. If we are normal
3646      server our action is to send the packet to our router. */
3647   if (server->server_type != SILC_ROUTER && !server->standalone) {
3648     silc_free(id);
3649     if (idata)
3650       *idata = (SilcIDListData)server->router;
3651     return server->router->connection;
3652   }
3653
3654   /* We are router and we will perform route lookup for the destination 
3655      and send the packet to fastest route. */
3656   if (server->server_type == SILC_ROUTER && !server->standalone) {
3657     /* Check first that the ID is valid */
3658     client = silc_idlist_find_client_by_id(server->global_list, id, 
3659                                            TRUE, NULL);
3660     if (client) {
3661       SilcSocketConnection dst_sock;
3662
3663       dst_sock = silc_server_route_get(server, id, SILC_ID_CLIENT);
3664
3665       silc_free(id);
3666       if (idata)
3667         *idata = (SilcIDListData)dst_sock->user_data;
3668       return dst_sock;
3669     }
3670   }
3671
3672   silc_free(id);
3673   return NULL;
3674 }
3675
3676 /* Encodes and returns channel list of channels the `client' has joined.
3677    Secret channels are not put to the list. */
3678
3679 SilcBuffer silc_server_get_client_channel_list(SilcServer server,
3680                                                SilcClientEntry client)
3681 {
3682   SilcBuffer buffer = NULL;
3683   SilcChannelEntry channel;
3684   SilcChannelClientEntry chl;
3685   SilcHashTableList htl;
3686   unsigned char *cid;
3687   uint32 id_len;
3688   uint16 name_len;
3689   int len;
3690
3691   silc_hash_table_list(client->channels, &htl);
3692   while (silc_hash_table_get(&htl, NULL, (void *)&chl)) {
3693     channel = chl->channel;
3694
3695     if (channel->mode & SILC_CHANNEL_MODE_SECRET ||
3696         channel->mode & SILC_CHANNEL_MODE_PRIVATE)
3697       continue;
3698
3699     cid = silc_id_id2str(channel->id, SILC_ID_CHANNEL);
3700     id_len = silc_id_get_len(channel->id, SILC_ID_CHANNEL);
3701     name_len = strlen(channel->channel_name);
3702     
3703     len = 4 + name_len + id_len + 4;
3704     buffer = silc_buffer_realloc(buffer, 
3705                                  (buffer ? (buffer)->truelen + len : len));
3706     silc_buffer_pull_tail(buffer, ((buffer)->end - (buffer)->data));
3707     silc_buffer_format(buffer,
3708                        SILC_STR_UI_SHORT(name_len),
3709                        SILC_STR_UI_XNSTRING(channel->channel_name, 
3710                                             name_len),
3711                        SILC_STR_UI_SHORT(id_len),
3712                        SILC_STR_UI_XNSTRING(cid, id_len),
3713                        SILC_STR_UI_INT(chl->mode), /* Client's mode */
3714                        SILC_STR_END);
3715     silc_buffer_pull(buffer, len);
3716     silc_free(cid);
3717   }
3718
3719   if (buffer)
3720     silc_buffer_push(buffer, buffer->data - buffer->head);
3721
3722   return buffer;
3723 }
3724
3725 /* Finds client entry by Client ID and if it is not found then resolves
3726    it using WHOIS command. */
3727
3728 SilcClientEntry silc_server_get_client_resolve(SilcServer server,
3729                                                SilcClientID *client_id)
3730 {
3731   SilcClientEntry client;
3732
3733   client = silc_idlist_find_client_by_id(server->local_list, client_id,
3734                                          TRUE, NULL);
3735   if (!client) {
3736     client = silc_idlist_find_client_by_id(server->global_list, 
3737                                            client_id, TRUE, NULL);
3738     if (!client && server->server_type == SILC_ROUTER)
3739       return NULL;
3740   }
3741
3742   if (!client && server->standalone)
3743     return NULL;
3744
3745   if (!client || !client->nickname || !client->username) {
3746     SilcBuffer buffer, idp;
3747
3748     client->data.status |= SILC_IDLIST_STATUS_RESOLVING;
3749     client->data.status &= ~SILC_IDLIST_STATUS_RESOLVED;
3750     client->resolve_cmd_ident = ++server->cmd_ident;
3751
3752     idp = silc_id_payload_encode(client_id, SILC_ID_CLIENT);
3753     buffer = silc_command_payload_encode_va(SILC_COMMAND_WHOIS,
3754                                             server->cmd_ident, 1,
3755                                             3, idp->data, idp->len);
3756     silc_server_packet_send(server, client ? client->router->connection :
3757                             server->router->connection,
3758                             SILC_PACKET_COMMAND, 0,
3759                             buffer->data, buffer->len, FALSE);
3760     silc_buffer_free(idp);
3761     silc_buffer_free(buffer);
3762     return NULL;
3763   }
3764
3765   return client;
3766 }
3767
3768 /* A timeout callback for the re-key. We will be the initiator of the
3769    re-key protocol. */
3770
3771 SILC_TASK_CALLBACK(silc_server_rekey_callback)
3772 {
3773   SilcSocketConnection sock = (SilcSocketConnection)context;
3774   SilcIDListData idata = (SilcIDListData)sock->user_data;
3775   SilcServer server = (SilcServer)idata->rekey->context;
3776   SilcProtocol protocol;
3777   SilcServerRekeyInternalContext *proto_ctx;
3778
3779   SILC_LOG_DEBUG(("Start"));
3780
3781   /* Allocate internal protocol context. This is sent as context
3782      to the protocol. */
3783   proto_ctx = silc_calloc(1, sizeof(*proto_ctx));
3784   proto_ctx->server = (void *)server;
3785   proto_ctx->sock = sock;
3786   proto_ctx->responder = FALSE;
3787   proto_ctx->pfs = idata->rekey->pfs;
3788       
3789   /* Perform rekey protocol. Will call the final callback after the
3790      protocol is over. */
3791   silc_protocol_alloc(SILC_PROTOCOL_SERVER_REKEY, 
3792                       &protocol, proto_ctx, silc_server_rekey_final);
3793   sock->protocol = protocol;
3794       
3795   /* Run the protocol */
3796   silc_protocol_execute(protocol, server->schedule, 0, 0);
3797
3798   /* Re-register re-key timeout */
3799   silc_schedule_task_add(server->schedule, sock->sock, 
3800                          silc_server_rekey_callback,
3801                          context, idata->rekey->timeout, 0,
3802                          SILC_TASK_TIMEOUT, SILC_TASK_PRI_NORMAL);
3803 }
3804
3805 /* The final callback for the REKEY protocol. This will actually take the
3806    new key material into use. */
3807
3808 SILC_TASK_CALLBACK_GLOBAL(silc_server_rekey_final)
3809 {
3810   SilcProtocol protocol = (SilcProtocol)context;
3811   SilcServerRekeyInternalContext *ctx =
3812     (SilcServerRekeyInternalContext *)protocol->context;
3813   SilcServer server = (SilcServer)ctx->server;
3814   SilcSocketConnection sock = ctx->sock;
3815
3816   SILC_LOG_DEBUG(("Start"));
3817
3818   if (protocol->state == SILC_PROTOCOL_STATE_ERROR ||
3819       protocol->state == SILC_PROTOCOL_STATE_FAILURE) {
3820     /* Error occured during protocol */
3821     SILC_LOG_ERROR(("Error occurred during rekey protocol"));
3822     silc_protocol_cancel(protocol, server->schedule);
3823     silc_protocol_free(protocol);
3824     sock->protocol = NULL;
3825     if (ctx->packet)
3826       silc_packet_context_free(ctx->packet);
3827     if (ctx->ske)
3828       silc_ske_free(ctx->ske);
3829     silc_free(ctx);
3830     return;
3831   }
3832
3833   /* Purge the outgoing data queue to assure that all rekey packets really
3834      go to the network before we quit the protocol. */
3835   silc_server_packet_queue_purge(server, sock);
3836
3837   /* Cleanup */
3838   silc_protocol_free(protocol);
3839   sock->protocol = NULL;
3840   if (ctx->packet)
3841     silc_packet_context_free(ctx->packet);
3842   if (ctx->ske)
3843     silc_ske_free(ctx->ske);
3844   silc_free(ctx);
3845 }