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);
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);
379 /* Call the final callback */
380 if (protocol->final_callback)
381 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
383 silc_protocol_free(protocol);
387 case SILC_PROTOCOL_STATE_ERROR:
392 /* Send abort notification */
393 silc_ske_abort(ctx->ske, ctx->ske->status,
394 silc_server_protocol_ke_send_packet,
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);
403 /* On error the final callback is always called. */
404 if (protocol->final_callback)
405 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
407 silc_protocol_free(protocol);
410 case SILC_PROTOCOL_STATE_FAILURE:
412 * We have received failure from remote
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);
421 /* On error the final callback is always called. */
422 if (protocol->final_callback)
423 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
425 silc_protocol_free(protocol);
428 case SILC_PROTOCOL_STATE_UNKNOWN:
434 * Connection Authentication protocol functions
437 /* XXX move these to somehwere else */
439 int silc_server_password_authentication(SilcServer server, char *auth1,
442 if (!auth1 || !auth2)
445 if (!memcmp(auth1, auth2, strlen(auth1)))
451 int silc_server_public_key_authentication(SilcServer server,
454 unsigned int sign_len,
457 SilcPublicKey pub_key;
462 if (!pkfile || !sign)
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))
470 silc_pkcs_alloc(pub_key->name, &pkcs);
471 if (!silc_pkcs_public_key_set(pkcs, pub_key)) {
472 silc_pkcs_free(pkcs);
476 /* Make the authentication data. Protocol says it is HASH plus
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),
487 /* Verify signature */
488 if (pkcs->pkcs->verify(pkcs->context, sign, sign_len,
489 auth->data, auth->len))
491 silc_pkcs_free(pkcs);
492 silc_pkcs_public_key_free(pub_key);
493 silc_buffer_free(auth);
497 silc_pkcs_free(pkcs);
498 silc_pkcs_public_key_free(pub_key);
499 silc_buffer_free(auth);
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. */
507 SILC_TASK_CALLBACK(silc_server_protocol_connection_auth)
509 SilcProtocol protocol = (SilcProtocol)context;
510 SilcServerConnAuthInternalContext *ctx =
511 (SilcServerConnAuthInternalContext *)protocol->context;
512 SilcServer server = (SilcServer)ctx->server;
514 SILC_LOG_DEBUG(("Start"));
516 if (protocol->state == SILC_PROTOCOL_STATE_UNKNOWN)
517 protocol->state = SILC_PROTOCOL_STATE_START;
519 SILC_LOG_DEBUG(("State=%d", protocol->state));
521 switch(protocol->state) {
522 case SILC_PROTOCOL_STATE_START:
528 if (ctx->responder == TRUE) {
530 * We are receiving party
533 unsigned short payload_len;
534 unsigned short conn_type;
535 unsigned char *auth_data;
537 SILC_LOG_INFO(("Performing authentication protocol for %s (%s)",
538 ctx->sock->hostname, ctx->sock->ip));
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),
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);
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);
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);
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,
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);
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.
594 SILC_LOG_DEBUG(("Remote connection type %d", conn_type));
596 /* Remote end is client */
597 if (conn_type == SILC_SOCKET_TYPE_CLIENT) {
598 SilcServerConfigSectionClientConnection *client = NULL;
600 silc_server_config_find_client_conn(server->config,
605 silc_server_config_find_client_conn(server->config,
610 switch(client->auth_meth) {
612 /* No authentication required */
613 SILC_LOG_DEBUG(("No authentication required"));
616 case SILC_AUTH_PASSWORD:
617 /* Password authentication */
618 SILC_LOG_DEBUG(("Password authentication"));
619 ret = silc_server_password_authentication(server, auth_data,
623 memset(auth_data, 0, payload_len);
624 silc_free(auth_data);
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);
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,
648 memset(auth_data, 0, payload_len);
649 silc_free(auth_data);
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);
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);
668 protocol->state = SILC_PROTOCOL_STATE_ERROR;
669 protocol->execute(server->timeout_queue, 0,
670 protocol, fd, 0, 300000);
675 /* Remote end is server */
676 if (conn_type == SILC_SOCKET_TYPE_SERVER) {
677 SilcServerConfigSectionServerConnection *serv = NULL;
679 silc_server_config_find_server_conn(server->config,
684 silc_server_config_find_server_conn(server->config,
689 switch(serv->auth_meth) {
691 /* No authentication required */
692 SILC_LOG_DEBUG(("No authentication required"));
695 case SILC_AUTH_PASSWORD:
696 /* Password authentication */
697 SILC_LOG_DEBUG(("Password authentication"));
698 ret = silc_server_password_authentication(server, auth_data,
702 memset(auth_data, 0, payload_len);
703 silc_free(auth_data);
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);
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,
727 memset(auth_data, 0, payload_len);
728 silc_free(auth_data);
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);
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);
747 protocol->state = SILC_PROTOCOL_STATE_ERROR;
748 protocol->execute(server->timeout_queue, 0,
749 protocol, fd, 0, 300000);
754 /* Remote end is router */
755 if (conn_type == SILC_SOCKET_TYPE_ROUTER) {
756 SilcServerConfigSectionServerConnection *serv = NULL;
758 silc_server_config_find_router_conn(server->config,
763 silc_server_config_find_router_conn(server->config,
768 switch(serv->auth_meth) {
770 /* No authentication required */
771 SILC_LOG_DEBUG(("No authentication required"));
774 case SILC_AUTH_PASSWORD:
775 /* Password authentication */
776 SILC_LOG_DEBUG(("Password authentication"));
777 ret = silc_server_password_authentication(server, auth_data,
781 memset(auth_data, 0, payload_len);
782 silc_free(auth_data);
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);
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,
806 memset(auth_data, 0, payload_len);
807 silc_free(auth_data);
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);
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);
826 protocol->state = SILC_PROTOCOL_STATE_ERROR;
827 protocol->execute(server->timeout_queue, 0,
828 protocol, fd, 0, 300000);
834 memset(auth_data, 0, payload_len);
835 silc_free(auth_data);
838 /* Save connection type. This is later used to create the
839 ID for the connection. */
840 ctx->conn_type = conn_type;
842 /* Advance protocol state. */
843 protocol->state = SILC_PROTOCOL_STATE_END;
844 protocol->execute(server->timeout_queue, 0, protocol, fd, 0, 0);
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.
854 unsigned char *auth_data = NULL;
855 unsigned int auth_data_len = 0;
857 switch(ctx->auth_meth) {
859 /* No authentication required */
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;
870 /* No authentication data exits. Ask interactively from user. */
875 case SILC_AUTH_PUBLIC_KEY:
876 /* Public key authentication */
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
888 SILC_SOCKET_TYPE_SERVER :
889 SILC_SOCKET_TYPE_ROUTER),
890 SILC_STR_UI_XNSTRING(auth_data, auth_data_len),
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);
899 memset(auth_data, 0, auth_data_len);
900 silc_free(auth_data);
902 silc_buffer_free(packet);
904 /* Next state is end of protocol */
905 protocol->state = SILC_PROTOCOL_STATE_END;
910 case SILC_PROTOCOL_STATE_END:
917 SILC_PUT32_MSB(SILC_AUTH_OK, ok);
919 /* Authentication failed */
920 silc_server_packet_send(server, ctx->sock, SILC_PACKET_SUCCESS,
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);
929 /* Protocol has ended, call the final callback */
930 if (protocol->final_callback)
931 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
933 silc_protocol_free(protocol);
936 case SILC_PROTOCOL_STATE_ERROR:
939 * Error. Send notify to remote.
941 unsigned char error[4];
943 SILC_PUT32_MSB(SILC_AUTH_FAILED, error);
945 /* Authentication failed */
946 silc_server_packet_send(server, ctx->sock, SILC_PACKET_FAILURE,
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);
955 /* On error the final callback is always called. */
956 if (protocol->final_callback)
957 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
959 silc_protocol_free(protocol);
963 case SILC_PROTOCOL_STATE_FAILURE:
965 * We have received failure from remote
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);
974 /* On error the final callback is always called. */
975 if (protocol->final_callback)
976 protocol->execute_final(server->timeout_queue, 0, protocol, fd);
978 silc_protocol_free(protocol);
981 case SILC_PROTOCOL_STATE_UNKNOWN:
986 /* Registers protocols used in server. */
988 void silc_server_protocols_register(void)
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);
996 /* Unregisters protocols */
998 void silc_server_protocols_unregister(void)
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);