5 Author: Pekka Riikonen <priikone@poseidon.pspt.fi>
7 Copyright (C) 1997 - 2001 Pekka Riikonen
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
21 * Server side of the protocols.
25 #include "serverincludes.h"
26 #include "server_internal.h"
28 SILC_TASK_CALLBACK(silc_server_protocol_connection_auth);
29 SILC_TASK_CALLBACK(silc_server_protocol_key_exchange);
31 extern char *silc_version_string;
34 * Key Exhange protocol functions
37 /* Packet sending callback. This function is provided as packet sending
38 routine to the Key Exchange functions. */
40 static void silc_server_protocol_ke_send_packet(SilcSKE ske,
45 SilcProtocol protocol = (SilcProtocol)context;
46 SilcServerKEInternalContext *ctx =
47 (SilcServerKEInternalContext *)protocol->context;
48 SilcServer server = (SilcServer)ctx->server;
50 /* Send the packet immediately */
51 silc_server_packet_send(server, ske->sock,
52 type, 0, packet->data, packet->len, TRUE);
55 /* Sets the negotiated key material into use for particular connection. */
57 static int silc_server_protocol_ke_set_keys(SilcSKE ske,
58 SilcSocketConnection sock,
59 SilcSKEKeyMaterial *keymat,
65 SilcUnknownEntry conn_data;
69 SILC_LOG_DEBUG(("Setting new key into use"));
71 conn_data = silc_calloc(1, sizeof(*conn_data));
72 idata = (SilcIDListData)conn_data;
74 /* Allocate cipher to be used in the communication */
75 if (!silc_cipher_alloc(cipher->cipher->name, &idata->send_key)) {
79 if (!silc_cipher_alloc(cipher->cipher->name, &idata->receive_key)) {
84 if (is_responder == TRUE) {
85 idata->send_key->cipher->set_key(idata->send_key->context,
86 keymat->receive_enc_key,
88 idata->send_key->set_iv(idata->send_key, keymat->receive_iv);
89 idata->receive_key->cipher->set_key(idata->receive_key->context,
92 idata->receive_key->set_iv(idata->receive_key, keymat->send_iv);
95 idata->send_key->cipher->set_key(idata->send_key->context,
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);
105 /* Allocate PKCS to be used */
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
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);
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);
123 silc_hmac_alloc(nhash, &idata->hmac);
124 silc_hmac_set_key(idata->hmac, keymat->hmac_key, keymat->hmac_key_len);
126 sock->user_data = (void *)conn_data;
131 /* Check remote host version string */
133 SilcSKEStatus silc_ske_check_version(SilcSKE ske, unsigned char *version,
136 SilcSKEStatus status = SILC_SKE_STATUS_OK;
138 /* Check for initial version string */
139 if (!strstr(version, "SILC-1.0-"))
140 status = SILC_SKE_STATUS_BAD_VERSION;
142 /* Check software version */
144 if (len < strlen(silc_version_string))
145 status = SILC_SKE_STATUS_BAD_VERSION;
147 /* XXX for now there is no other tests due to the abnormal version
148 string that is used */
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. */
157 SILC_TASK_CALLBACK(silc_server_protocol_key_exchange)
159 SilcProtocol protocol = (SilcProtocol)context;
160 SilcServerKEInternalContext *ctx =
161 (SilcServerKEInternalContext *)protocol->context;
162 SilcServer server = (SilcServer)ctx->server;
163 SilcSKEStatus status = 0;
165 SILC_LOG_DEBUG(("Start"));
167 if (protocol->state == SILC_PROTOCOL_STATE_UNKNOWN)
168 protocol->state = SILC_PROTOCOL_STATE_START;
170 SILC_LOG_DEBUG(("State=%d", protocol->state));
172 switch(protocol->state) {
173 case SILC_PROTOCOL_STATE_START:
180 /* Allocate Key Exchange object */
181 ske = silc_ske_alloc();
183 ske->rng = server->rng;
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,
190 ctx->packet->buffer, NULL, NULL);
192 SilcSKEStartPayload *start_payload;
194 /* Assemble security properties. */
195 silc_ske_assemble_security_properties(ske, SILC_SKE_SP_FLAG_NONE,
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,
203 silc_server_protocol_ke_send_packet,
207 if (status != SILC_SKE_STATUS_OK) {
208 SILC_LOG_WARNING(("Error (type %d) during Key Exchange protocol",
210 SILC_LOG_DEBUG(("Error (type %d) during Key Exchange protocol",
213 protocol->state = SILC_PROTOCOL_STATE_ERROR;
214 protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
218 /* Advance protocol state and call the next state if we are responder */
220 if (ctx->responder == TRUE)
221 protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 100000);
229 if (ctx->responder == TRUE) {
230 /* Sends the selected security properties to the initiator. */
232 silc_ske_responder_phase_1(ctx->ske,
233 ctx->ske->start_payload,
234 silc_server_protocol_ke_send_packet,
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
241 status = silc_ske_initiator_phase_1(ctx->ske, ctx->packet->buffer,
245 if (status != SILC_SKE_STATUS_OK) {
246 SILC_LOG_WARNING(("Error (type %d) during Key Exchange protocol",
248 SILC_LOG_DEBUG(("Error (type %d) during Key Exchange protocol",
251 protocol->state = SILC_PROTOCOL_STATE_ERROR;
252 protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
256 /* Advance protocol state and call next state if we are initiator */
258 if (ctx->responder == FALSE)
259 protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 100000);
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,
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. */
278 silc_ske_initiator_phase_2(ctx->ske,
280 silc_server_protocol_ke_send_packet,
284 if (status != SILC_SKE_STATUS_OK) {
285 SILC_LOG_WARNING(("Error (type %d) during Key Exchange protocol",
287 SILC_LOG_DEBUG(("Error (type %d) during Key Exchange protocol",
290 protocol->state = SILC_PROTOCOL_STATE_ERROR;
291 protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
295 /* Advance protocol state and call the next state if we are responder */
297 if (ctx->responder == TRUE)
298 protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 100000);
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. */
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,
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);
322 if (status != SILC_SKE_STATUS_OK) {
323 SILC_LOG_WARNING(("Error (type %d) during Key Exchange protocol",
325 SILC_LOG_DEBUG(("Error (type %d) during Key Exchange protocol",
328 protocol->state = SILC_PROTOCOL_STATE_ERROR;
329 protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 300000);
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);
338 /* End the protocol on the next round */
339 protocol->state = SILC_PROTOCOL_STATE_END;
343 case SILC_PROTOCOL_STATE_END:
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;
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);
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,
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,
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);
374 silc_ske_free_key_material(keymat);
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);
382 /* Call the final callback */
383 if (protocol->final_callback)
384 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
386 silc_protocol_free(protocol);
390 case SILC_PROTOCOL_STATE_ERROR:
395 /* Send abort notification */
396 silc_ske_abort(ctx->ske, ctx->ske->status,
397 silc_server_protocol_ke_send_packet,
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);
406 /* On error the final callback is always called. */
407 if (protocol->final_callback)
408 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
410 silc_protocol_free(protocol);
413 case SILC_PROTOCOL_STATE_FAILURE:
415 * We have received failure from remote
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);
424 /* On error the final callback is always called. */
425 if (protocol->final_callback)
426 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
428 silc_protocol_free(protocol);
431 case SILC_PROTOCOL_STATE_UNKNOWN:
437 * Connection Authentication protocol functions
440 /* XXX move these to somehwere else */
442 int silc_server_password_authentication(SilcServer server, char *auth1,
445 if (!auth1 || !auth2)
448 if (!memcmp(auth1, auth2, strlen(auth1)))
454 int silc_server_public_key_authentication(SilcServer server,
457 unsigned int sign_len,
460 SilcPublicKey pub_key;
465 if (!pkfile || !sign)
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))
473 silc_pkcs_alloc(pub_key->name, &pkcs);
474 if (!silc_pkcs_public_key_set(pkcs, pub_key)) {
475 silc_pkcs_free(pkcs);
479 /* Make the authentication data. Protocol says it is HASH plus
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),
490 /* Verify signature */
491 if (pkcs->pkcs->verify(pkcs->context, sign, sign_len,
492 auth->data, auth->len))
494 silc_pkcs_free(pkcs);
495 silc_pkcs_public_key_free(pub_key);
496 silc_buffer_free(auth);
500 silc_pkcs_free(pkcs);
501 silc_pkcs_public_key_free(pub_key);
502 silc_buffer_free(auth);
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. */
510 SILC_TASK_CALLBACK(silc_server_protocol_connection_auth)
512 SilcProtocol protocol = (SilcProtocol)context;
513 SilcServerConnAuthInternalContext *ctx =
514 (SilcServerConnAuthInternalContext *)protocol->context;
515 SilcServer server = (SilcServer)ctx->server;
517 SILC_LOG_DEBUG(("Start"));
519 if (protocol->state == SILC_PROTOCOL_STATE_UNKNOWN)
520 protocol->state = SILC_PROTOCOL_STATE_START;
522 SILC_LOG_DEBUG(("State=%d", protocol->state));
524 switch(protocol->state) {
525 case SILC_PROTOCOL_STATE_START:
531 if (ctx->responder == TRUE) {
533 * We are receiving party
536 unsigned short payload_len;
537 unsigned short conn_type;
538 unsigned char *auth_data;
540 SILC_LOG_INFO(("Performing authentication protocol for %s (%s)",
541 ctx->sock->hostname, ctx->sock->ip));
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),
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);
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);
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);
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,
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);
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.
597 SILC_LOG_DEBUG(("Remote connection type %d", conn_type));
599 /* Remote end is client */
600 if (conn_type == SILC_SOCKET_TYPE_CLIENT) {
601 SilcServerConfigSectionClientConnection *client = NULL;
603 silc_server_config_find_client_conn(server->config,
608 silc_server_config_find_client_conn(server->config,
613 switch(client->auth_meth) {
615 /* No authentication required */
616 SILC_LOG_DEBUG(("No authentication required"));
619 case SILC_AUTH_PASSWORD:
620 /* Password authentication */
621 SILC_LOG_DEBUG(("Password authentication"));
622 ret = silc_server_password_authentication(server, auth_data,
626 memset(auth_data, 0, payload_len);
627 silc_free(auth_data);
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);
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,
651 memset(auth_data, 0, payload_len);
652 silc_free(auth_data);
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);
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);
671 protocol->state = SILC_PROTOCOL_STATE_ERROR;
672 protocol->execute(server->timeout_queue, 0,
673 protocol, fd, 0, 300000);
678 /* Remote end is server */
679 if (conn_type == SILC_SOCKET_TYPE_SERVER) {
680 SilcServerConfigSectionServerConnection *serv = NULL;
682 silc_server_config_find_server_conn(server->config,
687 silc_server_config_find_server_conn(server->config,
692 switch(serv->auth_meth) {
694 /* No authentication required */
695 SILC_LOG_DEBUG(("No authentication required"));
698 case SILC_AUTH_PASSWORD:
699 /* Password authentication */
700 SILC_LOG_DEBUG(("Password authentication"));
701 ret = silc_server_password_authentication(server, auth_data,
705 memset(auth_data, 0, payload_len);
706 silc_free(auth_data);
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);
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,
730 memset(auth_data, 0, payload_len);
731 silc_free(auth_data);
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);
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);
750 protocol->state = SILC_PROTOCOL_STATE_ERROR;
751 protocol->execute(server->timeout_queue, 0,
752 protocol, fd, 0, 300000);
757 /* Remote end is router */
758 if (conn_type == SILC_SOCKET_TYPE_ROUTER) {
759 SilcServerConfigSectionServerConnection *serv = NULL;
761 silc_server_config_find_router_conn(server->config,
766 silc_server_config_find_router_conn(server->config,
771 switch(serv->auth_meth) {
773 /* No authentication required */
774 SILC_LOG_DEBUG(("No authentication required"));
777 case SILC_AUTH_PASSWORD:
778 /* Password authentication */
779 SILC_LOG_DEBUG(("Password authentication"));
780 ret = silc_server_password_authentication(server, auth_data,
784 memset(auth_data, 0, payload_len);
785 silc_free(auth_data);
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);
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,
809 memset(auth_data, 0, payload_len);
810 silc_free(auth_data);
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);
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);
829 protocol->state = SILC_PROTOCOL_STATE_ERROR;
830 protocol->execute(server->timeout_queue, 0,
831 protocol, fd, 0, 300000);
837 memset(auth_data, 0, payload_len);
838 silc_free(auth_data);
841 /* Save connection type. This is later used to create the
842 ID for the connection. */
843 ctx->conn_type = conn_type;
845 /* Advance protocol state. */
846 protocol->state = SILC_PROTOCOL_STATE_END;
847 protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 0);
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.
857 unsigned char *auth_data = NULL;
858 unsigned int auth_data_len = 0;
860 switch(ctx->auth_meth) {
862 /* No authentication required */
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;
873 /* No authentication data exits. Ask interactively from user. */
878 case SILC_AUTH_PUBLIC_KEY:
879 /* Public key authentication */
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
891 SILC_SOCKET_TYPE_SERVER :
892 SILC_SOCKET_TYPE_ROUTER),
893 SILC_STR_UI_XNSTRING(auth_data, auth_data_len),
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);
902 memset(auth_data, 0, auth_data_len);
903 silc_free(auth_data);
905 silc_buffer_free(packet);
907 /* Next state is end of protocol */
908 protocol->state = SILC_PROTOCOL_STATE_END;
913 case SILC_PROTOCOL_STATE_END:
920 SILC_PUT32_MSB(SILC_AUTH_OK, ok);
922 /* Authentication failed */
923 silc_server_packet_send(server, ctx->sock, SILC_PACKET_SUCCESS,
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);
932 /* Protocol has ended, call the final callback */
933 if (protocol->final_callback)
934 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
936 silc_protocol_free(protocol);
939 case SILC_PROTOCOL_STATE_ERROR:
942 * Error. Send notify to remote.
944 unsigned char error[4];
946 SILC_PUT32_MSB(SILC_AUTH_FAILED, error);
948 /* Authentication failed */
949 silc_server_packet_send(server, ctx->sock, SILC_PACKET_FAILURE,
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);
958 /* On error the final callback is always called. */
959 if (protocol->final_callback)
960 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
962 silc_protocol_free(protocol);
966 case SILC_PROTOCOL_STATE_FAILURE:
968 * We have received failure from remote
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);
977 /* On error the final callback is always called. */
978 if (protocol->final_callback)
979 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
981 silc_protocol_free(protocol);
984 case SILC_PROTOCOL_STATE_UNKNOWN:
989 /* Registers protocols used in server. */
991 void silc_server_protocols_register(void)
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);
999 /* Unregisters protocols */
1001 void silc_server_protocols_unregister(void)
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);