updates.
[silc.git] / apps / silcd / protocol.c
1 /*
2
3   protocol.c
4
5   Author: Pekka Riikonen <priikone@poseidon.pspt.fi>
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  * Server side of the protocols.
22  */
23 /* $Id$ */
24
25 #include "serverincludes.h"
26 #include "server_internal.h"
27
28 SILC_TASK_CALLBACK(silc_server_protocol_connection_auth);
29 SILC_TASK_CALLBACK(silc_server_protocol_key_exchange);
30
31 extern char *silc_version_string;
32
33 /*
34  * Key Exhange protocol functions
35  */
36
37 /* Packet sending callback. This function is provided as packet sending
38    routine to the Key Exchange functions. */
39
40 static void silc_server_protocol_ke_send_packet(SilcSKE ske,
41                                                 SilcBuffer packet,
42                                                 SilcPacketType type,
43                                                 void *context)
44 {
45   SilcProtocol protocol = (SilcProtocol)context;
46   SilcServerKEInternalContext *ctx = 
47     (SilcServerKEInternalContext *)protocol->context;
48   SilcServer server = (SilcServer)ctx->server;
49
50   /* Send the packet immediately */
51   silc_server_packet_send(server, ske->sock,
52                           type, 0, packet->data, packet->len, TRUE);
53 }
54
55 /* Sets the negotiated key material into use for particular connection. */
56
57 static int silc_server_protocol_ke_set_keys(SilcSKE ske,
58                                             SilcSocketConnection sock,
59                                             SilcSKEKeyMaterial *keymat,
60                                             SilcCipher cipher,
61                                             SilcPKCS pkcs,
62                                             SilcHash hash,
63                                             int is_responder)
64 {
65   SilcUnknownEntry conn_data;
66   SilcIDListData idata;
67   SilcHash nhash;
68
69   SILC_LOG_DEBUG(("Setting new key into use"));
70
71   conn_data = silc_calloc(1, sizeof(*conn_data));
72   idata = (SilcIDListData)conn_data;
73
74   /* Allocate cipher to be used in the communication */
75   if (!silc_cipher_alloc(cipher->cipher->name, &idata->send_key)) {
76     silc_free(conn_data);
77     return FALSE;
78   }
79   if (!silc_cipher_alloc(cipher->cipher->name, &idata->receive_key)) {
80     silc_free(conn_data);
81     return FALSE;
82   }
83   
84   if (is_responder == TRUE) {
85     idata->send_key->cipher->set_key(idata->send_key->context, 
86                                      keymat->receive_enc_key, 
87                                      keymat->enc_key_len);
88     idata->send_key->set_iv(idata->send_key, keymat->receive_iv);
89     idata->receive_key->cipher->set_key(idata->receive_key->context, 
90                                         keymat->send_enc_key, 
91                                         keymat->enc_key_len);
92     idata->receive_key->set_iv(idata->receive_key, keymat->send_iv);
93     
94   } else {
95     idata->send_key->cipher->set_key(idata->send_key->context, 
96                                      keymat->send_enc_key, 
97                                      keymat->enc_key_len);
98     idata->send_key->set_iv(idata->send_key, keymat->send_iv);
99     idata->receive_key->cipher->set_key(idata->receive_key->context, 
100                                         keymat->receive_enc_key, 
101                                         keymat->enc_key_len);
102     idata->receive_key->set_iv(idata->receive_key, keymat->receive_iv);
103   }
104
105   /* Allocate PKCS to be used */
106 #if 0
107   /* XXX Do we ever need to allocate PKCS for the connection??
108      If yes, we need to change KE protocol to get the initiators
109      public key. */
110   silc_pkcs_alloc(pkcs->pkcs->name, &idata->pkcs);
111   idata->public_key = silc_pkcs_public_key_alloc(XXX);
112   silc_pkcs_set_public_key(idata->pkcs, ske->ke2_payload->pk_data, 
113                            ske->ke2_payload->pk_len);
114 #endif
115
116   /* Save HMAC key to be used in the communication. */
117   if (!silc_hash_alloc(hash->hash->name, &nhash)) {
118     silc_cipher_free(idata->send_key);
119     silc_cipher_free(idata->receive_key);
120     silc_free(conn_data);
121     return FALSE;
122   }
123   silc_hmac_alloc(nhash, &idata->hmac);
124   silc_hmac_set_key(idata->hmac, keymat->hmac_key, keymat->hmac_key_len);
125
126   sock->user_data = (void *)conn_data;
127
128   return TRUE;
129 }
130
131 /* Check remote host version string */
132
133 SilcSKEStatus silc_ske_check_version(SilcSKE ske, unsigned char *version,
134                                      unsigned int len)
135 {
136   SilcSKEStatus status = SILC_SKE_STATUS_OK;
137
138   /* Check for initial version string */
139   if (!strstr(version, "SILC-1.0-"))
140     status = SILC_SKE_STATUS_BAD_VERSION;
141
142   /* Check software version */
143
144   if (len < strlen(silc_version_string))
145     status = SILC_SKE_STATUS_BAD_VERSION;
146
147   /* XXX for now there is no other tests due to the abnormal version
148      string that is used */
149
150   return status;
151 }
152
153 /* Performs key exchange protocol. This is used for both initiator
154    and responder key exchange. This is performed always when accepting
155    new connection to the server. This may be called recursively. */
156
157 SILC_TASK_CALLBACK(silc_server_protocol_key_exchange)
158 {
159   SilcProtocol protocol = (SilcProtocol)context;
160   SilcServerKEInternalContext *ctx = 
161     (SilcServerKEInternalContext *)protocol->context;
162   SilcServer server = (SilcServer)ctx->server;
163   SilcSKEStatus status = 0;
164
165   SILC_LOG_DEBUG(("Start"));
166
167   if (protocol->state == SILC_PROTOCOL_STATE_UNKNOWN)
168     protocol->state = SILC_PROTOCOL_STATE_START;
169
170   SILC_LOG_DEBUG(("State=%d", protocol->state));
171
172   switch(protocol->state) {
173   case SILC_PROTOCOL_STATE_START:
174     {
175       /*
176        * Start protocol
177        */
178       SilcSKE ske;
179
180       /* Allocate Key Exchange object */
181       ske = silc_ske_alloc();
182       ctx->ske = ske;
183       ske->rng = server->rng;
184       
185       if (ctx->responder == TRUE) {
186         /* Start the key exchange by processing the received security
187            properties packet from initiator. */
188         status = silc_ske_responder_start(ske, ctx->rng, ctx->sock,
189                                           silc_version_string,
190                                           ctx->packet->buffer, NULL, NULL);
191       } else {
192         SilcSKEStartPayload *start_payload;
193
194         /* Assemble security properties. */
195         silc_ske_assemble_security_properties(ske, SILC_SKE_SP_FLAG_NONE, 
196                                               silc_version_string,
197                                               &start_payload);
198
199         /* Start the key exchange by sending our security properties
200            to the remote end. */
201         status = silc_ske_initiator_start(ske, ctx->rng, ctx->sock,
202                                           start_payload,
203                                           silc_server_protocol_ke_send_packet,
204                                           context);
205       }
206
207       if (status != SILC_SKE_STATUS_OK) {
208         SILC_LOG_WARNING(("Error (type %d) during Key Exchange protocol",
209                           status));
210         SILC_LOG_DEBUG(("Error (type %d) during Key Exchange protocol",
211                         status));
212
213         protocol->state = SILC_PROTOCOL_STATE_ERROR;
214         protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
215         return;
216       }
217
218       /* Advance protocol state and call the next state if we are responder */
219       protocol->state++;
220       if (ctx->responder == TRUE)
221         protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 100000);
222     }
223     break;
224   case 2:
225     {
226       /* 
227        * Phase 1 
228        */
229       if (ctx->responder == TRUE) {
230         /* Sends the selected security properties to the initiator. */
231         status = 
232           silc_ske_responder_phase_1(ctx->ske, 
233                                      ctx->ske->start_payload,
234                                      silc_server_protocol_ke_send_packet,
235                                      context);
236       } else {
237         /* Call Phase-1 function. This processes the Key Exchange Start
238            paylaod reply we just got from the responder. The callback
239            function will receive the processed payload where we will
240            save it. */
241         status = silc_ske_initiator_phase_1(ctx->ske, ctx->packet->buffer,
242                                             NULL, NULL);
243       }
244
245       if (status != SILC_SKE_STATUS_OK) {
246         SILC_LOG_WARNING(("Error (type %d) during Key Exchange protocol",
247                           status));
248         SILC_LOG_DEBUG(("Error (type %d) during Key Exchange protocol",
249                         status));
250
251         protocol->state = SILC_PROTOCOL_STATE_ERROR;
252         protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
253         return;
254       }
255
256       /* Advance protocol state and call next state if we are initiator */
257       protocol->state++;
258       if (ctx->responder == FALSE)
259         protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 100000);
260     }
261     break;
262   case 3:
263     {
264       /* 
265        * Phase 2 
266        */
267       if (ctx->responder == TRUE) {
268         /* Process the received Key Exchange 1 Payload packet from
269            the initiator. This also creates our parts of the Diffie
270            Hellman algorithm. */
271         status = silc_ske_responder_phase_2(ctx->ske, ctx->packet->buffer, 
272                                             NULL, NULL);
273       } else {
274         /* Call the Phase-2 function. This creates Diffie Hellman
275            key exchange parameters and sends our public part inside
276            Key Exhange 1 Payload to the responder. */
277         status = 
278           silc_ske_initiator_phase_2(ctx->ske,
279                                      server->public_key,
280                                      silc_server_protocol_ke_send_packet,
281                                      context);
282       }
283
284       if (status != SILC_SKE_STATUS_OK) {
285         SILC_LOG_WARNING(("Error (type %d) during Key Exchange protocol",
286                           status));
287         SILC_LOG_DEBUG(("Error (type %d) during Key Exchange protocol",
288                         status));
289
290         protocol->state = SILC_PROTOCOL_STATE_ERROR;
291         protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
292         return;
293       }
294
295       /* Advance protocol state and call the next state if we are responder */
296       protocol->state++;
297       if (ctx->responder == TRUE)
298         protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 100000);
299     }
300     break;
301   case 4:
302     {
303       /* 
304        * Finish protocol
305        */
306       if (ctx->responder == TRUE) {
307         /* This creates the key exchange material and sends our
308            public parts to the initiator inside Key Exchange 2 Payload. */
309         status = 
310           silc_ske_responder_finish(ctx->ske, 
311                                     server->public_key, server->private_key,
312                                     SILC_SKE_PK_TYPE_SILC,
313                                     silc_server_protocol_ke_send_packet,
314                                     context);
315       } else {
316         /* Finish the protocol. This verifies the Key Exchange 2 payload
317            sent by responder. */
318         status = silc_ske_initiator_finish(ctx->ske, ctx->packet->buffer, 
319                                            NULL, NULL, NULL, NULL);
320       }
321
322       if (status != SILC_SKE_STATUS_OK) {
323         SILC_LOG_WARNING(("Error (type %d) during Key Exchange protocol",
324                           status));
325         SILC_LOG_DEBUG(("Error (type %d) during Key Exchange protocol",
326                         status));
327
328         protocol->state = SILC_PROTOCOL_STATE_ERROR;
329         protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
330         return;
331       }
332
333       /* Send Ok to the other end. We will end the protocol as responder
334          sends Ok to us when we will take the new keys into use. */
335       if (ctx->responder == FALSE)
336         silc_ske_end(ctx->ske, silc_server_protocol_ke_send_packet, context);
337
338       /* End the protocol on the next round */
339       protocol->state = SILC_PROTOCOL_STATE_END;
340     }
341     break;
342
343   case SILC_PROTOCOL_STATE_END:
344     {
345       /* 
346        * End protocol
347        */
348       SilcSKEKeyMaterial *keymat;
349       int key_len = silc_cipher_get_key_len(ctx->ske->prop->cipher, NULL);
350       int hash_len = ctx->ske->prop->hash->hash->hash_len;
351
352       /* Send Ok to the other end if we are responder. If we are 
353          initiator we have sent this already. */
354       if (ctx->responder == TRUE)
355         silc_ske_end(ctx->ske, silc_server_protocol_ke_send_packet, context);
356
357       /* Process the key material */
358       keymat = silc_calloc(1, sizeof(*keymat));
359       silc_ske_process_key_material(ctx->ske, 16, key_len, hash_len,
360                                     keymat);
361
362       /* Take the new keys into use. */
363       if (!silc_server_protocol_ke_set_keys(ctx->ske, ctx->sock, keymat,
364                                             ctx->ske->prop->cipher,
365                                             ctx->ske->prop->pkcs,
366                                             ctx->ske->prop->hash,
367                                             ctx->responder)) {
368         protocol->state = SILC_PROTOCOL_STATE_ERROR;
369         protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
370         return;
371       }
372
373       /* Unregister the timeout task since the protocol has ended. 
374          This was the timeout task to be executed if the protocol is
375          not completed fast enough. */
376       if (ctx->timeout_task)
377         silc_task_unregister(server->timeout_queue, ctx->timeout_task);
378
379       /* Call the final callback */
380       if (protocol->final_callback)
381         protocol->execute_final(server->timeout_queue, 0, protocol, fd);
382       else
383         silc_protocol_free(protocol);
384     }
385     break;
386
387   case SILC_PROTOCOL_STATE_ERROR:
388     /*
389      * Error occured
390      */
391
392     /* Send abort notification */
393     silc_ske_abort(ctx->ske, ctx->ske->status, 
394                    silc_server_protocol_ke_send_packet,
395                    context);
396
397     /* Unregister the timeout task since the protocol has ended. 
398        This was the timeout task to be executed if the protocol is
399        not completed fast enough. */
400     if (ctx->timeout_task)
401       silc_task_unregister(server->timeout_queue, ctx->timeout_task);
402
403     /* On error the final callback is always called. */
404     if (protocol->final_callback)
405       protocol->execute_final(server->timeout_queue, 0, protocol, fd);
406     else
407       silc_protocol_free(protocol);
408     break;
409
410   case SILC_PROTOCOL_STATE_FAILURE:
411     /*
412      * We have received failure from remote
413      */
414
415     /* Unregister the timeout task since the protocol has ended. 
416        This was the timeout task to be executed if the protocol is
417        not completed fast enough. */
418     if (ctx->timeout_task)
419       silc_task_unregister(server->timeout_queue, ctx->timeout_task);
420
421     /* On error the final callback is always called. */
422     if (protocol->final_callback)
423       protocol->execute_final(server->timeout_queue, 0, protocol, fd);
424     else
425       silc_protocol_free(protocol);
426     break;
427
428   case SILC_PROTOCOL_STATE_UNKNOWN:
429     break;
430   }
431 }
432
433 /*
434  * Connection Authentication protocol functions
435  */
436
437 /* XXX move these to somehwere else */
438
439 int silc_server_password_authentication(SilcServer server, char *auth1, 
440                                         char *auth2)
441 {
442   if (!auth1 || !auth2)
443     return FALSE;
444
445   if (!memcmp(auth1, auth2, strlen(auth1)))
446     return TRUE;
447
448   return FALSE;
449 }
450
451 int silc_server_public_key_authentication(SilcServer server,
452                                           char *pkfile,
453                                           unsigned char *sign,
454                                           unsigned int sign_len,
455                                           SilcSKE ske)
456 {
457   SilcPublicKey pub_key;
458   SilcPKCS pkcs;
459   int len;
460   SilcBuffer auth;
461
462   if (!pkfile || !sign)
463     return FALSE;
464
465   /* Load public key from file */
466   if (!silc_pkcs_load_public_key(pkfile, &pub_key, SILC_PKCS_FILE_PEM))
467     if (!silc_pkcs_load_public_key(pkfile, &pub_key, SILC_PKCS_FILE_BIN))
468       return FALSE;
469
470   silc_pkcs_alloc(pub_key->name, &pkcs);
471   if (!silc_pkcs_public_key_set(pkcs, pub_key)) {
472     silc_pkcs_free(pkcs);
473     return FALSE;
474   }
475
476   /* Make the authentication data. Protocol says it is HASH plus
477      KE Start Payload. */
478   len = ske->hash_len + ske->start_payload_copy->len;
479   auth = silc_buffer_alloc(len);
480   silc_buffer_pull_tail(auth, len);
481   silc_buffer_format(auth,
482                      SILC_STR_UI_XNSTRING(ske->hash, ske->hash_len),
483                      SILC_STR_UI_XNSTRING(ske->start_payload_copy->data,
484                                           ske->start_payload_copy->len),
485                      SILC_STR_END);
486
487   /* Verify signature */
488   if (pkcs->pkcs->verify(pkcs->context, sign, sign_len,
489                          auth->data, auth->len))
490     {
491       silc_pkcs_free(pkcs);
492       silc_pkcs_public_key_free(pub_key);
493       silc_buffer_free(auth);
494       return TRUE;
495     }
496
497   silc_pkcs_free(pkcs);
498   silc_pkcs_public_key_free(pub_key);
499   silc_buffer_free(auth);
500   return FALSE;
501 }
502
503 /* Performs connection authentication protocol. If responder, we 
504    authenticate the remote data received. If initiator, we will send
505    authentication data to the remote end. */
506
507 SILC_TASK_CALLBACK(silc_server_protocol_connection_auth)
508 {
509   SilcProtocol protocol = (SilcProtocol)context;
510   SilcServerConnAuthInternalContext *ctx = 
511     (SilcServerConnAuthInternalContext *)protocol->context;
512   SilcServer server = (SilcServer)ctx->server;
513
514   SILC_LOG_DEBUG(("Start"));
515
516   if (protocol->state == SILC_PROTOCOL_STATE_UNKNOWN)
517     protocol->state = SILC_PROTOCOL_STATE_START;
518
519   SILC_LOG_DEBUG(("State=%d", protocol->state));
520
521   switch(protocol->state) {
522   case SILC_PROTOCOL_STATE_START:
523     {
524       /* 
525        * Start protocol.
526        */
527
528       if (ctx->responder == TRUE) {
529         /*
530          * We are receiving party
531          */
532         int ret;
533         unsigned short payload_len;
534         unsigned short conn_type;
535         unsigned char *auth_data;
536
537         SILC_LOG_INFO(("Performing authentication protocol for %s (%s)",
538                        ctx->sock->hostname, ctx->sock->ip));
539
540         /* Parse the received authentication data packet. The received
541            payload is Connection Auth Payload. */
542         ret = silc_buffer_unformat(ctx->packet->buffer,
543                                    SILC_STR_UI_SHORT(&payload_len),
544                                    SILC_STR_UI_SHORT(&conn_type),
545                                    SILC_STR_END);
546         if (ret == -1) {
547           SILC_LOG_DEBUG(("Bad payload in authentication packet"));
548           protocol->state = SILC_PROTOCOL_STATE_ERROR;
549           protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
550           return;
551         }
552         
553         if (payload_len != ctx->packet->buffer->len) {
554           SILC_LOG_DEBUG(("Bad payload in authentication packet"));
555           protocol->state = SILC_PROTOCOL_STATE_ERROR;
556           protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
557           return;
558         }
559         
560         payload_len -= 4;
561         
562         if (conn_type < SILC_SOCKET_TYPE_CLIENT || 
563             conn_type > SILC_SOCKET_TYPE_ROUTER) {
564           SILC_LOG_ERROR(("Bad connection type %d", conn_type));
565           protocol->state = SILC_PROTOCOL_STATE_ERROR;
566           protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
567           return;
568         }
569         
570         if (payload_len > 0) {
571           /* Get authentication data */
572           silc_buffer_pull(ctx->packet->buffer, 4);
573           ret = silc_buffer_unformat(ctx->packet->buffer,
574                                      SILC_STR_UI_XNSTRING_ALLOC(&auth_data, 
575                                                                 payload_len),
576                                      SILC_STR_END);
577           if (ret == -1) {
578             SILC_LOG_DEBUG(("Bad payload in authentication packet"));
579             protocol->state = SILC_PROTOCOL_STATE_ERROR;
580             protocol->execute(server->timeout_queue, 0, 
581                               protocol, fd, 0, 300000);
582             return;
583           }
584         } else {
585           auth_data = NULL;
586         }
587
588         /* 
589          * Check the remote connection type and make sure that we have
590          * configured this connection. If we haven't allowed this connection
591          * the authentication must be failed.
592          */
593
594         SILC_LOG_DEBUG(("Remote connection type %d", conn_type));
595
596         /* Remote end is client */
597         if (conn_type == SILC_SOCKET_TYPE_CLIENT) {
598           SilcServerConfigSectionClientConnection *client = NULL;
599           client = 
600             silc_server_config_find_client_conn(server->config,
601                                                 ctx->sock->ip,
602                                                 ctx->sock->port);
603           if (!client)
604             client = 
605               silc_server_config_find_client_conn(server->config,
606                                                   ctx->sock->hostname,
607                                                   ctx->sock->port);
608           
609           if (client) {
610             switch(client->auth_meth) {
611             case SILC_AUTH_NONE:
612               /* No authentication required */
613               SILC_LOG_DEBUG(("No authentication required"));
614               break;
615               
616             case SILC_AUTH_PASSWORD:
617               /* Password authentication */
618               SILC_LOG_DEBUG(("Password authentication"));
619               ret = silc_server_password_authentication(server, auth_data,
620                                                         client->auth_data);
621
622               if (ret) {
623                 memset(auth_data, 0, payload_len);
624                 silc_free(auth_data);
625                 auth_data = NULL;
626                 break;
627               }
628
629               /* Authentication failed */
630               SILC_LOG_ERROR(("Authentication failed"));
631               SILC_LOG_DEBUG(("Authentication failed"));
632               protocol->state = SILC_PROTOCOL_STATE_ERROR;
633               protocol->execute(server->timeout_queue, 0, 
634                                 protocol, fd, 0, 300000);
635               return;
636               break;
637               
638             case SILC_AUTH_PUBLIC_KEY:
639               /* Public key authentication */
640               SILC_LOG_DEBUG(("Public key authentication"));
641               ret = silc_server_public_key_authentication(server, 
642                                                           client->auth_data,
643                                                           auth_data,
644                                                           payload_len, 
645                                                           ctx->ske);
646                                                           
647               if (ret) {
648                 memset(auth_data, 0, payload_len);
649                 silc_free(auth_data);
650                 auth_data = NULL;
651                 break;
652               }
653
654               SILC_LOG_ERROR(("Authentication failed"));
655               SILC_LOG_DEBUG(("Authentication failed"));
656               protocol->state = SILC_PROTOCOL_STATE_ERROR;
657               protocol->execute(server->timeout_queue, 0, 
658                                 protocol, fd, 0, 300000);
659               return;
660             }
661           } else {
662             SILC_LOG_DEBUG(("No configuration for remote connection"));
663             SILC_LOG_ERROR(("Remote connection not configured"));
664             SILC_LOG_ERROR(("Authentication failed"));
665             memset(auth_data, 0, payload_len);
666             silc_free(auth_data);
667             auth_data = NULL;
668             protocol->state = SILC_PROTOCOL_STATE_ERROR;
669             protocol->execute(server->timeout_queue, 0, 
670                               protocol, fd, 0, 300000);
671             return;
672           }
673         }
674         
675         /* Remote end is server */
676         if (conn_type == SILC_SOCKET_TYPE_SERVER) {
677           SilcServerConfigSectionServerConnection *serv = NULL;
678           serv = 
679             silc_server_config_find_server_conn(server->config,
680                                                 ctx->sock->ip,
681                                                 ctx->sock->port);
682           if (!serv)
683             serv = 
684               silc_server_config_find_server_conn(server->config,
685                                                   ctx->sock->hostname,
686                                                   ctx->sock->port);
687           
688           if (serv) {
689             switch(serv->auth_meth) {
690             case SILC_AUTH_NONE:
691               /* No authentication required */
692               SILC_LOG_DEBUG(("No authentication required"));
693               break;
694               
695             case SILC_AUTH_PASSWORD:
696               /* Password authentication */
697               SILC_LOG_DEBUG(("Password authentication"));
698               ret = silc_server_password_authentication(server, auth_data,
699                                                         serv->auth_data);
700
701               if (ret) {
702                 memset(auth_data, 0, payload_len);
703                 silc_free(auth_data);
704                 auth_data = NULL;
705                 break;
706               }
707               
708               /* Authentication failed */
709               SILC_LOG_ERROR(("Authentication failed"));
710               SILC_LOG_DEBUG(("Authentication failed"));
711               protocol->state = SILC_PROTOCOL_STATE_ERROR;
712               protocol->execute(server->timeout_queue, 0, 
713                                 protocol, fd, 0, 300000);
714               return;
715               break;
716               
717             case SILC_AUTH_PUBLIC_KEY:
718               /* Public key authentication */
719               SILC_LOG_DEBUG(("Public key authentication"));
720               ret = silc_server_public_key_authentication(server, 
721                                                           serv->auth_data,
722                                                           auth_data,
723                                                           payload_len, 
724                                                           ctx->ske);
725                                                           
726               if (ret) {
727                 memset(auth_data, 0, payload_len);
728                 silc_free(auth_data);
729                 auth_data = NULL;
730                 break;
731               }
732
733               SILC_LOG_ERROR(("Authentication failed"));
734               SILC_LOG_DEBUG(("Authentication failed"));
735               protocol->state = SILC_PROTOCOL_STATE_ERROR;
736               protocol->execute(server->timeout_queue, 0, 
737                                 protocol, fd, 0, 300000);
738               return;
739             }
740           } else {
741             SILC_LOG_DEBUG(("No configuration for remote connection"));
742             SILC_LOG_ERROR(("Remote connection not configured"));
743             SILC_LOG_ERROR(("Authentication failed"));
744             memset(auth_data, 0, payload_len);
745             silc_free(auth_data);
746             auth_data = NULL;
747             protocol->state = SILC_PROTOCOL_STATE_ERROR;
748             protocol->execute(server->timeout_queue, 0, 
749                               protocol, fd, 0, 300000);
750             return;
751           }
752         }
753         
754         /* Remote end is router */
755         if (conn_type == SILC_SOCKET_TYPE_ROUTER) {
756           SilcServerConfigSectionServerConnection *serv = NULL;
757           serv = 
758             silc_server_config_find_router_conn(server->config,
759                                                 ctx->sock->ip,
760                                                 ctx->sock->port);
761           if (!serv)
762             serv = 
763               silc_server_config_find_router_conn(server->config,
764                                                   ctx->sock->hostname,
765                                                   ctx->sock->port);
766           
767           if (serv) {
768             switch(serv->auth_meth) {
769             case SILC_AUTH_NONE:
770               /* No authentication required */
771               SILC_LOG_DEBUG(("No authentication required"));
772               break;
773               
774             case SILC_AUTH_PASSWORD:
775               /* Password authentication */
776               SILC_LOG_DEBUG(("Password authentication"));
777               ret = silc_server_password_authentication(server, auth_data,
778                                                         serv->auth_data);
779
780               if (ret) {
781                 memset(auth_data, 0, payload_len);
782                 silc_free(auth_data);
783                 auth_data = NULL;
784                 break;
785               }
786               
787               /* Authentication failed */
788               SILC_LOG_ERROR(("Authentication failed"));
789               SILC_LOG_DEBUG(("Authentication failed"));
790               protocol->state = SILC_PROTOCOL_STATE_ERROR;
791               protocol->execute(server->timeout_queue, 0, 
792                                 protocol, fd, 0, 300000);
793               return;
794               break;
795               
796             case SILC_AUTH_PUBLIC_KEY:
797               /* Public key authentication */
798               SILC_LOG_DEBUG(("Public key authentication"));
799               ret = silc_server_public_key_authentication(server, 
800                                                           serv->auth_data,
801                                                           auth_data,
802                                                           payload_len, 
803                                                           ctx->ske);
804                                                           
805               if (ret) {
806                 memset(auth_data, 0, payload_len);
807                 silc_free(auth_data);
808                 auth_data = NULL;
809                 break;
810               }
811
812               SILC_LOG_ERROR(("Authentication failed"));
813               SILC_LOG_DEBUG(("Authentication failed"));
814               protocol->state = SILC_PROTOCOL_STATE_ERROR;
815               protocol->execute(server->timeout_queue, 0, 
816                                 protocol, fd, 0, 300000);
817               return;
818             }
819           } else {
820             SILC_LOG_DEBUG(("No configuration for remote connection"));
821             SILC_LOG_ERROR(("Remote connection not configured"));
822             SILC_LOG_ERROR(("Authentication failed"));
823             memset(auth_data, 0, payload_len);
824             silc_free(auth_data);
825             auth_data = NULL;
826             protocol->state = SILC_PROTOCOL_STATE_ERROR;
827             protocol->execute(server->timeout_queue, 0, 
828                               protocol, fd, 0, 300000);
829             return;
830           }
831         }
832         
833         if (auth_data) {
834           memset(auth_data, 0, payload_len);
835           silc_free(auth_data);
836         }
837         
838         /* Save connection type. This is later used to create the
839            ID for the connection. */
840         ctx->conn_type = conn_type;
841           
842         /* Advance protocol state. */
843         protocol->state = SILC_PROTOCOL_STATE_END;
844         protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 0);
845
846       } else {
847         /* 
848          * We are initiator. We are authenticating ourselves to a
849          * remote server. We will send the authentication data to the
850          * other end for verify. 
851          */
852         SilcBuffer packet;
853         int payload_len = 0;
854         unsigned char *auth_data = NULL;
855         unsigned int auth_data_len = 0;
856         
857         switch(ctx->auth_meth) {
858         case SILC_AUTH_NONE:
859           /* No authentication required */
860           break;
861           
862         case SILC_AUTH_PASSWORD:
863           /* Password authentication */
864           if (ctx->auth_data && ctx->auth_data_len) {
865             auth_data = ctx->auth_data;
866             auth_data_len = ctx->auth_data_len;
867             break;
868           }
869
870           /* No authentication data exits. Ask interactively from user. */
871           /* XXX */
872
873           break;
874           
875         case SILC_AUTH_PUBLIC_KEY:
876           /* Public key authentication */
877           /* XXX TODO */
878           break;
879         }
880         
881         payload_len = 4 + auth_data_len;
882         packet = silc_buffer_alloc(payload_len);
883         silc_buffer_pull_tail(packet, SILC_BUFFER_END(packet));
884         silc_buffer_format(packet,
885                            SILC_STR_UI_SHORT(payload_len),
886                            SILC_STR_UI_SHORT(server->server_type 
887                                               == SILC_SERVER ?
888                                               SILC_SOCKET_TYPE_SERVER :
889                                               SILC_SOCKET_TYPE_ROUTER),
890                            SILC_STR_UI_XNSTRING(auth_data, auth_data_len),
891                            SILC_STR_END);
892         
893         /* Send the packet to server */
894         silc_server_packet_send(server, ctx->sock,
895                                 SILC_PACKET_CONNECTION_AUTH, 0, 
896                                 packet->data, packet->len, TRUE);
897         
898         if (auth_data) {
899           memset(auth_data, 0, auth_data_len);
900           silc_free(auth_data);
901         }
902         silc_buffer_free(packet);
903         
904         /* Next state is end of protocol */
905         protocol->state = SILC_PROTOCOL_STATE_END;
906       }
907     }
908     break;
909
910   case SILC_PROTOCOL_STATE_END:
911     {
912       /* 
913        * End protocol
914        */
915       unsigned char ok[4];
916
917       SILC_PUT32_MSB(SILC_AUTH_OK, ok);
918
919       /* Authentication failed */
920       silc_server_packet_send(server, ctx->sock, SILC_PACKET_SUCCESS,
921                               0, ok, 4, TRUE);
922
923       /* Unregister the timeout task since the protocol has ended. 
924          This was the timeout task to be executed if the protocol is
925          not completed fast enough. */
926       if (ctx->timeout_task)
927         silc_task_unregister(server->timeout_queue, ctx->timeout_task);
928
929       /* Protocol has ended, call the final callback */
930       if (protocol->final_callback)
931         protocol->execute_final(server->timeout_queue, 0, protocol, fd);
932       else
933         silc_protocol_free(protocol);
934     }
935     break;
936   case SILC_PROTOCOL_STATE_ERROR:
937     {
938       /*
939        * Error. Send notify to remote.
940        */
941       unsigned char error[4];
942
943       SILC_PUT32_MSB(SILC_AUTH_FAILED, error);
944
945       /* Authentication failed */
946       silc_server_packet_send(server, ctx->sock, SILC_PACKET_FAILURE,
947                               0, error, 4, TRUE);
948
949       /* Unregister the timeout task since the protocol has ended. 
950          This was the timeout task to be executed if the protocol is
951          not completed fast enough. */
952       if (ctx->timeout_task)
953         silc_task_unregister(server->timeout_queue, ctx->timeout_task);
954
955       /* On error the final callback is always called. */
956       if (protocol->final_callback)
957         protocol->execute_final(server->timeout_queue, 0, protocol, fd);
958       else
959         silc_protocol_free(protocol);
960     }
961     break;
962
963   case SILC_PROTOCOL_STATE_FAILURE:
964     /*
965      * We have received failure from remote
966      */
967
968     /* Unregister the timeout task since the protocol has ended. 
969        This was the timeout task to be executed if the protocol is
970        not completed fast enough. */
971     if (ctx->timeout_task)
972       silc_task_unregister(server->timeout_queue, ctx->timeout_task);
973
974     /* On error the final callback is always called. */
975     if (protocol->final_callback)
976       protocol->execute_final(server->timeout_queue, 0, protocol, fd);
977     else
978       silc_protocol_free(protocol);
979     break;
980
981   case SILC_PROTOCOL_STATE_UNKNOWN:
982     break;
983   }
984 }
985
986 /* Registers protocols used in server. */
987
988 void silc_server_protocols_register(void)
989 {
990   silc_protocol_register(SILC_PROTOCOL_SERVER_CONNECTION_AUTH,
991                          silc_server_protocol_connection_auth);
992   silc_protocol_register(SILC_PROTOCOL_SERVER_KEY_EXCHANGE,
993                          silc_server_protocol_key_exchange);
994 }
995
996 /* Unregisters protocols */
997
998 void silc_server_protocols_unregister(void)
999 {
1000   silc_protocol_unregister(SILC_PROTOCOL_SERVER_CONNECTION_AUTH,
1001                            silc_server_protocol_connection_auth);
1002   silc_protocol_unregister(SILC_PROTOCOL_SERVER_KEY_EXCHANGE,
1003                            silc_server_protocol_key_exchange);
1004 }