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         silc_ske_free_key_material(keymat);
371         return;
372       }
373
374       silc_ske_free_key_material(keymat);
375
376       /* Unregister the timeout task since the protocol has ended. 
377          This was the timeout task to be executed if the protocol is
378          not completed fast enough. */
379       if (ctx->timeout_task)
380         silc_task_unregister(server->timeout_queue, ctx->timeout_task);
381
382       /* Call the final callback */
383       if (protocol->final_callback)
384         protocol->execute_final(server->timeout_queue, 0, protocol, fd);
385       else
386         silc_protocol_free(protocol);
387     }
388     break;
389
390   case SILC_PROTOCOL_STATE_ERROR:
391     /*
392      * Error occured
393      */
394
395     /* Send abort notification */
396     silc_ske_abort(ctx->ske, ctx->ske->status, 
397                    silc_server_protocol_ke_send_packet,
398                    context);
399
400     /* Unregister the timeout task since the protocol has ended. 
401        This was the timeout task to be executed if the protocol is
402        not completed fast enough. */
403     if (ctx->timeout_task)
404       silc_task_unregister(server->timeout_queue, ctx->timeout_task);
405
406     /* On error the final callback is always called. */
407     if (protocol->final_callback)
408       protocol->execute_final(server->timeout_queue, 0, protocol, fd);
409     else
410       silc_protocol_free(protocol);
411     break;
412
413   case SILC_PROTOCOL_STATE_FAILURE:
414     /*
415      * We have received failure from remote
416      */
417
418     /* Unregister the timeout task since the protocol has ended. 
419        This was the timeout task to be executed if the protocol is
420        not completed fast enough. */
421     if (ctx->timeout_task)
422       silc_task_unregister(server->timeout_queue, ctx->timeout_task);
423
424     /* On error the final callback is always called. */
425     if (protocol->final_callback)
426       protocol->execute_final(server->timeout_queue, 0, protocol, fd);
427     else
428       silc_protocol_free(protocol);
429     break;
430
431   case SILC_PROTOCOL_STATE_UNKNOWN:
432     break;
433   }
434 }
435
436 /*
437  * Connection Authentication protocol functions
438  */
439
440 /* XXX move these to somehwere else */
441
442 int silc_server_password_authentication(SilcServer server, char *auth1, 
443                                         char *auth2)
444 {
445   if (!auth1 || !auth2)
446     return FALSE;
447
448   if (!memcmp(auth1, auth2, strlen(auth1)))
449     return TRUE;
450
451   return FALSE;
452 }
453
454 int silc_server_public_key_authentication(SilcServer server,
455                                           char *pkfile,
456                                           unsigned char *sign,
457                                           unsigned int sign_len,
458                                           SilcSKE ske)
459 {
460   SilcPublicKey pub_key;
461   SilcPKCS pkcs;
462   int len;
463   SilcBuffer auth;
464
465   if (!pkfile || !sign)
466     return FALSE;
467
468   /* Load public key from file */
469   if (!silc_pkcs_load_public_key(pkfile, &pub_key, SILC_PKCS_FILE_PEM))
470     if (!silc_pkcs_load_public_key(pkfile, &pub_key, SILC_PKCS_FILE_BIN))
471       return FALSE;
472
473   silc_pkcs_alloc(pub_key->name, &pkcs);
474   if (!silc_pkcs_public_key_set(pkcs, pub_key)) {
475     silc_pkcs_free(pkcs);
476     return FALSE;
477   }
478
479   /* Make the authentication data. Protocol says it is HASH plus
480      KE Start Payload. */
481   len = ske->hash_len + ske->start_payload_copy->len;
482   auth = silc_buffer_alloc(len);
483   silc_buffer_pull_tail(auth, len);
484   silc_buffer_format(auth,
485                      SILC_STR_UI_XNSTRING(ske->hash, ske->hash_len),
486                      SILC_STR_UI_XNSTRING(ske->start_payload_copy->data,
487                                           ske->start_payload_copy->len),
488                      SILC_STR_END);
489
490   /* Verify signature */
491   if (pkcs->pkcs->verify(pkcs->context, sign, sign_len,
492                          auth->data, auth->len))
493     {
494       silc_pkcs_free(pkcs);
495       silc_pkcs_public_key_free(pub_key);
496       silc_buffer_free(auth);
497       return TRUE;
498     }
499
500   silc_pkcs_free(pkcs);
501   silc_pkcs_public_key_free(pub_key);
502   silc_buffer_free(auth);
503   return FALSE;
504 }
505
506 /* Performs connection authentication protocol. If responder, we 
507    authenticate the remote data received. If initiator, we will send
508    authentication data to the remote end. */
509
510 SILC_TASK_CALLBACK(silc_server_protocol_connection_auth)
511 {
512   SilcProtocol protocol = (SilcProtocol)context;
513   SilcServerConnAuthInternalContext *ctx = 
514     (SilcServerConnAuthInternalContext *)protocol->context;
515   SilcServer server = (SilcServer)ctx->server;
516
517   SILC_LOG_DEBUG(("Start"));
518
519   if (protocol->state == SILC_PROTOCOL_STATE_UNKNOWN)
520     protocol->state = SILC_PROTOCOL_STATE_START;
521
522   SILC_LOG_DEBUG(("State=%d", protocol->state));
523
524   switch(protocol->state) {
525   case SILC_PROTOCOL_STATE_START:
526     {
527       /* 
528        * Start protocol.
529        */
530
531       if (ctx->responder == TRUE) {
532         /*
533          * We are receiving party
534          */
535         int ret;
536         unsigned short payload_len;
537         unsigned short conn_type;
538         unsigned char *auth_data;
539
540         SILC_LOG_INFO(("Performing authentication protocol for %s (%s)",
541                        ctx->sock->hostname, ctx->sock->ip));
542
543         /* Parse the received authentication data packet. The received
544            payload is Connection Auth Payload. */
545         ret = silc_buffer_unformat(ctx->packet->buffer,
546                                    SILC_STR_UI_SHORT(&payload_len),
547                                    SILC_STR_UI_SHORT(&conn_type),
548                                    SILC_STR_END);
549         if (ret == -1) {
550           SILC_LOG_DEBUG(("Bad payload in authentication packet"));
551           protocol->state = SILC_PROTOCOL_STATE_ERROR;
552           protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
553           return;
554         }
555         
556         if (payload_len != ctx->packet->buffer->len) {
557           SILC_LOG_DEBUG(("Bad payload in authentication packet"));
558           protocol->state = SILC_PROTOCOL_STATE_ERROR;
559           protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
560           return;
561         }
562         
563         payload_len -= 4;
564         
565         if (conn_type < SILC_SOCKET_TYPE_CLIENT || 
566             conn_type > SILC_SOCKET_TYPE_ROUTER) {
567           SILC_LOG_ERROR(("Bad connection type %d", conn_type));
568           protocol->state = SILC_PROTOCOL_STATE_ERROR;
569           protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
570           return;
571         }
572         
573         if (payload_len > 0) {
574           /* Get authentication data */
575           silc_buffer_pull(ctx->packet->buffer, 4);
576           ret = silc_buffer_unformat(ctx->packet->buffer,
577                                      SILC_STR_UI_XNSTRING_ALLOC(&auth_data, 
578                                                                 payload_len),
579                                      SILC_STR_END);
580           if (ret == -1) {
581             SILC_LOG_DEBUG(("Bad payload in authentication packet"));
582             protocol->state = SILC_PROTOCOL_STATE_ERROR;
583             protocol->execute(server->timeout_queue, 0, 
584                               protocol, fd, 0, 300000);
585             return;
586           }
587         } else {
588           auth_data = NULL;
589         }
590
591         /* 
592          * Check the remote connection type and make sure that we have
593          * configured this connection. If we haven't allowed this connection
594          * the authentication must be failed.
595          */
596
597         SILC_LOG_DEBUG(("Remote connection type %d", conn_type));
598
599         /* Remote end is client */
600         if (conn_type == SILC_SOCKET_TYPE_CLIENT) {
601           SilcServerConfigSectionClientConnection *client = NULL;
602           client = 
603             silc_server_config_find_client_conn(server->config,
604                                                 ctx->sock->ip,
605                                                 ctx->sock->port);
606           if (!client)
607             client = 
608               silc_server_config_find_client_conn(server->config,
609                                                   ctx->sock->hostname,
610                                                   ctx->sock->port);
611           
612           if (client) {
613             switch(client->auth_meth) {
614             case SILC_AUTH_NONE:
615               /* No authentication required */
616               SILC_LOG_DEBUG(("No authentication required"));
617               break;
618               
619             case SILC_AUTH_PASSWORD:
620               /* Password authentication */
621               SILC_LOG_DEBUG(("Password authentication"));
622               ret = silc_server_password_authentication(server, auth_data,
623                                                         client->auth_data);
624
625               if (ret) {
626                 memset(auth_data, 0, payload_len);
627                 silc_free(auth_data);
628                 auth_data = NULL;
629                 break;
630               }
631
632               /* Authentication failed */
633               SILC_LOG_ERROR(("Authentication failed"));
634               SILC_LOG_DEBUG(("Authentication failed"));
635               protocol->state = SILC_PROTOCOL_STATE_ERROR;
636               protocol->execute(server->timeout_queue, 0, 
637                                 protocol, fd, 0, 300000);
638               return;
639               break;
640               
641             case SILC_AUTH_PUBLIC_KEY:
642               /* Public key authentication */
643               SILC_LOG_DEBUG(("Public key authentication"));
644               ret = silc_server_public_key_authentication(server, 
645                                                           client->auth_data,
646                                                           auth_data,
647                                                           payload_len, 
648                                                           ctx->ske);
649                                                           
650               if (ret) {
651                 memset(auth_data, 0, payload_len);
652                 silc_free(auth_data);
653                 auth_data = NULL;
654                 break;
655               }
656
657               SILC_LOG_ERROR(("Authentication failed"));
658               SILC_LOG_DEBUG(("Authentication failed"));
659               protocol->state = SILC_PROTOCOL_STATE_ERROR;
660               protocol->execute(server->timeout_queue, 0, 
661                                 protocol, fd, 0, 300000);
662               return;
663             }
664           } else {
665             SILC_LOG_DEBUG(("No configuration for remote connection"));
666             SILC_LOG_ERROR(("Remote connection not configured"));
667             SILC_LOG_ERROR(("Authentication failed"));
668             memset(auth_data, 0, payload_len);
669             silc_free(auth_data);
670             auth_data = NULL;
671             protocol->state = SILC_PROTOCOL_STATE_ERROR;
672             protocol->execute(server->timeout_queue, 0, 
673                               protocol, fd, 0, 300000);
674             return;
675           }
676         }
677         
678         /* Remote end is server */
679         if (conn_type == SILC_SOCKET_TYPE_SERVER) {
680           SilcServerConfigSectionServerConnection *serv = NULL;
681           serv = 
682             silc_server_config_find_server_conn(server->config,
683                                                 ctx->sock->ip,
684                                                 ctx->sock->port);
685           if (!serv)
686             serv = 
687               silc_server_config_find_server_conn(server->config,
688                                                   ctx->sock->hostname,
689                                                   ctx->sock->port);
690           
691           if (serv) {
692             switch(serv->auth_meth) {
693             case SILC_AUTH_NONE:
694               /* No authentication required */
695               SILC_LOG_DEBUG(("No authentication required"));
696               break;
697               
698             case SILC_AUTH_PASSWORD:
699               /* Password authentication */
700               SILC_LOG_DEBUG(("Password authentication"));
701               ret = silc_server_password_authentication(server, auth_data,
702                                                         serv->auth_data);
703
704               if (ret) {
705                 memset(auth_data, 0, payload_len);
706                 silc_free(auth_data);
707                 auth_data = NULL;
708                 break;
709               }
710               
711               /* Authentication failed */
712               SILC_LOG_ERROR(("Authentication failed"));
713               SILC_LOG_DEBUG(("Authentication failed"));
714               protocol->state = SILC_PROTOCOL_STATE_ERROR;
715               protocol->execute(server->timeout_queue, 0, 
716                                 protocol, fd, 0, 300000);
717               return;
718               break;
719               
720             case SILC_AUTH_PUBLIC_KEY:
721               /* Public key authentication */
722               SILC_LOG_DEBUG(("Public key authentication"));
723               ret = silc_server_public_key_authentication(server, 
724                                                           serv->auth_data,
725                                                           auth_data,
726                                                           payload_len, 
727                                                           ctx->ske);
728                                                           
729               if (ret) {
730                 memset(auth_data, 0, payload_len);
731                 silc_free(auth_data);
732                 auth_data = NULL;
733                 break;
734               }
735
736               SILC_LOG_ERROR(("Authentication failed"));
737               SILC_LOG_DEBUG(("Authentication failed"));
738               protocol->state = SILC_PROTOCOL_STATE_ERROR;
739               protocol->execute(server->timeout_queue, 0, 
740                                 protocol, fd, 0, 300000);
741               return;
742             }
743           } else {
744             SILC_LOG_DEBUG(("No configuration for remote connection"));
745             SILC_LOG_ERROR(("Remote connection not configured"));
746             SILC_LOG_ERROR(("Authentication failed"));
747             memset(auth_data, 0, payload_len);
748             silc_free(auth_data);
749             auth_data = NULL;
750             protocol->state = SILC_PROTOCOL_STATE_ERROR;
751             protocol->execute(server->timeout_queue, 0, 
752                               protocol, fd, 0, 300000);
753             return;
754           }
755         }
756         
757         /* Remote end is router */
758         if (conn_type == SILC_SOCKET_TYPE_ROUTER) {
759           SilcServerConfigSectionServerConnection *serv = NULL;
760           serv = 
761             silc_server_config_find_router_conn(server->config,
762                                                 ctx->sock->ip,
763                                                 ctx->sock->port);
764           if (!serv)
765             serv = 
766               silc_server_config_find_router_conn(server->config,
767                                                   ctx->sock->hostname,
768                                                   ctx->sock->port);
769           
770           if (serv) {
771             switch(serv->auth_meth) {
772             case SILC_AUTH_NONE:
773               /* No authentication required */
774               SILC_LOG_DEBUG(("No authentication required"));
775               break;
776               
777             case SILC_AUTH_PASSWORD:
778               /* Password authentication */
779               SILC_LOG_DEBUG(("Password authentication"));
780               ret = silc_server_password_authentication(server, auth_data,
781                                                         serv->auth_data);
782
783               if (ret) {
784                 memset(auth_data, 0, payload_len);
785                 silc_free(auth_data);
786                 auth_data = NULL;
787                 break;
788               }
789               
790               /* Authentication failed */
791               SILC_LOG_ERROR(("Authentication failed"));
792               SILC_LOG_DEBUG(("Authentication failed"));
793               protocol->state = SILC_PROTOCOL_STATE_ERROR;
794               protocol->execute(server->timeout_queue, 0, 
795                                 protocol, fd, 0, 300000);
796               return;
797               break;
798               
799             case SILC_AUTH_PUBLIC_KEY:
800               /* Public key authentication */
801               SILC_LOG_DEBUG(("Public key authentication"));
802               ret = silc_server_public_key_authentication(server, 
803                                                           serv->auth_data,
804                                                           auth_data,
805                                                           payload_len, 
806                                                           ctx->ske);
807                                                           
808               if (ret) {
809                 memset(auth_data, 0, payload_len);
810                 silc_free(auth_data);
811                 auth_data = NULL;
812                 break;
813               }
814
815               SILC_LOG_ERROR(("Authentication failed"));
816               SILC_LOG_DEBUG(("Authentication failed"));
817               protocol->state = SILC_PROTOCOL_STATE_ERROR;
818               protocol->execute(server->timeout_queue, 0, 
819                                 protocol, fd, 0, 300000);
820               return;
821             }
822           } else {
823             SILC_LOG_DEBUG(("No configuration for remote connection"));
824             SILC_LOG_ERROR(("Remote connection not configured"));
825             SILC_LOG_ERROR(("Authentication failed"));
826             memset(auth_data, 0, payload_len);
827             silc_free(auth_data);
828             auth_data = NULL;
829             protocol->state = SILC_PROTOCOL_STATE_ERROR;
830             protocol->execute(server->timeout_queue, 0, 
831                               protocol, fd, 0, 300000);
832             return;
833           }
834         }
835         
836         if (auth_data) {
837           memset(auth_data, 0, payload_len);
838           silc_free(auth_data);
839         }
840         
841         /* Save connection type. This is later used to create the
842            ID for the connection. */
843         ctx->conn_type = conn_type;
844           
845         /* Advance protocol state. */
846         protocol->state = SILC_PROTOCOL_STATE_END;
847         protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 0);
848
849       } else {
850         /* 
851          * We are initiator. We are authenticating ourselves to a
852          * remote server. We will send the authentication data to the
853          * other end for verify. 
854          */
855         SilcBuffer packet;
856         int payload_len = 0;
857         unsigned char *auth_data = NULL;
858         unsigned int auth_data_len = 0;
859         
860         switch(ctx->auth_meth) {
861         case SILC_AUTH_NONE:
862           /* No authentication required */
863           break;
864           
865         case SILC_AUTH_PASSWORD:
866           /* Password authentication */
867           if (ctx->auth_data && ctx->auth_data_len) {
868             auth_data = ctx->auth_data;
869             auth_data_len = ctx->auth_data_len;
870             break;
871           }
872
873           /* No authentication data exits. Ask interactively from user. */
874           /* XXX */
875
876           break;
877           
878         case SILC_AUTH_PUBLIC_KEY:
879           /* Public key authentication */
880           /* XXX TODO */
881           break;
882         }
883         
884         payload_len = 4 + auth_data_len;
885         packet = silc_buffer_alloc(payload_len);
886         silc_buffer_pull_tail(packet, SILC_BUFFER_END(packet));
887         silc_buffer_format(packet,
888                            SILC_STR_UI_SHORT(payload_len),
889                            SILC_STR_UI_SHORT(server->server_type 
890                                               == SILC_SERVER ?
891                                               SILC_SOCKET_TYPE_SERVER :
892                                               SILC_SOCKET_TYPE_ROUTER),
893                            SILC_STR_UI_XNSTRING(auth_data, auth_data_len),
894                            SILC_STR_END);
895         
896         /* Send the packet to server */
897         silc_server_packet_send(server, ctx->sock,
898                                 SILC_PACKET_CONNECTION_AUTH, 0, 
899                                 packet->data, packet->len, TRUE);
900         
901         if (auth_data) {
902           memset(auth_data, 0, auth_data_len);
903           silc_free(auth_data);
904         }
905         silc_buffer_free(packet);
906         
907         /* Next state is end of protocol */
908         protocol->state = SILC_PROTOCOL_STATE_END;
909       }
910     }
911     break;
912
913   case SILC_PROTOCOL_STATE_END:
914     {
915       /* 
916        * End protocol
917        */
918       unsigned char ok[4];
919
920       SILC_PUT32_MSB(SILC_AUTH_OK, ok);
921
922       /* Authentication failed */
923       silc_server_packet_send(server, ctx->sock, SILC_PACKET_SUCCESS,
924                               0, ok, 4, TRUE);
925
926       /* Unregister the timeout task since the protocol has ended. 
927          This was the timeout task to be executed if the protocol is
928          not completed fast enough. */
929       if (ctx->timeout_task)
930         silc_task_unregister(server->timeout_queue, ctx->timeout_task);
931
932       /* Protocol has ended, call the final callback */
933       if (protocol->final_callback)
934         protocol->execute_final(server->timeout_queue, 0, protocol, fd);
935       else
936         silc_protocol_free(protocol);
937     }
938     break;
939   case SILC_PROTOCOL_STATE_ERROR:
940     {
941       /*
942        * Error. Send notify to remote.
943        */
944       unsigned char error[4];
945
946       SILC_PUT32_MSB(SILC_AUTH_FAILED, error);
947
948       /* Authentication failed */
949       silc_server_packet_send(server, ctx->sock, SILC_PACKET_FAILURE,
950                               0, error, 4, TRUE);
951
952       /* Unregister the timeout task since the protocol has ended. 
953          This was the timeout task to be executed if the protocol is
954          not completed fast enough. */
955       if (ctx->timeout_task)
956         silc_task_unregister(server->timeout_queue, ctx->timeout_task);
957
958       /* On error the final callback is always called. */
959       if (protocol->final_callback)
960         protocol->execute_final(server->timeout_queue, 0, protocol, fd);
961       else
962         silc_protocol_free(protocol);
963     }
964     break;
965
966   case SILC_PROTOCOL_STATE_FAILURE:
967     /*
968      * We have received failure from remote
969      */
970
971     /* Unregister the timeout task since the protocol has ended. 
972        This was the timeout task to be executed if the protocol is
973        not completed fast enough. */
974     if (ctx->timeout_task)
975       silc_task_unregister(server->timeout_queue, ctx->timeout_task);
976
977     /* On error the final callback is always called. */
978     if (protocol->final_callback)
979       protocol->execute_final(server->timeout_queue, 0, protocol, fd);
980     else
981       silc_protocol_free(protocol);
982     break;
983
984   case SILC_PROTOCOL_STATE_UNKNOWN:
985     break;
986   }
987 }
988
989 /* Registers protocols used in server. */
990
991 void silc_server_protocols_register(void)
992 {
993   silc_protocol_register(SILC_PROTOCOL_SERVER_CONNECTION_AUTH,
994                          silc_server_protocol_connection_auth);
995   silc_protocol_register(SILC_PROTOCOL_SERVER_KEY_EXCHANGE,
996                          silc_server_protocol_key_exchange);
997 }
998
999 /* Unregisters protocols */
1000
1001 void silc_server_protocols_unregister(void)
1002 {
1003   silc_protocol_unregister(SILC_PROTOCOL_SERVER_CONNECTION_AUTH,
1004                            silc_server_protocol_connection_auth);
1005   silc_protocol_unregister(SILC_PROTOCOL_SERVER_KEY_EXCHANGE,
1006                            silc_server_protocol_key_exchange);
1007 }